Building a initramfs image

Hi All,

I am trying to build an initramfs image for a ar71xx based device. The below steps captures what I thought would work but since it didn't I tried a few other things with the config's and the Makefile and I not going into the details of those as it might be misleading.

  1. git clone "https://github.com/openwrt/openwrt.git"
  2. Edited the file “target/linux/ar71xx/generic/config-default to change the following. ”CONFIG_CMDLINE="console=ttyS0,115200 loglevel=7 root=/dev/ram0 rootfstype=ramfs board=Lima"
  3. Under “Target System”, choose “Atheros AR7xxx/AR9xxx”, and under “Subtarget”, choose “Generic”
    Under “Target Profile”, I selected the “*devices LIMA” profile.
    Under “Target Images”, selected “ramdisk” (“lzma” compression) and de-selected “squashfs”.
  4. make -j2 V=s

After executing the above steps, I see the following initramfs images in the "bin/targets/ar71xx" directory.

./generic/openwrt-ar71xx-generic-vmlinux-initramfs.bin
./generic/openwrt-ar71xx-generic-uImage-initramfs-lzma.bin
./generic/openwrt-ar71xx-generic-tl-wr842n-v1-initramfs-kernel.bin

I copied them (tried each image) to the target device using TFTP and then I executed the "go 0x80060400". After this I didn't see anything upcoming up in the serial terminal.

I tried this image from the above link and it works for me.
http://hackspot.net/Circle/tftp-kernel.bin

So I believe there is something wrong with my configuration of the build and there is no issues with the set-up.

Can somebody please help me out with this.

Thanks/Siva

What is the actual device you have? Are you following a tutorial? In order for any device to boot many things need to happen just right ..

The device I am using is based on a reference design of LIMA (8devices) which is based on Atheros AR71XX.

My Squashfs image works just fine. I am trying to create an initramfs image to boot from the network (BOOTP/TFTP).

I am able to create an initramfs image with the LZMA/GZIP compression but the u-booot is not able to uncompress it (u-boot version is v1.1.4 which is quite old). I haven't tried to fix the u-boot yet because I dont want to modify it. I tried removing the compression mechanism (lzma in this case) from the below line which I added in the image/Makefile but the build is throwing this error.

KERNEL_INITRAMFS := kernel-bin | patch-cmdline | lzma | uImage lzma

ERROR-> "Invalid Compression Type - valid names are: none, bzip2, gzip, lzma, lzo"

The image I have been using is "openwrt-ar71xx-generic-ourdevice-initramfs-kernel.bin" and the "openwrt-ar71xx-generic-vmlinux-initramfs.bin" . I was looking for ways to create an initramfs image without any compression hoping that it would work.

I haven't tried to fix the u-boot yet because I dont want to modify it

Agreed. If it goes wrong your device is potentially bricked permanently. Its definitely possible but i would not attempt that myself unless i had jtag ready to rescue it.

Do you know if the uboot is modified at all by the vendor? Assuming is built from original source, this site apparently hosts the documention (curiously there are 3 separate 1.1.4 tar.bz2 files in there) . Check if those docs mention anything regarding booting from ram , and if so what extra steps are needed?

Edit: i missed you already have serial connection/ deleted redundant info

Thanks for that. I'll go through the documentation. The vendor have not made any changes to the "boot flow" part of the code. There changes are specific to their drivers. We maintain the u-boot code so we have the full freedom to modify it. It is just that we have considered it as the last option.

This is the error that I get when we use LZMA compression in the u-boot. (TFTP image is our application specific initramfs)

ath> bootm 0x80060000
  Booting image at 80060000 ...
   Image Name:   MIPS OpenWrt Linux-4.1.23
   Created:      2019-01-14  21:11:26 UTC
   Image Type:   MIPS Linux Kernel Image (lzma compressed)
   Data Size:    4380870 Bytes =  4.2 MB
   Load Address: 80060000
   Entry Point:  80060000
   Verifying Checksum at 0x80060040 ...OK
   Uncompressing Kernel Image ... ERROR: LzmaDecode.c, 543

This is the error that I get when we use GZIP compression in the u-boot. (TFTP image is our application specific initramfs)

ath> bootm 0x80060000
   Booting image at 80060000 ...
   Image Name:   MIPS OpenWrt Linux-4.1.23
   Created:      2019-01-14  21:11:26 UTC
   Image Type:   MIPS Linux Kernel Image (gzip compressed)
   Data Size:    4886742 Bytes =  4.7 MB
   Load Address: 80060000
   Entry Point:  80060000
   Verifying Checksum at 0x80060040 ...OK
   Uncompressing Kernel Image ... Error: inflate() returned -3

This is error that I get when I use the "openwrt-ar71xx-generic-vmlinux-initramfs.bin" image for TFTP.
Booting image at 80060000 ...
Bad Magic Number

This makes sense becuase this image doesnt have any image header. I also tried "go 0x80060400" on this image but still I dont see anything happening.

Could an uncompressed initramfs image work in this case?

Thanks/Siva

Is it possible to use

option

I tried to pass "none" was the compression option but it resulted in a failed build process.

Makefile:2681: *** Missing Build/none. Stop.

It looks like I am not doing it in the right away. Could you please help me find the right place to do this.

Thanks/Siva

i'm not sure how, it was just something I noticed in your post

Can you paste output from printenv ? Might contain some clues.

Bit of googling around found some genius people tftp’d a newer uboot image into ram, ‘boot’ that, and from there they could then tftp and boot their initramfs image .. :wink:

No worries. I am trying to find other ways to pass the compression as "None" with no luck so far.

Are you building from the command line or using make menuconfig to set the options

There you go.

ath> printenv
bootargs=
bootcmd=bootm 0x9f0c0000
bootdelay=1
baudrate=115200
production=no
upgrade_available=0
bootcount=3
stdin=serial
stdout=serial
stderr=serial
ethaddr=C4:93:00:0E:F8:C6
ethact=eth0
filesize=42dbd5
fileaddr=80060000
ipaddr=192.168.1.1
serverip=192.168.1.10

Thats pretty interesting. I'll take a look. I can tftp download the squashfs image and write that to the flash from the u-boot. But again that would be quite risky.

I have modified the "target/linux/ar71xx/image/Makefile" to include the KERNEL_INITRAMFS option. I have also enabled the “ramdisk” in the menuconfig under “Target Images”.

Updating the squashfs image on flash is reasonably safe (since you have serial connection available) provided you get the image size and postion right, its pretty unlikely to brick.

Updating the uboot image, yes thats a lot more risky. If anything goes wrong, its done.

The problem you are facing is not the lacking decompression algorithms of the uboot. You are loading a compressed image to 0x80060000.

The image header tells the bootloader to decompress the image to the same address, resulting in a corrupted image.

Try loading the compressed kernel to e.g. 0x80010000 and try booting the image from there (with lzma compression in place).

Thanks for the input. What you said makes perfect sense but I got the same result.

Bytes transferred = 4381212 (42da1c hex)
ath> bootm 0x80010000
 Booting image at 80010000 ...
   Image Name:   MIPS OpenWrt Linux-4.1.23
   Created:      2019-01-14  21:11:26 UTC
   Image Type:   MIPS Linux Kernel Image (lzma compressed)
   Data Size:    4381148 Bytes =  4.2 MB
   Load Address: 80060000
   Entry Point:  80060000
   Verifying Checksum at 0x80010040 ...OK
   Uncompressing Kernel Image ... ERROR: LzmaDecode.c, 543

Decoding error = 1
LZMA ERROR 1 - must RESET board to recover

https://forum.archive.openwrt.org/viewtopic.php?id=53865

The gist of that thread seems to be that the uboot lzma library doesnt understand what to do with the image it recieved, apparently due to dictionary size of the lzma compression.

@hnyman might be able to shed some light here?

you can also try the lzma loader (like in the 1043nd-v1)

Sounds familiar, likely the u-boot chokes on the compressed image's structure.

You may need to implement similar dictionary size restricting option that I figured out for WNDR3700 series (also ar71xx)

The old forum thread have disappeared, but this bug is still intact:
https://dev.archive.openwrt.org/ticket/12454#comment:12

The current implementation of that dictionary size option is in
https://github.com/openwrt/openwrt/blob/master/target/linux/ar71xx/image/generic.mk#L626

2 Likes

I tried both the solutions suggested.

$(STAGING_DIR_HOST)/bin/lzma e $(1) -d20 $(3) $(2)
$(STAGING_DIR_HOST)/bin/lzma e $(1) -lc1 -lp2 -pb2 -d20 $(3) $(2)

But the problem still persisted. The error messages were different when I TFTP ed it to 0x80060000 to
0x80010000 addresses.

ath> bootm 0x80060000
Booting image at 80060000 ...
Image Name: MIPS OpenWrt Linux-4.1.23
Created: 2019-01-14 21:11:26 UTC
Image Type: MIPS Linux Kernel Image (lzma compressed)
Data Size: 4382411 Bytes = 4.2 MB
Load Address: 80060000
Entry Point: 80060000
Verifying Checksum at 0x80060040 ...OK
Uncompressing Kernel Image ... Too big uncompressed streamLZMA ERROR 1 - must RESET board to recover

ath> bootm 0x80010000
Booting image at 80010000 ...
Image Name: MIPS OpenWrt Linux-4.1.23
Created: 2019-01-14 21:11:26 UTC
Image Type: MIPS Linux Kernel Image (lzma compressed)
Data Size: 4382411 Bytes = 4.2 MB
Load Address: 80060000
Entry Point: 80060000
Verifying Checksum at 0x80010040 ...OK
Uncompressing Kernel Image ... ERROR: LzmaDecode.c, 543

Why does the u-boot have a problem when it tries to uncompress an image from RAM. The same image works fine when uncompressed from flash.

I did manager to build an initramfs without any compression but still it doesn't boot and gets stuck in "Starting the kernel...."