Documentation: UPX_F_VMLINUX_PPC32 changes to arch/powerpc/boot/main.c

This commit is contained in:
John Reiser 2007-04-30 13:48:50 -07:00
parent f347458c53
commit faa33d89a2

View File

@ -331,6 +331,109 @@ void PackVmlinuxBase<T>::pack(OutputFile *fo)
hdr_info.b_cto8 = ft.cto;
fo->write(&hdr_info, sizeof(hdr_info)); fo_off += sizeof(hdr_info);
ppc32_extra += sizeof(hdr_info);
#if 0 /*{ Documentation: changes to arch/powerpc/boot/main.c */
struct b_info {
unsigned sz_unc;
unsigned sz_cpr;
unsigned char b_method;
unsigned char b_ftid;
unsigned char b_cto8;
unsigned char b_unused;
};
typedef int (*upx_f_unc)( /* uncompress */
unsigned char const *src, unsigned src_len,
unsigned char *dst, unsigned *dst_len,
int method
);
typedef int (*upx_f_unf)( /* unfilter */
unsigned char *buf,
unsigned len,
unsigned cto8,
unsigned ftid
);
unsigned char const *upx_expand( // return updated src [aligned, too]
unsigned char const *src,
unsigned char *dst,
unsigned *const dst_len,
upx_f_unc const f_unc
)
{
if (0==*dst_len) {
*dst_len = ((struct b_info const *)src)->sz_unc;
}
upx_f_unf const f_unf = (upx_f_unf)(sizeof(int) + (char *)f_unc);
unsigned total_len = 0;
unsigned need = *dst_len;
while (0 < need) {
struct b_info const *const b_hdr = (struct b_info const *)src;
src = (unsigned char const *)(1+ b_hdr);
unsigned blk_len = b_hdr->sz_unc;
int const rv = (*f_unc)(src, b_hdr->sz_cpr, dst, &blk_len, b_hdr->b_method);
if (0!=rv) {
printf("decompress error %d\n\r", rv);
exit();
}
if (b_hdr->b_ftid) {
(*f_unf)(dst, b_hdr->sz_unc, b_hdr->b_cto8, b_hdr->b_ftid);
}
src += b_hdr->sz_cpr;
src += (3& -(int)src); // 4-byte align
dst += b_hdr->sz_unc;
total_len += b_hdr->sz_unc;
need -= b_hdr->sz_unc;
}
*dst_len = total_len;
return src;
}
void prep_kernel(unsigned long a1, unsigned long a2)
{
upx_f_unc f_unc = (upx_f_unc)0;
vmlinuz.addr = (unsigned long)_vmlinux_start;
vmlinuz.size = (unsigned long)(_vmlinux_end - _vmlinux_start);
if (0x55505821 == *(unsigned *)vmlinuz.addr) {
/* was compressed by upx */
/* Uncompress elfheader */
unsigned const *const fwa = (unsigned *)vmlinuz.addr;
f_unc = (upx_f_unc)((char *)&fwa[2] + fwa[1]);
unsigned dst_len = 0;
unsigned char const *src = (unsigned char const *)&fwa[2];
src = upx_expand(src, (unsigned char *)elfheader, &dst_len, f_unc);
unsigned const src_len = src - (unsigned char const *)&fwa[0];
vmlinuz.addr += src_len;
vmlinuz.size -= src_len;
} else {
memcpy(elfheader, (const void *)vmlinuz.addr,
sizeof(elfheader));
}
=====
/* Eventually gunzip the kernel */
if (f_unc) {
/* was compressed by upx */
printf("upx_expand (0x%lx <- 0x%lx:0x%0lx)...",
vmlinux.addr, vmlinuz.addr, vmlinuz.addr+vmlinuz.size);
unsigned dst_len = vmlinux.size - elfoffset;
upx_expand((unsigned char const *)vmlinuz.addr,
(unsigned char *)vmlinux.addr, &dst_len, f_unc);
printf("done 0x%lx bytes\n\r", len);
} else {
memmove((void *)vmlinux.addr,(void *)vmlinuz.addr,
vmlinuz.size);
/* Skip over the ELF header */
#ifdef DEBUG
printf("... skipping 0x%lx bytes of ELF header\n\r",
elfoffset);
#endif
vmlinux.addr += elfoffset;
}
=====
}
#endif /*}*/
}
else {
compressWithFilters(&ft, 512, &cconf, getStrategy(ft));