# [minihowto] Network bootable (no nfs) minimal livecd

## Raffi

This mini howto will address the changes needed to the livecd init

script and cpio ramdisk image in order to make it bootable via pxe

without using NFS. I will not be spending any time on setting up the pxe

server (other than the specific configuration needed to boot the livecd

image).

I have seen another howto on this topic, but I could not find it when I

was getting ready to convert the 2007.0 minimal livecd so I had to start

from scratch.

Recent version of cpio are able to deal the the multi part cpio

archive without the need to run them through a special spiller

program first. Due to various bugs in cpio, I would suggest using the

app-arch/cpio-2.7-r2 version.

The following patch will patch the init script on the livecd so that it

can mount the included squashfs image.

```

*** init.orig   2007-05-09 08:23:52.000000000 -0700

--- init        2007-05-09 09:32:11.000000000 -0700

***************

*** 370,375 ****

--- 370,381 ----

                        got_good_root=0

                        continue

  

+               elif [ "${REAL_ROOT}" = '/' ]

+               then

+                       got_good_root=1

+                       mkdir -p ${NEW_ROOT}/mnt/cdrom

+                       mkdir -p ${NEW_ROOT}/mnt/livecd

+                       cp /image.squashfs ${NEW_ROOT}/mnt/cdrom

                elif [ "${REAL_ROOT}" = '' ]

                then

                        # No REAL_ROOT determined/specified. Prompt user for root block device.

```

Edit 7/8/08 Added Patch for init on 2008.0

```

*** init.orig   2008-07-08 10:09:42.000000000 -0700

--- init        2008-07-08 10:09:04.000000000 -0700

***************

*** 356,362 ****

                                ;;

                esac

  

!               if [ "${REAL_ROOT}" = '' ]

                then

                        # No REAL_ROOT determined/specified. Prompt user for root block device.

                        whereis "REAL_ROOT" "root block device"

--- 356,368 ----

                                ;;

                esac

  

!               if [ "${REAL_ROOT}" = '/' ]

!               then

!                       got_good_root=1

!                       mkdir -p ${NEW_ROOT}/mnt/cdrom

!                       mkdir -p ${NEW_ROOT}/mnt/livecd

!                       cp /image.squashfs ${NEW_ROOT}/mnt/cdrom

!               elif [ "${REAL_ROOT}" = '' ]

                then

                        # No REAL_ROOT determined/specified. Prompt user for root block device.

                        whereis "REAL_ROOT" "root block device"

```

Edit 11/6/09 Added Patch for init on latest minimal cd (20091103)

```

*** init.orig   Fri Nov  6 08:40:31 2009

--- init        Fri Nov  6 08:58:00 2009

***************

*** 423,428 ****

--- 423,434 ----

                then

                        got_good_root=1

  

+               elif [ "${REAL_ROOT}" = '/' ]

+               then

+                       got_good_root=1

+                       mkdir -p ${NEW_ROOT}/mnt/cdrom

+                       mkdir -p ${NEW_ROOT}/mnt/livecd

+                       cp /image.squashfs ${NEW_ROOT}/mnt/cdrom

                else

                        bad_msg "Block device ${REAL_ROOT} is not a valid root device..."

                        REAL_ROOT=""

```

Edit 4/30/10 Added Patch for init on latest minimal cd (20100408)

```

*** init.orig   Thu Apr  8 06:29:36 2010

--- init        Thu Apr 29 13:37:54 2010

***************

*** 422,428 ****

                elif [ -b "${REAL_ROOT}" ] || [ "${REAL_ROOT}" = "/dev/nfs" ]

                then

                        got_good_root=1

! 

                else

                        bad_msg "Block device ${REAL_ROOT} is not a valid root device..."

                        REAL_ROOT=""

--- 422,433 ----

                elif [ -b "${REAL_ROOT}" ] || [ "${REAL_ROOT}" = "/dev/nfs" ]

                then

                        got_good_root=1

!               elif [ "${REAL_ROOT}" = '/' ]

!               then

!                       got_good_root=1

!                       mkdir -p ${NEW_ROOT}/mnt/cdrom

!                       mkdir -p ${NEW_ROOT}/mnt/livecd

!                       cp /image.squashfs ${NEW_ROOT}/mnt/cdrom

                else

                        bad_msg "Block device ${REAL_ROOT} is not a valid root device..."

                        REAL_ROOT=""

```

Edit 12/14/10 Added Patch for init on latest minimal cds (20101123 and 20101209)

```

*** init.orig   Tue Nov 23 04:54:52 2010

--- init        Mon Dec 13 17:16:14 2010

***************

*** 458,464 ****

                elif [ -b "${REAL_ROOT}" ] || [ "${REAL_ROOT}" = "/dev/nfs" ]

                then

                        got_good_root=1

! 

                else

                        bad_msg "Block device ${REAL_ROOT} is not a valid root device..."

                        REAL_ROOT=""

--- 458,469 ----

                elif [ -b "${REAL_ROOT}" ] || [ "${REAL_ROOT}" = "/dev/nfs" ]

                then

                        got_good_root=1

!               elif [ "${REAL_ROOT}" = '/' ]

!               then

!                       got_good_root=1

!                       mkdir -p ${NEW_ROOT}/mnt/cdrom

!                       mkdir -p ${NEW_ROOT}/mnt/livecd

!                       cp /image.squashfs ${NEW_ROOT}/mnt/cdrom 

                else

                        bad_msg "Block device ${REAL_ROOT} is not a valid root device..."

                        REAL_ROOT=""

```

Edit 7/17/2012 Added Patch for init on latest minimal cds (20120710 and 20120621)

```

*** init.orig   Mon Jul 16 14:11:54 2012

--- init        Tue Jul 17 06:33:02 2012

***************

*** 456,462 ****

                elif [ -b "${REAL_ROOT}" ] || [ "${REAL_ROOT}" = "/dev/nfs" ]

                then

                        got_good_root=1

! 

                else

                        bad_msg "Block device ${REAL_ROOT} is not a valid root device..."

                        REAL_ROOT=""

--- 456,465 ----

                elif [ -b "${REAL_ROOT}" ] || [ "${REAL_ROOT}" = "/dev/nfs" ]

                then

                        got_good_root=1

!               elif [ "${REAL_ROOT}" = '/' ]

!               then

!                       got_good_root=1

!                       cp /image.squashfs ${CDROOT_PATH}

                else

                        bad_msg "Block device ${REAL_ROOT} is not a valid root device..."

                        REAL_ROOT=""

```

Edit 5/9/2013 Added Patch for init on latest minimal cds (20130423 and 20130425)

```

--- init.orig   2013-05-09 13:19:04.952112000 -0700

+++ init        2013-05-09 13:20:58.643969000 -0700

@@ -589,7 +589,10 @@

                elif [ -b "${REAL_ROOT}" ] || [ "${REAL_ROOT}" = "/dev/nfs" ]

                then

                        got_good_root=1

-

+               elif [ "${REAL_ROOT}" = '/' ]

+               then

+                       got_good_root=1

+                       cp /image.squashfs ${CDROOT_PATH}

                else

                        bad_msg "Block device ${REAL_ROOT} is not a valid root device..."

                        REAL_ROOT=""

```

The basic steps needed for this to work are

 Unpack the cpio ramdisk file included in the minimal livecd

 Edit the init file to work with the squashfs file system included

 Add the squashfs image to the unpacked ramdisk image.

 Re-cpio gzip the ramdisk image

 Add image entry to pxe server.

The following needs to be done as root:

```

# Mount iso through loopback device so you can access the cpio file.

#

mount -o loop [i]/path/to/livecd_image.iso[/i] /mnt/loop

# Create a directory to unpack the cpio ramdisk info

#

mkdir ramdisk

cd ramdisk

zcat /mnt/loop/isolinux/gentoo.igz | cpio -ivmd

# Patch the init script in the ramdisk image

patch <[i]/path/to/where/you/saved/init.patch[/i]

# Copy in squashfs image

cp /mnt/loop/image.squashfs .

# re-cpio ramdisk image

find . -print | cpio -H newc -o | gzip -9 >../gentoo.igz

```

Edit 5/9/2013 using xz insead of gzip for initrd

```

find . -print | cpio -H newc -o | xz --check=crc32 >../gentoo.igz

```

You will now have a minimal livecd ramdisk image that can be used to

boot a system via pxe. This can be used along with the kernel from the

livecd to do a network boot.

```

cp gentoo.igz /tftpboot

cp /mnt/loop/isolinux/gentoo /tftpboot

```

To configure pxe linux to boot the system add the following to

/tftpboot/pxelinux.cfg/default or whatever name you have configured to

use.

```

label gentoo

  kernel gentoo

  append initrd=gentoo.igz root=/dev/ram0 init=/linuxrc loop=image.squashfs looptype=squashfs cdroot=1 real_root=/

```

I have successfully applied these changes to both the x86 and the amd64

version of the minimal live cd.Last edited by Raffi on Thu May 09, 2013 9:11 pm; edited 6 times in total

----------

## elgato319

thanks for this post, worked like a charm on 2007.0

----------

## ManOfMilk

I attempted to make this image and I must be having some issues, on the 945, i can get the system to post up, however, it panics with this error.

"Cannot open root device "<NULL>" or unknown-block(8,2)"

i thought passing it the /dev/ram0 is the correct root= option? Is it different with the 2007.0-r1 CD?

any help is appreciated..

----------

## st0kk

Here is a init.patch for 2007.0-r1

```

--- init        2007-05-07 22:23:48.000000000 +0200

+++ /tmp/init   2007-09-26 14:17:26.000000000 +0200

@@ -370,6 +370,13 @@

                        got_good_root=0

                        continue

+               elif [ "${REAL_ROOT}" = '/' ]

+               then

+                       got_good_root=1

+                       mkdir -p ${NEW_ROOT}/mnt/cdrom

+                       mkdir -p ${NEW_ROOT}/mnt/livecd

+                       cp /image.squashfs ${NEW_ROOT}/mnt/cdrom

+

                elif [ "${REAL_ROOT}" = '' ]

                then

                        # No REAL_ROOT determined/specified. Prompt user for root block device.

```

Many thnx for the 1st patch, it solved my 1 problem..

----------

## cnrs

Hello,

Sorry for my English, i'm French...

I have a problem with patch:

 *Quote:*   

> *** init.orig   2007-05-09 08:23:52.000000000 -0700
> 
> --- init        2007-05-09 09:32:11.000000000 -0700
> 
> ***************
> ...

 

See my problem:

 *Quote:*   

> patch < init.patch
> 
> patching file init
> 
> Hunk #1 FAILED at 370.
> ...

 

i'm paste your code in vim   :Shocked: 

 *Quote:*   

> 
> 
> opteron144 ramdisk # cat init.patch
> 
> *** init.orig   2007-05-09 08:23:52.000000000 -0700
> ...

 

thx for help me, and sorry for my English

----------

## Raffi

Try the -l option to patch.

----------

## fabiim

I've tried : 

```
root@black:~/ramdisk# patch -l < ../init.patch 

missing header for context diff at line 3 of patch

patching file init

Hunk #1 FAILED at 370.

1 out of 1 hunk FAILED -- saving rejects to file init.rej

```

As you can see it gives me some error .  

Anyway I "patched" it by hand and it did boot , i'm really thankful for your post .

 :Smile: 

----------

## solamour

It worked great with 2007.0-r1 release, but when I tried it on 2008.0-beta2, it didn't seem to find "image.squashfs" correctly. I'd appreciate any help.

__

sol

----------

## Raffi

I have not looked at any of the 2008 betas. I have been waiting for the final release. Can you find the image.squashfs on the cd? Did the location change?

----------

## solamour

"image.squashfs" is there, and "init" script didn't seem to be changed much as well. However, one thing that I noticed is that GRUB is used in 2008 beta, although I'm not certain how that would make things different. Anyhow, no big deal. I'm sure things would work out when the final version is released.

__

sol

----------

## Raffi

I have posted a patch that will work for 2008.0. So far, I have edited the x86 version and things work. I will be doing the amd64 next.

----------

## Raffi

Works for amd64 as well, but the name of the directory on that cd is boot instead of isolinux.

----------

## richard.scott

Hi,

Is there a size limit on the final initramfs file?

Before copy in my squashfs image pxelinux can find it, and after it can't

Cheers,

Rich

----------

## Raffi

I have not run into a size limit, how big is your file? Mine are around 60M.

----------

## richard.scott

 *Raffi wrote:*   

> I have not run into a size limit, how big is your file? Mine are around 60M.

 

LOL, my initramfs file ends up being over 168M   :Wink: 

My SquashFS file is around that size and works fine from a CD or USB stick  :Smile: 

(I was hoping it would work via this method too)

----------

## Raffi

Interesting. I would not have expected a size limit, but that is a lot of data. When you said it did not see it, I assume that means it says file not found or some such and does not try to load for a while and then stop.

It would be interesting for your to try to narrow down when it stops working. We have a data point at around 60M, if you can try something at that size and it still does not work, the size is not the issue. If it does, keep upping the size until it breaks.

----------

## richard.scott

 *Raffi wrote:*   

> Interesting. I would not have expected a size limit, but that is a lot of data. When you said it did not see it, I assume that means it says file not found or some such and does not try to load for a while and then stop.
> 
> It would be interesting for your to try to narrow down when it stops working. We have a data point at around 60M, if you can try something at that size and it still does not work, the size is not the issue. If it does, keep upping the size until it breaks.

 

It's the pxelinux part that doesn't see the file. I get the Loading /kernel........ part and then the next line errors on not finding the /initramfs file.

I'll try using files from a LiveCD and increase the initramfs file to see when it does error again. I'll start at a 60MB file and work up  :Wink: 

----------

## richard.scott

Ah, apparently it seems that there is a limit of about 90MB for files when using atftpas your tftp server  :Sad: 

----------

## Raffi

That's good to know. I'm using tftp-hpa, I wonder if it has a similar limit or not.

----------

## Raffi

I have updated the mini howto with a patch for the current minimal live cd.

----------

## Raffi

Added another patch for latest minimal cd.

----------

## Raffi

Another update for the latest cds

----------

## Raffi

Added updated patch for latest minimal cds.

----------

## Raffi

Added patch and directions for latest minimal iso

----------

## solamour

I tried "install-amd64-minimal-20131010.iso" and received the following message.

```
# zcat /mnt/cdrom/isolinux/gentoo.igz | cpio -ivmd

gzip: /mnt/cdrom/isolinux/gentoo.igz: not in gzip format

cpio: premature end of archive
```

I guess it's because "gentoo.igz" is compressed with xz instead of gzip.

```
# file /mnt/cdrom/isolinux/gentoo.igz

/mnt/cdrom/isolinux/gentoo.igz: XZ compressed data

```

So I had to use "xzcat" instead of "zcat".

```
xzcat /mnt/cdrom/isolinux/gentoo.igz | cpio -ivmd
```

__

sol

----------

## solamour

Pardon me for resurrecting such an old topic. I noticed there is a script that makes all the necessary changes with a single command.

https://wiki.gentoo.org/wiki/Installation_alternatives#Diskless_install_using_PXE_and_kernel.2Finitrd.2Fsquashfs_from_the_LiveCD

But the patch is more than a year old and no longer applies cleanly to the latest minimal iso image. I'd very much appreciate if someone more knowledgeable takes a look at "init" file and lets everyone know what changes are necessary.

__

sol

----------

## Raffi

Last time I did this (a couple of weeks ago), I just made the changes by hand, but here's a patch from that changes

```

--- init.old   2020-06-10 11:37:47.050888808 -0700

+++ init   2020-06-10 11:38:43.594721612 -0700

@@ -664,6 +664,10 @@

    if [ "${got_good_root}" != '1' ] && [ /dev/nfs != "${REAL_ROOT}" ] && [ sgimips != "${LOOPTYPE}" ] && [ 1 != "${aufs}" ] && [ 1 != "${overlayfs}" ]

    then

       bootstrapCD

+   elif [ "${REAL_ROOT}" = '/' ]

+   then

+      got_good_root=1

+      cp /image.squashfs ${CDROOT_PATH} 

    fi

 

    if [ "${REAL_ROOT}" = '' ] && [ "${got_good_root}" != '1' ]

```

----------

## solamour

 *Raffi wrote:*   

> Last time I did this (a couple of weeks ago), I just made the changes by hand, but here's a patch from that changes
> 
> ```
> 
> --- init.old   2020-06-10 11:37:47.050888808 -0700
> ...

 

That did the trick. Thank you.

One thing I noticed is that as long as I have "loop=/image.squashfs" (i.e. use absolute path), I don't need to copy "image.squashfs". In other words,

```
[pxelinux.cfg/default]

label gentoo

    kernel gentoo/gentoo

    append initrd=gentoo/gentoo.igz root=/dev/ram0 init=/linuxrc loop=/image.squashfs looptype=squashfs cdroot=1 real_root=/

```

```
[init]

if [ "${got_good_root}" != '1' ] && [ /dev/nfs != "${REAL_ROOT}" ] && [ sgimips != "${LOOPTYPE}" ] && [ 1 != "${aufs}" ] && [ 1 != "${overlayfs}" ]

then

    bootstrapCD

elif [ "${REAL_ROOT}" = '/' ]

then

    got_good_root=1

fi 

```

__

solLast edited by solamour on Wed Jun 10, 2020 8:49 pm; edited 1 time in total

----------

## Raffi

Since my iso is not what I put on my tftp site and is not available anywhere else, there would be no image.squashfs if I didn't copy it into the ramdisk.

One of these days I need to revisit this and see if there is a better way, but for now, every year or so, I update my network book and as long as I works, I've not really spent much time with it.

----------

## solamour

As for me, the following step in the setup process must be the reason I could skip copying "image.squashfs" in init file.

```
# Copy in squashfs image

cp /mnt/loop/image.squashfs .
```

Anyhow, I wish there were a simpler way than manually updating it every so often, especially when the official documentation can get easily outdated.

__

sol

----------

