1

I need to create an initramfs to load a driver to access EMMC which contains the root filesystem.

  • In my current kernel build, the EMMC driver is modular (sorry, can't change this).
  • After the kernel boots, it loads initramfs.
  • From initramfs, it needs to switch to a partition on the EMMC which contains the actual rootfs using the switch_root function.

Till here it is all works well. I can create initramfs, get the kernel to load it and then also get it to switch to /dev/mmcblk0p2 which is the EMMC partition containing the actual rootfs. My query:

After the booting is complete, mount command shows the following:

rootfs on / type rootfs (rw)
/dev/mmcblk0p2 on / type ext4 (rw,sync,noatime,data=ordered)
proc on /proc type proc (rw,relatime)
…
/dev/mmcblk0p1 on /var/volatile/run/media/mmcblk0p1 type vfat (rw,relatime,fmask=0022,dmask=0022,codepage=437,iocharset=iso8859-1,sh)
/dev/mmcblk0p3 on /var/volatile/run/media/mmcblk0p3 type ext4 (rw,relatime,data=ordered)
/dev/mmcblk0p4 on /var/volatile/run/media/mmcblk0p4 type ext4 (rw,relatime,data=ordered)

If I build the EMMC driver as a part of the kernel (and get rid of initramfs), the output is very different:

rootfs on / type rootfs (rw)
/dev/root on / type ext4 (rw,relatime,discard,journal_checksum,commit=1,data=ordered)
devtmpfs on /dev type devtmpfs (rw,relatime,size=112272k,nr_inodes=28068,mode=755)
…
/dev/mmcblk0p1 on /var/volatile/run/media/mmcblk0p1 type vfat (rw,relatime,fmask=0022,dmask=0022,codepage=437,iocharset=iso8859-1,sh)
/dev/mmcblk0p3 on /var/volatile/run/media/mmcblk0p3 type ext4 (rw,relatime,data=ordered)
/dev/mmcblk0p4 on /var/volatile/run/media/mmcblk0p4 type ext4 (rw,relatime,data=ordered)
  • Though when I checked kernel logs and major, minor device numbers I found that /dev/root corresponds to /dev/mmcblk0p2 only.
  • But I can not figure out why the output of mount is different.

After having spent so much effort in getting initramfs to work, I don't want to miss out on anything trivial. Any help, greatly appreciated.

The scripts which does this is given below:

#!/bin/sh

#Make busybox links
#/bin/busybox mkdir -p /usr/bin /sbin /bin
#BBINSTALL="/bin/busybox --install -s"
SWITCH="/bin/busybox switch_root"
INSERT="/sbin/insmod"
MOUNT="/bin/busybox mount"
UMOUNT="/bin/busybox umount"
DISKF="/bin/busybox df"
LSMOD="/bin/busybox lsmod"
LS="/bin/busybox ls"
CAT="/bin/busybox cat"
LS="/bin/busybox ls"
PRINTENV="/usr/bin/printenv"
SLEEP="/bin/busybox sleep"
PS="/bin/busybox ps"
MKDIR="/bin/busybox mkdir"
CAT="/bin/busybox cat"
GREP="/bin/busybox grep"
WC="/bin/busybox wc"

#mount proc and sysfs
$MOUNT -t proc none /proc
$MOUNT -t sysfs none /sys

#Mount NFS/EMMC - check
$CAT /proc/cmdline | $GREP -inr "/dev/nfs" | $WC -l > /var/NFSFOUND
ISNFSFOUND=$($CAT /var/NFSFOUND)

#Check if NFS was found in Kernel command line
if [ $ISNFSFOUND -ne 0 ]
then
    echo "Mounting NFS:"
    $MOUNT -a -t nfs -o rw,relatime,vers=2,rsize=8192,wsize=8192,namlen=255,hard,nolock,proto=udp,timeo=1,retrans=1,mountvers=1,addr=172.31.219.19 172.31.219.19:/home/user/Perforce/Mfg_Repo/ng5_mfg/b5/main/nfsroot /mnt/root/
else
#If NFS was not found, mount EMMC
    if [ ! -d /mnt/root ];  then
            $MKDIR /mnt/root
    fi
        echo "Mounting EMMC:"
    $MOUNT -t devtmpfs -o rw,relatime,mode=755 none /dev
    $SLEEP 1

    #Load EMMC driver
    echo "Inserting EMMC driver"
    $INSERT /lib/mmc_block.ko
    $INSERT /lib/omap.ko
    $INSERT /lib/omap_hsmmc.ko
    $SLEEP 1

    #Mount the mount point
    $MOUNT -a -t ext4 -o rw,relatime,discard,journal_checksum,commit=1,data=ordered  /dev/mmcblk0p2 /mnt/root/
fi

#Unmount the current mounts
echo "Unmounting initramfs:"
if [ $ISNFSFOUND -eq 0 ]
then
echo "Unmounting devtmpfs(EMMC):"
    $UMOUNT /dev
fi

#Switch to actual rootfs - This will be done by init program
  • Are you just trying to understand why the output is different, or does this cause a problem? Is your question about the device name, about the mount options, or both? How is the initramfs made: are you using a distribution's script, or did you make your own? If it's your own, you need to post all the relevant scripts from the initramfs. – Gilles May 19 '16 at 21:35
  • Hi Giles, Thanks for taking time out on this one. I am trying to find out why the output is different( device name and not mount options ). I want to know if this can cause any issue in my final product. I don't see a problem with the current output. I created this initramfs script on my own. The script is called from a C program( which compiles to init ). The call is system("./init.sh"); Later on I switch root from within the C program via call execl("/bin/busybox", "switch_root", "/mnt/root/", "/sbin/init", NULL); – manbir May 20 '16 at 13:40
  • /dev/root probably won't cause any problem (it could if you have code that parses the mount list and wants to know what kind of device the root filesystem is on, but that's unusual). The different mount options may cause problems however, e.g. the lack of TRIM. Please edit your question to post the actual scripts, not an unreadable modified version — use the {} button or press Ctrl+K to format code. – Gilles May 20 '16 at 13:55
  • Thanks Gilles. I updated the script( apologies, I didn't know how to earlier ). 1) I matched the mount options now. 2) Actually it is the opposite. /dev/root on / is what the kernel originally creates. If I use my initramfs, then the mount is /dev/mmcblkop2 on /. This was my concern. I checked the major, minor numbers under /dev in both cases i.e. /dev/root and /dev/mmcblkop2 and found they are the same. Maybe /dev/root is merely a symbolic link created by the kernel. Appreciate your response anyways. – manbir May 20 '16 at 18:57
  • Btw, what is TRIM? – manbir May 20 '16 at 18:58

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.