In case the root and /usr filesystems are of different types, or are on different types of device, we must add the modules needed for both. Signed-off-by: Ben Hutchings <ben@decadent.org.uk> --- I don't think we have an open bug report for this, but it's obvious we need to deal with it. It looks like a big patch but mostly it's renaming to generalise from root. Tested using a VM with MODULES=dep, root on virtio disk and /usr on an emulated PIIX PATA disk. Ben. hook-functions | 152 +++++++++++++++++++++++++++++++-------------------------- 1 file changed, 83 insertions(+), 69 deletions(-) diff --git a/hook-functions b/hook-functions index e71f0f8..4edbfde 100644 --- a/hook-functions +++ b/hook-functions @@ -256,53 +256,61 @@ add_loaded_modules() fi } -# find and only copy root relevant modules -dep_add_modules() +# find and only copy modules relevant to a mountpoint +dep_add_modules_mount() { - local block minor root FSTYPE root_dev_path + local dir block minor dev_node FSTYPE dev_sys_path local modules= + dir="$1" + # require mounted sysfs if [ ! -d /sys/devices/ ]; then echo "mkinitramfs: MODULES dep requires mounted sysfs on /sys" >&2 exit 1 fi - # findout root block device + fstype + # find out block device + fstype eval "$( mount | while read -r dev foo mp foo fs opts rest ; do \ - [ "$mp" = "/" ] && [ "$fs" != "rootfs" ] \ - && printf "root='%s'\nFSTYPE='%s'" "$dev" "$fs" \ + [ "$mp" = "$dir" ] && [ "$fs" != "rootfs" ] \ + && printf "dev_node='%s'\nFSTYPE='%s'" "$dev" "$fs" \ && break; done)" # On failure fallback to /proc/mounts if readable - if [ -z "$root" ] && [ -r /proc/mounts ]; then + if [ -z "$dev_node" ] && [ -r /proc/mounts ]; then eval "$(while read dev mp fs opts rest ; do \ - [ "$mp" = "/" ] && [ "$fs" != "rootfs" ] \ - && printf "root=$dev\nFSTYPE=$fs"\ + [ "$mp" = "$dir" ] && [ "$fs" != "rootfs" ] \ + && printf "dev_node=$dev\nFSTYPE=$fs"\ && break; done < /proc/mounts)" fi - # handle ubifs and return since ubifs root is a char device but - # most of the commands below only work with block devices. + # Only the root mountpoint has to exist; do nothing if any other + # directory is not a mountpoint. + if [ "$dir" != / ] && [ -z "$dev_node" ]; then + return + fi + + # handle ubifs and return since ubifs is mounted on char devices + # but most of the commands below only work with block devices. if [ "${FSTYPE}" = "ubifs" ]; then manual_add_modules "${FSTYPE}" return fi - if [ "${root}" = "/dev/root" ] ; then - if [ -b "${root}" ]; then + if [ "$dir" = / ] && [ "${dev_node}" = "/dev/root" ] ; then + if [ -b "${dev_node}" ]; then # Match it to the canonical device name by UUID - root="/dev/disk/by-uuid/"$(blkid -o value -s UUID ${root}) 2>/dev/null + dev_node="/dev/disk/by-uuid/"$(blkid -o value -s UUID ${dev_node}) 2>/dev/null else # Does not exist in our namespace, so look at the # kernel command line - root= + dev_node= for arg in $(cat /proc/cmdline); do case "$arg" in root=*) - root="${arg#root=}" - if [ "${root#/dev/}" = "$root" ]; then - root="/dev/$root" + dev_node="${arg#root=}" + if [ "${dev_node#/dev/}" = "$dev_node" ]; then + dev_node="/dev/$dev_node" fi ;; --) @@ -315,9 +323,10 @@ dep_add_modules() fi fi - # recheck root device - if [ -z "$root" ] || ! root="$(readlink -f ${root})" || ! [ -b "$root" ]; then - echo "mkinitramfs: failed to determine root device" >&2 + # recheck device + if [ -z "$dev_node" ] || ! dev_node="$(readlink -f ${dev_node})" \ + || ! [ -b "$dev_node" ]; then + echo "mkinitramfs: failed to determine device for $dir" >&2 echo "mkinitramfs: workaround is MODULES=most, check:" >&2 echo "grep -r MODULES /etc/initramfs-tools/" >&2 echo "" >&2 @@ -327,26 +336,26 @@ dep_add_modules() fi # do not trust mount, check superblock - eval "$(/usr/lib/klibc/bin/fstype ${root})" + eval "$(/usr/lib/klibc/bin/fstype ${dev_node})" - # check that fstype rootfs recognition + # check that fstype fs recognition if [ "${FSTYPE}" = "unknown" ]; then - FSTYPE=$(blkid -o value -s TYPE "${root}") + FSTYPE=$(blkid -o value -s TYPE "${dev_node}") if [ -z "${FSTYPE}" ]; then - echo "mkinitramfs: unknown fstype on root ${root}" >&2 + echo "mkinitramfs: unknown fstype on device ${dev_node}" >&2 echo "mkinitramfs: workaround is MODULES=most" >&2 echo "Error please report bug on initramfs-tools" >&2 exit 1 fi fi - # Add rootfs + # Add filesystem modules="$modules ${FSTYPE}" - # lvm or luks root - if [ "${root#/dev/mapper/}" != "${root}" ] \ - || [ "${root#/dev/dm-}" != "${root}" ]; then - minor=$((0x$(stat --format "%T" ${root}) % 256)) + # lvm or luks device + if [ "${dev_node#/dev/mapper/}" != "${dev_node}" ] \ + || [ "${dev_node#/dev/dm-}" != "${dev_node}" ]; then + minor=$((0x$(stat --format "%T" ${dev_node}) % 256)) block=$(ls -1 /sys/block/dm-${minor}/slaves | head -n 1) # lvm on luks or luks on lvm, possibly lvm snapshots while [ "${block#dm-}" != "${block}" ]; do @@ -363,85 +372,85 @@ dep_add_modules() else block=${block%%[0-9]*} fi - # md root new naming scheme /dev/md/X - elif [ "${root#/dev/md/}" != "${root}" ]; then - root=${root#/dev/md/} + # md device new naming scheme /dev/md/X + elif [ "${dev_node#/dev/md/}" != "${dev_node}" ]; then + dev_node=${dev_node#/dev/md/} # strip partion number - root=${root%%p[0-9]*} + dev_node=${dev_node%%p[0-9]*} # drop the partition number only for sdX and hdX devices # and keep it for other devices like loop#, dm-# devices - block=$(sed -ne 's/multipath/[/' -e 's/linear/[/' -e 's/raid[0-9][0-9]*/[/' -e 's/\([hs]d[a-z][a-z]*\)[0-9][0-9]*/\1/g' -e '/^md'$root' :/s/^[^[]*\[ \([^\[]*\)\[.*$/\1/p' </proc/mdstat) - # md root /dev/mdX - elif [ "${root#/dev/md}" != "${root}" ]; then - root=${root#/dev/md} + block=$(sed -ne 's/multipath/[/' -e 's/linear/[/' -e 's/raid[0-9][0-9]*/[/' -e 's/\([hs]d[a-z][a-z]*\)[0-9][0-9]*/\1/g' -e '/^md'$dev_node' :/s/^[^[]*\[ \([^\[]*\)\[.*$/\1/p' </proc/mdstat) + # md device /dev/mdX + elif [ "${dev_node#/dev/md}" != "${dev_node}" ]; then + dev_node=${dev_node#/dev/md} # strip partion number - root=${root%%p[0-9]*} + dev_node=${dev_node%%p[0-9]*} # drop the partition number only for sdX and hdX devices # and keep it for other devices like loop#, dm-# devices - block=$(sed -ne 's/multipath/[/' -e 's/linear/[/' -e 's/raid[0-9][0-9]*/[/' -e 's/\([hs]d[a-z][a-z]*\)[0-9][0-9]*/\1/g' -e '/^md'$root' :/s/^[^[]*\[ \([^\[]*\)\[.*$/\1/p' </proc/mdstat) + block=$(sed -ne 's/multipath/[/' -e 's/linear/[/' -e 's/raid[0-9][0-9]*/[/' -e 's/\([hs]d[a-z][a-z]*\)[0-9][0-9]*/\1/g' -e '/^md'$dev_node' :/s/^[^[]*\[ \([^\[]*\)\[.*$/\1/p' </proc/mdstat) # cciss device - elif [ "${root#/dev/cciss/}" != "${root}" ]; then - block=${root#/dev/cciss/*} + elif [ "${dev_node#/dev/cciss/}" != "${dev_node}" ]; then + block=${dev_node#/dev/cciss/*} block="cciss!${block%p*}" # ida device - elif [ "${root#/dev/ida/}" != "${root}" ]; then - block=${root#/dev/ida/*} + elif [ "${dev_node#/dev/ida/}" != "${dev_node}" ]; then + block=${dev_node#/dev/ida/*} block="ida!${block%p*}" - # loop root /dev/loopX - elif [ "${root#/dev/loop}" != "${root}" ]; then - root=${root#/dev/} + # loop device /dev/loopX + elif [ "${dev_node#/dev/loop}" != "${dev_node}" ]; then + dev_node=${dev_node#/dev/} block=$(losetup -a \ - | awk "/${root}/{print substr(\$3, 7, 3); exit}") + | awk "/${dev_node}/{print substr(\$3, 7, 3); exit}") # Xen virtual device /dev/xvdX - elif [ "${root#/dev/xvd}" != "${root}" ]; then - block=${root#/dev/} + elif [ "${dev_node#/dev/xvd}" != "${dev_node}" ]; then + block=${dev_node#/dev/} # Xen has a mode where only the individual partitions are # registered with the kernel as well as the usual full disk # with partition table scheme. if [ ! -e /sys/block/${block} ] ; then block=${block%%[0-9]*} fi - # mmc root /dev/mmcblkXpX - elif [ "${root#/dev/mmcblk}" != "${root}" ]; then - block=${root#/dev/} + # mmc device /dev/mmcblkXpX + elif [ "${dev_node#/dev/mmcblk}" != "${dev_node}" ]; then + block=${dev_node#/dev/} block=${block%%p[0-9]*} - # nbd root /dev/nbdXpX - elif [ "${root#/dev/nbd}" != "${root}" ]; then - block=${root#/dev/} + # nbd device /dev/nbdXpX + elif [ "${dev_node#/dev/nbd}" != "${dev_node}" ]; then + block=${dev_node#/dev/} block=${block%%p[0-9]*} - # DAC960 - good old mylex raid - root dev format /dev/rd/cXdXpX - elif [ "${root#/dev/rd/c}" != "${root}" ]; then - block="rd!c${root#/dev/rd/c}" + # DAC960 - good old mylex raid - device format /dev/rd/cXdXpX + elif [ "${dev_node#/dev/rd/c}" != "${dev_node}" ]; then + block="rd!c${dev_node#/dev/rd/c}" block=${block%%p[0-9]*} # etherd device - elif [ "${root#/dev/etherd/}" != "${root}" ]; then - block=${root#/dev/etherd/*} + elif [ "${dev_node#/dev/etherd/}" != "${dev_node}" ]; then + block=${dev_node#/dev/etherd/*} block="etherd!${block%p*}" # i2o raid device - elif [ "${root#/dev/i2o/}" != "${root}" ]; then - block=${root#/dev/i2o/} + elif [ "${dev_node#/dev/i2o/}" != "${dev_node}" ]; then + block=${dev_node#/dev/i2o/} block=${block%%[0-9]*} block='i2o!'$block - # classical root device + # classical block device else - block=${root#/dev/} + block=${dev_node#/dev/} block=${block%%[0-9]*} fi # Error out if /sys lack block dev if [ -z "${block}" ] || [ ! -e /sys/block/${block} ]; then - echo "mkinitramfs: for root ${root} missing ${block} /sys/block/ entry" >&2 + echo "mkinitramfs: for device ${dev_node} missing ${block} /sys/block/ entry" >&2 echo "mkinitramfs: workaround is MODULES=most" >&2 echo "mkinitramfs: Error please report the bug" >&2 exit 1 fi # sys walk ATA - root_dev_path=$(readlink -f /sys/block/${block}/device) - sys_walk_mod_add ${root_dev_path} + dev_sys_path=$(readlink -f /sys/block/${block}/device) + sys_walk_mod_add ${dev_sys_path} # sys walk some important device classes for class in gpio phy regulator; do @@ -459,7 +468,7 @@ dep_add_modules() # catch old-style IDE if [ -e /sys/bus/ide/devices/ ]; then - sys_walk_modalias ${root_dev_path} + sys_walk_modalias ${dev_sys_path} modules="$modules ide-gd_mod ide-cd" fi @@ -491,6 +500,11 @@ dep_add_modules() manual_add_modules $modules } +dep_add_modules() +{ + dep_add_modules_mount / + dep_add_modules_mount /usr +} # The modules "most" classes added per default to the initramfs auto_add_modules() -- Ben Hutchings The generation of random numbers is too important to be left to chance. - Robert Coveyou
Attachment:
signature.asc
Description: This is a digitally signed message part