From: nbd <nbd@3c298f89-4303-0410-b956-a3cf2f4a3e73>
Date: Fri, 16 Nov 2007 03:11:27 +0000 (+0000)
Subject: add lzma compressed initramfs for bcm947xx
X-Git-Url: https://git.rohieb.name/openwrt.git/commitdiff_plain/547c09c6fa70494bcb90e7f3a6c631934b640154

add lzma compressed initramfs for bcm947xx


git-svn-id: svn://svn.openwrt.org/openwrt/trunk@9559 3c298f89-4303-0410-b956-a3cf2f4a3e73
---

diff --git a/target/linux/brcm47xx/patches-2.6.23/500-lzma_initramfs.patch b/target/linux/brcm47xx/patches-2.6.23/500-lzma_initramfs.patch
new file mode 100644
index 000000000..b545bba26
--- /dev/null
+++ b/target/linux/brcm47xx/patches-2.6.23/500-lzma_initramfs.patch
@@ -0,0 +1,121 @@
+Index: linux-2.6.23.1/scripts/gen_initramfs_list.sh
+===================================================================
+--- linux-2.6.23.1.orig/scripts/gen_initramfs_list.sh	2007-11-16 02:26:47.821227881 +0100
++++ linux-2.6.23.1/scripts/gen_initramfs_list.sh	2007-11-16 02:45:42.753904007 +0100
+@@ -287,7 +287,7 @@
+ 	if [ "${is_cpio_compressed}" = "compressed" ]; then
+ 		cat ${cpio_tfile} > ${output_file}
+ 	else
+-		cat ${cpio_tfile} | gzip -f -9 - > ${output_file}
++		lzma e -lc1 -lp2 -pb2 ${cpio_tfile} ${output_file}
+ 	fi
+ 	[ -z ${cpio_file} ] && rm ${cpio_tfile}
+ fi
+Index: linux-2.6.23.1/init/initramfs.c
+===================================================================
+--- linux-2.6.23.1.orig/init/initramfs.c	2007-11-16 02:26:47.829228332 +0100
++++ linux-2.6.23.1/init/initramfs.c	2007-11-16 03:03:09.661563882 +0100
+@@ -441,6 +441,69 @@
+ 	outcnt = 0;
+ }
+ 
++#include <linux/LzmaDecode.h>
++static int __init lzma_unzip(void)
++{
++	unsigned int i;  /* temp value */
++	unsigned int lc; /* literal context bits */
++	unsigned int lp; /* literal pos state bits */
++	unsigned int pb; /* pos state bits */
++	unsigned int osize; /* uncompressed size */
++	unsigned char *workspace;
++	unsigned char* outputbuffer;
++	unsigned int outsizeProcessed = 0;
++	int workspace_size;
++	int res;
++
++	// lzma args
++	i = get_byte();
++	lc = i % 9, i = i / 9;
++	lp = i % 5, pb = i / 5;
++
++	// skip dictionary size
++	for (i = 0; i < 4; i++)
++		get_byte();
++
++	/* read the lower half of uncompressed size in the header */
++	osize = ((unsigned int)get_byte()) +
++		((unsigned int)get_byte() << 8) +
++		((unsigned int)get_byte() << 16) +
++		((unsigned int)get_byte() << 24);
++
++	/* skip rest of the header (upper half of uncompressed size) */
++	for (i = 0; i < 4; i++)
++		get_byte();
++
++	workspace_size = ((LZMA_BASE_SIZE + (LZMA_LIT_SIZE << (lc + lp))) * sizeof(CProb)) + 100;
++	printk( KERN_NOTICE "initramfs: LZMA lc=%d,lp=%d,pb=%d,origSize=%d\n",
++	lc,lp,pb,osize);
++	outputbuffer = kmalloc(osize, GFP_KERNEL);
++	if (outputbuffer == 0) {
++		printk(KERN_ERR "initramfs: Couldn't allocate lzma output buffer\n");
++		return -1;
++	}
++
++	workspace = kmalloc(workspace_size, GFP_KERNEL);
++	if (workspace == NULL) {
++		printk(KERN_ERR "initramfs: Couldn't allocate lzma workspace\n");
++		return -1;
++	}
++
++	res = LzmaDecode(workspace, workspace_size, lc, lp, pb, inbuf + inptr, insize - inptr, outputbuffer, osize, &outsizeProcessed);
++	if( res != 0 ) {
++		panic( KERN_ERR "initramfs: Lzma decode failure\n");
++		return -1;
++	}
++
++	flush_buffer(outputbuffer, outsizeProcessed);
++	inptr = insize;
++
++	kfree(outputbuffer);
++	kfree(workspace);
++	state = Reset;
++	return 0;
++}
++
+ static char * __init unpack_to_rootfs(char *buf, unsigned len, int check_only)
+ {
+ 	int written;
+@@ -475,12 +538,28 @@
+ 		inptr = 0;
+ 		outcnt = 0;		/* bytes in output buffer */
+ 		bytes_out = 0;
+-		crc = (ulg)0xffffffffL; /* shift register contents */
+-		makecrc();
+-		gunzip();
+-		if (state != Reset)
++		if( inbuf[0] == 037 && ((inbuf[1] == 0213) || (inbuf[1] == 0236)))
++		{
++		   printk( KERN_NOTICE "detected gzip initramfs\n");
++		   crc = (ulg)0xffffffffL; /* shift register contents */
++		   makecrc();
++		   gunzip();
++		   if (state != Reset)
+ 			error("junk in gzipped archive");
+-		this_header = saved_offset + inptr;
++		}
++		else if(!memcmp(inbuf+1, "\x00\x00\x80\x00", 4)) /* FIXME: hardcoded dictionary size */
++		{
++		   printk( KERN_NOTICE "detected lzma initramfs\n");
++		   lzma_unzip();
++		}
++		else
++		{
++		   // skip forward ?
++		   crc = (ulg)0xffffffffL; /* shift register contents */
++		   makecrc();
++		   gunzip();
++		}
++	        this_header = saved_offset + inptr;
+ 		buf += inptr;
+ 		len -= inptr;
+ 	}