
Can someone, maybe Wolfgang, comment on the maximum 4MB uncompressed size of gunzip (and, possibly, bzip2) images? I've been working on a Coldfire 5272 system for quite some time with u-boot and uClinux. Both have been remarkably stable. We use the uClinux default build wherein the root filesystem (romfs) is appended to the end of the kernel image, starting where the bss would normally be. The kernel startup code relocates the romfs image to just beyond the bss, then, and everything runs smoothly. I know that many folks in the PPC world use separate kernel and root filesystem images, for many good reasons, but many (most?) of the uClinux platforms use this concatenated kernel+romfs image. Recently, we've been adding more content to the root filesystem. As our root filesystem grew larger (say about 3MB), however, we started seeing boot problems where the kernel would boot fine but the root filesystem was clearly corrupt. I've spent the better part of two days trying to track down where things go wrong, from the kernel to u-boot. Of course, I used a hardware debugger, looked at u-boot's memory assignments, image load addresses, entry points, malloc areas, etc. I just located the source of my trouble, a hard-coded 4MB maximum uncompressed size in do_bootm:
int do_bootm (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) { ulong iflag; ulong addr; ulong data, len, checksum; ulong *len_ptr; uint unc_len = 0x400000; ^^^^^^^^^ int i, verify;
SNIP
case IH_COMP_GZIP: printf (" Uncompressing %s ... ", name); if (gunzip ((void *)ntohl(hdr->ih_load), unc_len, ^^^^^^^^ (uchar *)data, (int *)&len) != 0) { printf ("GUNZIP ERROR - must RESET board to recover\n"); SHOW_BOOT_PROGRESS (-6); do_reset (cmdtp, flag, argc, argv); } break;
SNIP
Increasing unc_len to larger values (like 6MB) seems to solve my problem. With an uncompressed image larger than 4MB, gunzip doesn't seem to generate any errors (granted, I haven't stepped through gunzip and zlib), but merrily runs along, although the data beyond the 4MB boundary seems to be missing or corrupt. It looks like there's a truncation (about line 1875 in zlib.c) to z.avail_out in zlib that prevents data from being copied beyond unc_len - maybe that should be an error instead of silently truncating data? Just a thought. I'll into submitting a patch for that. I was wondering if there was some reason for the 0x400000 magic number for unc_len. Is that just a magic number? Is that larger than anyone uses for images? I guess I'm a little surprised that this hasn't bitten anyone else so far (nothing I could see on the mailing list archive, at least). Our 1MB kernel and 3MB romfs root filesystem might be exceptionally large, I don't know. Would there be any issues with making unc_len a CFG_ macro, if I submitted a patch?
Nick Barendt