7 # based on mkinitrd from RedHat Linux
10 # - make udev start before insmods
11 # - make proper use of USE_UDEV - don't copy rules if USE_UDEV is off no!
15 R=${RCSID#* * }; VERSION=${R%% *}
18 . /etc/rc.d/init.d/functions
19 . /etc/geninitrd/functions
20 . /etc/sysconfig/system
28 # it should be safe to remove scsi_mod from here, but I'm not sure...
29 PRESCSIMODS="-scsi_mod unknown -sd_mod"
30 PREIDEMODS="-ide-core unknown -ide-detect -ide-disk"
31 PREIDEMODSOLD="-ide-probe -ide-probe-mod -ide-disk"
42 # device node for rootfs from fstab
44 # requires bootsplash package to operate
46 # requires splashutils package to operate
48 # requires splashutils package to operate
58 # is /tmp mounted on tmpfs
61 # are /dev nodes already created from /proc/devices info?
64 # LVM devices that should not be included in vgscan on initrd
67 # whether v86d should be installed
70 # LVM volumes that are needed to activate
73 # VG for suspend resume dev
76 # DM name for cryptsetup luks
82 # if we should init NFS at boot
84 # if we should init LVM at boot
86 # if we should init md (softraid) at boot
88 # if we should init dmraid at boot
90 # if we should init cryptsetup luks at boot
92 # if we should init dm-multipath at boot
94 # dm-multipath wwid which is used for rootfs
99 echo "usage: $PROGRAM [--version] [-v] [-f] [--ifneeded] [--preload <module>]"
100 echo " [--with=<module>] [--image-version] [--fstab=<fstab>] [--nocompress]"
101 echo " [--initrdfs=rom|initramfs|ext2|cram] [--modules-conf=<modules.conf>]"
102 echo " [--with-raidstart] [--without-raidstart] [--with-insmod-static]"
103 echo " [--with-bootsplash] [--without-bootsplash]"
104 echo " [--with-fbsplash] [--without-fbsplash]"
105 echo " [--with-fbcondecor] [--without-fbcondecor]"
106 echo " [--lvmtoolsversion=1|2] [--with-udev] [--without-udev]"
107 echo " [--with-suspend] [--without-suspend]"
108 echo " [--with-tuxonice] [--without-tuxonice]"
109 echo " [--without-dmraid] [--without-multipath]"
110 echo " [--without-blkid] [--without-luks]"
111 echo " <initrd-image> <kernel-version>"
114 echo " $PROGRAM -f --initrdfs=rom /boot/initrd-$uname_r.gz $uname_r"
123 msg "WARNING: $*" >&2
127 [ -n "$verbose" ] && msg "$*" >&2
130 # aborts program abnormally
137 # append text to /linuxrc
138 # takes STDIN as input
143 # generate code to mount /dev on tmpfs and create initial nodes
144 # can be called multiple times. /dev is cleaned up (umounted) automatically at
147 if [ "$INITRDFS" = "initramfs" ]; then
148 # initramfs is read-write filesystem, no need for tmpfs
152 # we already generated tmpfs code; return
153 if is_yes "$dev_mounted"; then
159 busybox_applet mount mknod mkdir
162 mount -o mode=0755 -t tmpfs none /dev
163 mknod /dev/console c 5 1
164 mknod /dev/null c 1 3
165 mknod /dev/zero c 1 5
171 # generate code to mount /proc on initrd
172 # can be called multiple times
174 if is_yes "$proc_mounted"; then
179 if [ "$INITRDFS" = "initramfs" ]; then
180 # /proc is mounted with initramfs 2.6.22.14 kernel
181 # XXX: remove when it is clear why proc was already mounted
182 echo "[ -f /proc/cmdline ] || mount -t proc none /proc" | add_linuxrc
184 echo "mount -t proc none /proc" | add_linuxrc
188 # generate code to mount /sys on initrd
189 # can be called multiple times
191 if is_yes "$sys_mounted"; then
196 echo "mount -t sysfs none /sys" | add_linuxrc
199 # generate code to mount /tmp on initrd
200 # can be called multiple times
202 if [ "$INITRDFS" = "initramfs" ]; then
203 # initramfs is read-write filesystem, no need for tmpfs
207 if is_yes "$tmp_mounted"; then
212 echo "mount -t tmpfs none /tmp" | add_linuxrc
215 # unmount all mountpoints mounted by geninitrd
219 : Last shell before umounting all and giving control over to real init.
223 if is_yes "$dev_mounted"; then
224 echo 'umount /dev' | add_linuxrc
227 if is_yes "$proc_mounted"; then
228 echo 'umount /proc' | add_linuxrc
231 if is_yes "$sys_mounted"; then
232 echo 'umount /sys' | add_linuxrc
235 if is_yes "$tmp_mounted"; then
236 echo 'umount /tmp' | add_linuxrc
242 # Checks if busybox has support for APPLET(s)
243 # Exits from geninitrd if the support is not present.
245 # NB! XXX do not output to STDOUT, it will appear in initrd images in some cases!
249 if [ -z "$busybox_functions" ]; then
250 local tmp=$(/bin/initrd-busybox 2>&1)
252 # BusyBox v1.1.3 says applet not found if it's not called 'busybox'.
253 if [[ "$tmp" = *applet\ not\ found* ]]; then
255 ln -s /bin/initrd-busybox $t/busybox
256 local tmp=$($t/busybox 2>&1)
260 busybox_functions=$(echo "$tmp" | \
261 sed -ne '/Currently defined functions:/,$p' | \
262 xargs | sed -e 's,.*Currently defined functions: ,,'
268 eval have='$'busybox_have_$applet
269 if [ -z "$have" ]; then
270 have=$(echo "$busybox_functions" | egrep -c "( |^)$applet(,|$)")
271 if [ "$have" = 0 ]; then
272 warn "This setup requires busybox-initrd compiled with applet '$applet' support"
275 eval busybox_have_$applet=$have
278 if [ $err = 1 ]; then
283 # Finds module dependencies
286 # @param $mode [silent]
288 # Outputs each dependant module full path including the module itself.
293 # backwards compatible, process $mode
295 if [ "$mode" = "silent" ]; then
296 modfile=$(modinfo -k $kernel -n $module 2>/dev/null)
298 modfile=$(modinfo -k $kernel -n $module)
300 if [ ! -f "$modfile" ]; then
301 # module not found. try aliases!
302 local alias aliases=$(modprobe_conf | awk -vm="$module" '$1 == "alias" && $2 == m { print $3 }')
303 if [ "$aliases" ]; then
304 for alias in $aliases; do
305 debug "Try $alias alias for $module"
311 if [ "$mode" != "silent" ]; then
312 warn "$module: module not found for $kernel kernel"
314 if ! is_no "$EXIT_IF_MISSING"; then
317 warn "If $module isn't compiled in kernel then this initrd may not start your system."
321 # This works when user has module-init-tools installed even on 2.4 kernels
322 modprobe --set-version $kernel --show-depends $module | \
323 while read insmod modpath options; do
330 echo -n $(modinfo -k $kernel -F firmware $module 2>/dev/null | xargs)
337 if [ ${modName#-} != $modName ]; then
343 if [ "$modName" = "pluto" ]; then
347 if [ "$modName" = "fcal" ]; then
353 if [ "$skiperrors" = 1 ]; then
354 depmod=$(find_depmod $modName silent)
356 depmod=$(find_depmod $modName)
362 for mod in $depmod; do
363 mod=${mod#/lib/modules/$kernel/}
365 # add each module only once
367 for m in $MODULES; do
368 [ $m = $mod ] && have=1
370 if [ $have = 0 ]; then
371 MODULES="$MODULES $mod"
373 # if we are adding uvesafb, we need v86d as well
374 if [ "$modName" = "uvesafb" ]; then
381 # install a file to temporary mount image.
382 # it will operate recursively (copying directories)
383 # and will symlink destinations if source is symlink.
385 if [ $# -lt 2 ]; then
386 die 'Usage: inst <file> [<file>] <destination>'
389 local src i=0 c=$(($# - 1))
390 while [ $i -lt $c ]; do
397 parentDir=$(dirname $DESTDIR$dest)
398 [ ! -d "$parentDir" ] && (debug "+ mkdir -p $parentDir"; mkdir -p $parentDir)
399 debug "+ cp $* $DESTDIR$dest"
400 cp -HR "$@" "$DESTDIR$dest"
405 die 'Usage: inst_d <destination> <destination>'
408 install -d "$DESTDIR$dir"
412 # install executable and it's shared libraries
414 if [ $# -lt 2 ]; then
415 die 'Usage: inst_exec <file>[, <file>] <destination>'
417 local src i=0 c=$(($# - 1))
418 while [ $i -lt $c ]; do
428 local lib libs=$(ldd "$@" | awk '/statically|linux-(gate|vdso)\.so/{next} NF == 2 {print $1} /=/{print $3}' | sort -u)
430 if [ ! -f "$DESTDIR/$_lib/${lib##*/}" ]; then
432 inst_exec $lib /$_lib
437 # output modules.conf / modprobe.conf
439 echo "$modprobe_conf_cache"
443 # defaults to modprobe -c if not told otherwise, this means include statements
445 cache_modprobe_conf() {
446 if [ "$pack_version" -lt "002005" ]; then
447 modulefile=/etc/modules.conf
448 if [ ! -f "$modulefile" -a -f /etc/conf.modules ]; then
449 modulefile=/etc/conf.modules
453 if [ -n "$modulefile" ]; then
454 debug "Using $modulefile for modules config"
455 modprobe_conf_cache=$(cat $modulefile)
457 debug "Using modprobe -c to get modules config"
458 modprobe_conf_cache=$(modprobe -c --set-version $kernel)
463 local found raidlevel
465 if [ -f /etc/mdadm.conf ]; then
466 debug "Finding RAID details using mdadm for rootdev=$1"
467 eval `/sbin/mdadm -v --examine --scan --config=/etc/mdadm.conf | awk -v rootdev="$1" '
472 rootdev_devfs = rootdev;
473 if (rootdev ~ /\/dev\/md\/[0-9]/) {
474 gsub(/\/dev\/md\//,"/dev/md",rootdev_devfs);
479 if (($2 == rootdev) || ($2 == rootdev_devfs)) {
481 gsub(/level=/,NUL,raidlevel);
482 if (raidlevel ~ /^raid([0-6]|10)/) {
483 gsub(/raid/,NUL,raidlevel);
487 if (x ~ /devices=/) {
489 gsub(".*devices=", NUL, dev_list);
490 gsub(",", " ", dev_list);
496 print "have_md=" found;
497 print "raidlevel=" raidlevel;
498 print "dev_list=\"" dev_list "\"";
502 if [ "$have_md" != "yes" -a -f /etc/raidtab ]; then
503 die "raidtools are not longer supported. Please migrate to mdadm setup!"
506 if is_yes "$have_md"; then
509 findmodule "raid$raidlevel"
512 findmodule "-raid$raidlevel"
513 findmodule "-raid456"
519 warn "raid level $number (in mdadm config) not recognized"
523 die "RAID devices not found for \"$1\", check your configuration!"
526 rootdev_nr=$(( $rootdev_nr + 1 ))
527 eval "rootdev${rootdev_nr}=\"$1\""
528 eval "dev_list${rootdev_nr}=\"${dev_list}\""
530 for device in $dev_list; do
531 find_modules_for_devpath $device
535 find_modules_scsi() {
537 for n in $PRESCSIMODS; do
538 if [ "X$n" = "Xunknown" ]; then
539 debug "Finding SCSI modules using scsi_hostadapter"
540 local mod scsimodules=$(modprobe_conf | awk '/scsi_hostadapter/ && ! /^[\t ]*#/ { print $3; }')
541 for mod in $scsimodules; do
542 # for now allow scsi modules to come from anywhere. There are some
543 # RAID controllers with drivers in block
550 findmodule "-scsi_wait_scan"
555 # remove partition, if any
556 local disk=${devpath%[0-9]*}
557 # set blockdev for rootfs (hda, sdc, ...)
558 local rootblkdev=${disk#/dev/}
561 if [ "$pack_version_long" -lt "002004021" ]; then
562 debug "Finding IDE modules for kernels <= 2.4.20"
563 for n in $PREIDEMODSOLD; do
568 for n in $PREIDEMODS; do
569 if [ "X$n" = "Xunknown" ]; then
570 debug "Finding IDE modules using ide_hostadapter"
571 local mod idemodules=$(modprobe_conf | awk '/ide_hostadapter/ && ! /^[\t ]*#/ { print $3; }')
572 for mod in $idemodules; do
577 if [ "$tryauto" -eq 1 ]; then
579 if [ -r /usr/share/pci-database/ide.pci -a -r /proc/bus/pci/devices ]; then
580 debug "Finding IDE modules using PCI ID database"
581 # Finding IDE modules using PCI ID database {{{
582 if is_yes "${ide_only_root}"; then
583 if [ -f /sys/block/${rootblkdev}/device/../../vendor -a -f /sys/block/${rootblkdev}/device/../../device ]; then
584 vendorid="$(awk ' { gsub(/0x/,NUL); print $0 } ' /sys/block/${rootblkdev}/device/../../vendor)"
585 deviceid="$(awk ' { gsub(/0x/,NUL); print $0 } ' /sys/block/${rootblkdev}/device/../../device)"
586 searchpciid="${vendorid}${deviceid}"
587 elif [ -f /proc/ide/${rootblkdev}/../config ]; then
588 searchpciid="$(awk ' /pci bus/ { print $7$9 } ' /proc/ide/${rootblkdev}/../config)"
592 if [ -z "${searchpciid}" ]; then
593 searchpciid="$(awk ' { print $2 } ' /proc/bus/pci/devices)"
598 for nb in $searchpciid; do
599 eval `awk -v pciid="$nb" '{
605 compmod = $1 ""; # make sure comparison type will be string
606 # cause pci IDs are hexadecimal numeric
607 if (compmod == pciid) {
609 # min_kernel=$3; # now in ide.pci $3,$4 = vendor and device name
616 print "module=" module "\nmin_kernel=" min_kernel "\nmax_kernel=\"" max_kernel "\"\n";
617 }' /usr/share/pci-database/ide.pci`
618 [ -n "$module" ] && idemodules="$idemodules $module"
620 if is_yes "$(awk ' /ide=reverse/ { print "yes" } ' /proc/cmdline)"; then
622 for nc in idemodules; do
623 new_idemodules="$nc $new_idemodules"
625 idemodules="${new_idemodules}"
628 if [ -z "$idemodules" ]; then
629 warn "rootfs on IDE device but no related modules found, loading ide-generic."
630 idemodules="ide-generic"
634 for nd in $idemodules; do
640 [ -r /usr/share/pci-database/ide.pci ] || warn "/usr/share/pci-database/ide.pci missing."
641 [ -r /proc/bus/pci/devices ] || warn "/proc/bus/pci/devices missing."
642 warn "Automatic IDE modules finding not available."
653 # return true if node is lvm node
656 if [ ! -e "$node" ]; then
657 warn "check_lvm(): node $node doesn't exist!"
661 # block-major-58 is lvm1
662 ls -lL "$node" 2> /dev/null | awk '{if (/^b/) { if ($5 == "58,") { exit 0; } else { exit 1; } } else { exit 1; }}'
666 debug "LVM check: $node is LVM v1 node"
671 if [ ! -x /sbin/lvm ]; then
672 debug "LVM check: no lvm2 tools present to check"
676 /sbin/lvm lvdisplay "$node" > /dev/null 2>&1
678 if [ $rc -gt 127 ]; then
679 # lvdisplay terminated by signal! most likely it segfaulted.
680 die "Unexpected exit from 'lvdisplay $node': $rc - are your lvm tools broken?"
684 debug "LVM check: $node is LVM v2 node"
686 debug "LVM check: $node is not any LVM node"
691 # return true if node is cryptsetup luks encrypted
694 if [ ! -e "$node" ]; then
695 warn "is_luks(): node $node doesn't exist!"
699 local dev dm_name=${node#/dev/mapper/}
700 if [ "$node" = "$dm_name" ]; then
701 debug "is_luks: $node is not device mapper name"
705 dev=$(cryptsetup status $dm_name 2>/dev/null | awk '/device:/{print $2}')
706 cryptsetup isLuks $dev
710 debug "is_luks: $node is cryptsetup luks"
712 debug "is_luks: $node is not cryptsetup luks"
717 # return dependencies MAJOR:MINOR [MAJOR:MINOR] for DM_NAME
718 # TODO: patch `dmsetup export`
721 dmsetup deps $dm_name | sed -e 's/, /:/g;s/^.\+ dependencies[^:]: //;s/[()]//g;'
724 # export info from dmsetup
728 # - /dev/mapper/DM_NAME
734 local maj=${arg%:*} min=${arg#*:}
735 dmsetup -j $maj -m $min export
738 local min=${arg#*dm-}
739 local maj=$(awk '$2 == "device-mapper" {print $1}' /proc/devices)
743 local dm_name=${arg#/dev/mapper/}
744 dmsetup export $dm_name
747 die "dm_export: unexpected $arg"
752 # find dm-multipath modules for $devpath
753 # returns false if $devpath is not dm-multipath
754 find_modules_multipath() {
758 eval $(dm_export "$devpath")
759 if [ -z "$DM_NAME" ]; then
760 die "dm_export failed unexpectedly"
765 # DM_UUID=part1-mpath-36006016002c11800a0aa05fbfae0db11
768 # DM_UUID=mpath-36006016002c11800a0aa05fbfae0db11
769 MPATH_WWID=${DM_UUID##*-}
771 local info=$(multipath -l $MPATH_WWID)
772 if [ -z "$info" ]; then
776 debug "Finding modules for dm-multipath (WWID=$MPATH_WWID)"
778 local dev phydevs=$(echo "$info" | awk '$2 ~ /^[0-9]+:[0-9]+:[0-9]+:[0-9]+$/{printf("/dev/%s\n", $3)}')
779 for dev in $phydevs; do
780 find_modules_for_devpath $dev
781 lvm_ignore_devices="$lvm_ignore_devices $dev"
784 local hw hwhandlers=$(echo "$info" | awk '/hwhandler=1/{sub(/.*hwhandler=1 /, ""); sub(/\]$/, ""); print}')
785 for hw in $hwhandlers; do
789 local target targets=$(echo "$info" | awk '/prio=/{print $2}' | sort -u)
790 for target in $targets; do
791 findmodule "dm-$target"
798 # find dmraid modules for $devpath
799 # returns false if $devpath is not on dmraid
800 find_modules_dmraid() {
803 # get blockdev itself (without partition)
804 # /dev/mapper/sil_ahbgadcbchfc3 -> /dev/mapper/sil_ahbgadcbchfc
805 local blockdev=${devpath%%[0-9]*}
806 local raidname=${blockdev#/dev/mapper/}
809 local dev phydevs=$(dmraid -r -cdevpath,raidname | awk -F, -vv="$raidname" '{if ($2 == v) print $1}')
810 for dev in $phydevs; do
811 find_modules_for_devpath $dev
812 lvm_ignore_devices="$lvm_ignore_devices $dev"
816 if [ $found = 0 ]; then
820 findmodule "dm-mirror"
825 # find modules for $devpath
826 find_modules_luks() {
830 LUKSNAME=${devpath#/dev/mapper/}
831 LUKSDEV=$(cryptsetup status $LUKSNAME 2>/dev/null | awk '/device:/{print $2}')
832 if [ -z "$LUKSDEV" ]; then
833 die "Lost cryptsetup device meanwhile?"
836 findmodule "dm-crypt"
845 find_modules_for_devpath $LUKSDEV
849 # find modules for $devpath
850 find_modules_for_devpath() {
852 if [ -z "$devpath" ]; then
853 die "No argument passed to find_modules_for_devpath() - is your /etc/fstab correct?"
856 # /dev/dm-3 -> /dev/mapper/sil_ahbgadcbchfc3
859 devpath=$(dm_longname "$devpath")
862 debug "Finding modules for device path $devpath"
864 if is_luks "$devpath"; then
865 find_modules_luks "$devpath"
869 if is_yes "`echo "$devpath" | awk '/^([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+:|\/dev\/nfs)/ { print "yes"; }'`"; then
870 if [ ! -x /usr/bin/pcidev -a -z "$NFS_ETH_MODULES" ]; then
871 die "root on NFS but /usr/bin/pcidev not found. Please install correct pci-database package and rerun $PROGRAM."
873 if [ ! -f /proc/bus/pci/devices ]; then
874 warn "Remember to add network card modules in /etc/sysconfig/geninitrd, example:"
875 warn "BASICMODULES=\"e1000 ne2k-pci mii 8139too 3c59x\""
878 [ -z "$NFS_ETH_MODULES" ] && NFS_ETH_MODULES=$(/usr/bin/pcidev /m net | xargs)
879 warn "NOTE: Network card(s) module(s) $NFS_ETH_MODULES is for this machine"
880 for m in $NFS_ETH_MODULES; do
887 warn "Remember to use \`root=/dev/ram0 init=/linuxrc' when starting kernel"
888 warn "or you will have problems like init(xx) being child process of swapper(1)."
892 if [[ "$devpath" == /dev/md* ]]; then
893 find_modules_md "$devpath"
897 if is_yes "$USE_MULTIPATH" && [[ "$devpath" == /dev/mapper/* ]]; then
898 if find_modules_multipath "$devpath"; then
904 if is_yes "$USE_DMRAID" && is_yes "$(echo "$devpath" | awk '/^\/dev\/mapper\/(sil|hpt37x|hpt45x|isw|lsi|nvidia|pdc|sil|via|dos)_/ { print "yes"; }')"; then
905 if find_modules_dmraid "$devpath"; then
911 if is_yes "$(echo "$devpath" | awk '/^\/dev\/(sd|scsi)/ { print "yes"; }')"; then
916 if is_yes "$(echo "$devpath" | awk '/^\/dev\/(hd|ide)/ { print "yes"; }')"; then
917 find_modules_ide "$devpath"
921 if [[ "$devpath" == /dev/rd/* ]]; then
923 rootdev_add="/dev/rd/"
927 if [[ "$devpath" == /dev/ida/* ]]; then
928 findmodule "cpqarray"
929 rootdev_add="/dev/ida/"
933 if [[ "$devpath" == /dev/cciss/* ]]; then
935 rootdev_add="/dev/cciss/"
939 if [[ "$devpath" == /dev/ataraid/* ]]; then
942 ataraidmodules=$(modprobe_conf | awk '/ataraid_hostadapter/ && ! /^[\t ]*#/ { print $3; }')
943 if [ -n "$ataraidmodules" ]; then
944 # FIXME: think about modules compiled in kernel
945 die "ataraid_hostadapter alias not defined in modprobe.conf! Please set it and run $PROGRAM again."
947 for n in $ataraidmodules; do
950 rootdev_add="/dev/ataraid/"
954 # check to see if we need to set up a loopback filesystem
955 if [[ "$devpath" == /dev/loop* ]]; then
956 die "Sorry, root on loop device isn't supported."
957 # TODO: rewrite for bsp and make nfs ready
958 if [ ! -x /sbin/losetup ]; then
959 die "losetup is missing"
961 key="^# $(echo $devpath | awk -F/ '{print($3);}' | tr '[a-z]' '[A-Z]'):"
962 if ! is_yes "`awk '/'$key'/ { print( "yes"); }' $fstab`"; then
963 die "The root filesystem is on a $devpath, but there is no magic entry in $fstab for this device. Consult the $PROGRAM man page for more information"
966 line="`awk '/'$key'/ { print $0; }' $fstab`"
967 loopDev="$(echo $line | awk '{print $3}')"
968 loopFs="$(echo $line | awk '{print $4}')"
969 loopFile="$(echo $line | awk '{print $5}')"
971 BASICMODULES="$BASICMODULES -loop"
972 findmodule "-$loopFs"
973 BASICMODULES="$BASICMODULES -${loopFs}"
977 if is_lvm_node "$devpath"; then
980 if [ ! -f /sbin/initrd-lvm -o ! -x /sbin/lvdisplay -o ! -x /sbin/pvdisplay ]; then
981 die "root on LVM but /sbin/initrd-lvm, /sbin/lvdisplay and /sbin/pvdisplay not found. Please install lvm(2) and lvm(2)-initrd package and rerun $PROGRAM."
983 if [ -z "$LVMTOOLSVERSION" ]; then
984 LVMTOOLSVERSION=$(/sbin/initrd-lvm vgchange --version 2>/dev/null|head -n 1|awk '{gsub("vgchange: Logical Volume Manager ",NIL); gsub("LVM version: ",NIL); gsub(/\..*/,NIL); print $1}')
985 if [ -z "$LVMTOOLSVERSION" ]; then
986 die "Can't determine LVM tools version. Please set LVMTOOLSVERSION and rerun $PROGRAM."
990 local vg=$(/sbin/lvdisplay -c "$node" 2> /dev/null | awk -F":" ' { print $2 } ')
991 VGVOLUMES=$(echo $VGVOLUMES $vg | tr ' ' '\n' | sort -u)
992 local pv=$(/sbin/pvdisplay -c 2>/dev/null | awk -F":" -v vg="$vg" ' BEGIN { devices="" } { if ($2 == vg) { devices = devices " " $1 } } END { print devices } ')
993 PVDEVICES=$(echo $PVDEVICES $pv | tr ' ' '\n' | sort -u)
995 if [ -n "$PVDEVICES" ]; then
996 for device in $PVDEVICES; do
997 find_modules_for_devpath $device
1000 die "I wasn't able to find PV (via lvdisplay and pvdisplay). You can try to set PVDEVICES in /etc/sysconfig/geninitrd."
1002 if [ "$LVMTOOLSVERSION" = "2" ]; then
1003 findmodule "-dm-mod"
1004 elif [ "$LVMTOOLSVERSION" = "1" ]; then
1006 findmodule "-lvm-mod"
1008 die "LVM version $LVMTOOLSVERSION is not supported yet."
1010 debug "LVM v$LVMTOOLSVERSION enabled"
1016 firmware_install_module() {
1018 local firmware_files="$2"
1020 debug "Adding Firmwares ($firmware_files) to initrd for module $module"
1021 # firmware not yet installed
1022 if [ ! -f "$DESTDIR/lib/firmware/firmware.sh" ]; then
1023 inst_d /lib/firmware
1024 cat << 'EOF' >> "$DESTDIR/lib/firmware/firmware.sh"
1026 echo 1 > /sys$DEVPATH/loading
1027 cat "/lib/firmware/$FIRMWARE" > /sys$DEVPATH/data
1028 echo 0 > /sys$DEVPATH/loading
1031 chmod 755 "$DESTDIR/lib/firmware/firmware.sh"
1034 for firmware in $firmware_files; do
1035 if [ ! -f "/lib/firmware/$firmware" ]; then
1036 die "firmware file /lib/firmware/$firmware doesn't exist."
1038 FIRMWAREDIR=${firmware%/*}
1039 [ "$FIRMWAREDIR" != "$firmware" ] && inst_d /lib/firmware/$FIRMWAREDIR
1040 inst /lib/firmware/$firmware /lib/firmware/$firmware
1045 echo "echo -n "/lib/firmware/firmware.sh" > /proc/sys/kernel/hotplug" | add_linuxrc
1052 for mod in $modules; do
1054 inst_d "/lib/modules/$kernel/$MODULEDIR"
1055 cp -a "/lib/modules/$kernel/$mod" "$DESTDIR/lib/modules/$kernel/$mod"
1056 gunzip "$DESTDIR/lib/modules/$kernel/$mod" 2> /dev/null
1060 modules_add_linuxrc() {
1064 # module path without optional compression
1067 # name of the module
1068 module=${modpath##*/}
1069 module=${module%$modext}
1071 options=$(modprobe_conf | awk -vmodule="$module" '{ if ($1 == "options" && $2 == module) { for(i=3;i<=NF;i++) printf("%s ",$i); }}' | xargs)
1073 generic_module=$(echo $module | tr - _)
1074 sleep_var=$(eval echo \$MODULE_${generic_module}_USLEEP)
1075 firmware_var=$(eval echo \$MODULE_${generic_module}_FIRMWARE)
1077 if [ -n "$verbose" ]; then
1079 if [ "$options" ]; then
1080 s="$s with options [$options]"
1082 if [ "$sleep_var" ]; then
1083 s="$s and $sleep_var usleep"
1085 debug "Loading module [$module]$s"
1088 if [ -n "$firmware_var" ]; then
1089 firmware_install_module "$module" "$firmware_var"
1091 firmware_files=$(find_firmware "$module")
1092 if [ -n "$firmware_files" ]; then
1093 for file in $firmware_files; do
1094 firmware_install_module "$module" "$file"
1099 echo "$insmod /lib/modules/$kernel/$modpath $options" | add_linuxrc
1100 if [ -n "$sleep_var" ]; then
1101 echo "usleep $sleep_var" | add_linuxrc
1106 find_modules_suspend() {
1107 if [ ! -x /usr/${_lib}/suspend/resume -a ! -x /usr/sbin/resume ]; then
1108 die "/usr/${_lib}/suspend/resume is missing!"
1110 resume_dev="$(awk '/^resume device =/ { print $4 } ' /etc/suspend.conf)"
1112 local vgvolumes=$VGVOLUMES
1113 find_modules_for_devpath $resume_dev
1115 if [ "$VGVOLUMES" != "$vgvolumes" ]; then
1116 # save our VG to be able to differenciate between rootfs VG
1117 SUSPENDVG=$VGVOLUMES
1118 VGVOLUMES=$vgvolumes
1119 debug "suspend device is on LVM"
1123 initrd_gen_suspend() {
1124 mknod $DESTDIR/dev/snapshot c 10 231
1125 mkdir -p $DESTDIR${resume_dev%/*}
1126 inst $resume_dev $resume_dev
1128 inst /etc/suspend.conf /etc/suspend.conf
1129 if [ -x /usr/${_lib}/suspend/resume ]; then
1130 inst_exec /usr/${_lib}/suspend/resume /bin/resume
1132 inst_exec /usr/sbin/resume /bin/resume
1135 add_linuxrc <<-'EOF'
1137 for arg in $CMDLINE; do
1138 if [ "${arg##resume=}" != "${arg}" ]; then
1142 if [ "$resume" = "yes" ]; then
1148 initrd_gen_tuxonice() {
1150 add_linuxrc <<-'EOF'
1152 for arg in $CMDLINE; do
1153 if [ "${arg##resume=}" != "${arg}" -o "${arg##resume2=}" != "${arg}" ]; then
1157 if [ "$resume" = "yes" ]; then
1158 [ -e /proc/suspend2/do_resume ] && echo > /proc/suspend2/do_resume
1159 [ -e /sys/power/suspend2/do_resume ] && echo > /sys/power/suspend2/do_resume
1160 [ -e /sys/power/tuxonice/do_resume ] && echo > /sys/power/tuxonice/do_resume
1166 debug "initrd_gen_v86d"
1167 mknod $DESTDIR/dev/mem c 1 1
1168 mknod $DESTDIR/dev/tty1 c 4 1
1170 inst_exec /sbin/v86d /sbin
1174 debug "Setting up udev..."
1175 inst_d /sbin /etc/udev
1177 if [ ! -x /sbin/initrd-udevd ]; then
1178 die "/sbin/initrd-udevd not present"
1181 inst_exec /sbin/initrd-udevd /sbin/udevd
1182 inst /etc/udev/udev.conf /etc/udev/udev.conf
1186 add_linuxrc <<-'EOF'
1188 /sbin/udevd --daemon
1191 inst_exec /sbin/initrd-udevadm /sbin/udevadm
1192 ln -s udevadm $DESTDIR/sbin/udevsettle
1193 ln -s udevadm $DESTDIR/sbin/udevtrigger
1194 add_linuxrc <<-'EOF'
1199 busybox_applet killall
1200 add_linuxrc <<-'EOF'
1205 initrd_gen_multipath() {
1206 inst_d /sbin /lib/udev /etc/multipath
1207 inst_exec /sbin/kpartx /sbin
1208 inst_exec /sbin/multipath /sbin
1210 inst_exec /sbin/scsi_id /lib/udev
1211 inst_exec /sbin/mpath* /sbin
1212 egrep -v '^([ ]*$|#)' /etc/multipath.conf > $DESTDIR/etc/multipath.conf
1214 if [ -f /etc/multipath/bindings ]; then
1215 egrep -v '^([ ]*$|#)' /etc/multipath/bindings > $DESTDIR/etc/multipath/bindings
1217 touch $DESTDIR/etc/multipath/bindings
1224 echo "export MPATH_WWID=$MPATH_WWID" | add_linuxrc
1225 add_linuxrc <<-'EOF'
1226 # parse mpath_wwid= from kernel commandline
1227 for arg in $CMDLINE; do
1228 if [ "${arg##mpath_wwid=}" != "${arg}" ]; then
1229 MPATH_WWID=${arg##mpath_wwid=}
1230 if [ "$MPATH_WWID" = "*" ]; then
1231 # '*' would mean activate all WWID-s
1233 echo "multipath: Activating all WWID-s"
1235 echo "multipath: Activating WWID=$WWID"
1241 /sbin/multipath -v 0 $MPATH_WWID
1243 for a in /dev/mapper/*; do
1244 [ $a = /dev/mapper/control ] && continue
1245 /sbin/kpartx -a -p p $a
1251 initrd_gen_dmraid() {
1252 if [ ! -x /sbin/dmraid-initrd ]; then
1253 die "/sbin/dmraid-initrd is missing!"
1257 inst_exec /sbin/dmraid-initrd /sbin/dmraid
1263 # 2 secs was enough for my system to initialize. but really this is udev issue?
1265 : 'Activating Device-Mapper RAID(s)'
1273 [ "$1" = "/dev/urandom" -o "$1" = "/dev/hw_random" -o "$1" = "/dev/random" ]
1276 # produce cryptsetup from $name from /etc/crypttab
1281 # copy from /etc/rc.d/init.d/cryptsetup
1282 local dst src key opt mode owner
1284 while read dst src key opt; do
1285 [ -z "$dst" -o "${dst#\#}" != "$dst" ] && continue
1286 [ "$src" != "$LUKSDEV" ] && continue
1288 if [ -n "$key" -a "x$key" != "xnone" ]; then
1289 if test -e "$key" ; then
1290 mode=$(LC_ALL=C ls -l "$key" | cut -c 5-10)
1291 owner=$(LC_ALL=C ls -l $key | awk '{ print $3 }')
1292 if [ "$mode" != "------" ] && ! key_is_random "$key"; then
1293 die "INSECURE MODE FOR $key"
1295 if [ "$owner" != root ]; then
1296 die "INSECURE OWNER FOR $key"
1299 die "Key file for $dst not found"
1305 if /sbin/cryptsetup isLuks "$src" 2>/dev/null; then
1306 if key_is_random "$key"; then
1307 die "$dst: LUKS requires non-random key, skipping"
1309 if [ -n "$opt" ]; then
1310 warn "$dst: options are invalid for LUKS partitions, ignoring them"
1313 keyfile=/etc/luks-$LUKSNAME.key
1317 debug "+ cryptsetup ${keyfile:+-d $keyfile} luksOpen '$src' '$dst'"
1319 cryptsetup ${keyfile:+-d $keyfile} luksOpen '$src' '$dst' <&1
1324 die "$dst: only LUKS encryption supported"
1326 done < /etc/crypttab
1330 if [ ! -x /sbin/cryptsetup-initrd ]; then
1331 die "/sbin/cryptsetup-initrd is missing!"
1335 inst_exec /sbin/cryptsetup-initrd /bin/cryptsetup
1341 debug "luks: process /etc/crypttab $LUKSNAME $LUKSDEV"
1342 luks_crypttab $LUKSNAME $LUKSDEV
1345 initrd_gen_bootsplash() {
1348 debug "Generating bootsplash"
1350 if [ ! -x /bin/splash.bin ]; then
1351 warn "Failed to execute /bin/splash.bin. Is bootsplash package installed?"
1355 if [ -r /etc/sysconfig/bootsplash ]; then
1356 . /etc/sysconfig/bootsplash
1359 if [ -z "$THEME" ]; then
1360 warn "Please configure your /etc/sysconfig/bootsplash first."
1361 warn "Generating bootsplashes skipped."
1365 if [ -z "$BOOT_SPLASH_RESOLUTIONS" ]; then
1366 warn "No BOOT_SPLASH_RESOLUTIONS specified in /etc/sysconfig/bootsplash."
1367 warn "Not adding bootsplash to initrd."
1370 for res in $BOOT_SPLASH_RESOLUTIONS; do
1371 if [ -f "/etc/bootsplash/themes/$THEME/config/bootsplash-$res.cfg" ]; then
1372 /bin/splash.bin -s -f "/etc/bootsplash/themes/$THEME/config/bootsplash-$res.cfg" >> "$target" && \
1373 debug "Added $res $THEME theme to initrd."
1375 warn "/etc/bootsplash/themes/$THEME/config/bootsplash-$res.cfg doesn't exist, skipped"
1380 initrd_gen_fbsplash() {
1381 debug "Generating fbsplash"
1383 if [ ! -x /usr/bin/splash_geninitramfs -a ! -x /usr/sbin/splash_geninitramfs ]; then
1384 warn "Failed to find splash_geninitramfs. Is splashutils package installed?"
1387 splash_geninitramfs_bin=/usr/sbin/splash_geninitramfs
1388 [ -f /usr/bin/splash_geninitramfs ] && splash_geninitramfs_bin=/usr/bin/splash_geninitramfs
1390 if [ -r /etc/sysconfig/fbsplash ]; then
1391 . /etc/sysconfig/fbsplash
1394 if [ -z "$SPLASH_THEME" ]; then
1395 warn "Please configure your /etc/sysconfig/fbsplash first."
1396 warn "Generating fbsplashes skipped."
1400 if [ -z "$FB_SPLASH_RESOLUTIONS" ]; then
1401 warn "No FB_SPLASH_RESOLUTIONS specified in /etc/sysconfig/fbsplash."
1402 warn "Not adding fbsplash to initramfs."
1406 for res in $FB_SPLASH_RESOLUTIONS; do
1407 if [ -f "/etc/splash/$SPLASH_THEME/$res.cfg" ]; then
1408 $splash_geninitramfs_bin -c $DESTDIR -r $res $SPLASH_THEME && \
1409 debug "Added $res $SPLASH_THEME theme to initramfs."
1411 warn "/etc/splash/$SPLASH_THEME/$res.cfg doesn't exist, skipped"
1416 initrd_gen_fbcondecor() {
1417 debug "Generating fbcondecor"
1419 if [ ! -x /usr/bin/splash_geninitramfs -a ! -x /usr/sbin/splash_geninitramfs ]; then
1420 warn "Failed to find splash_geninitramfs. Is splashutils package installed?"
1423 splash_geninitramfs_bin=/usr/sbin/splash_geninitramfs
1424 [ -f /usr/bin/splash_geninitramfs ] && splash_geninitramfs_bin=/usr/bin/splash_geninitramfs
1426 if [ -r /etc/sysconfig/splash ]; then
1427 . /etc/sysconfig/splash
1430 if [ -z "$SPLASH_THEME" ]; then
1431 warn "Please configure your /etc/sysconfig/splash first."
1432 warn "Generating of splashes skipped."
1436 if [ -z "$FB_SPLASH_RESOLUTIONS" ]; then
1437 warn "No FB_SPLASH_RESOLUTIONS specified in /etc/sysconfig/splash."
1438 warn "Not adding fbcondecor to initramfs."
1442 for res in $FB_SPLASH_RESOLUTIONS; do
1443 if [ -f "/etc/splash/$SPLASH_THEME/$res.cfg" ]; then
1444 $splash_geninitramfs_bin -c $DESTDIR -r $res $SPLASH_THEME && \
1445 debug "Added $res $SPLASH_THEME theme to initramfs."
1447 warn "/etc/splash/$SPLASH_THEME/$res.cfg doesn't exist, skipped"
1452 # Generates /dev nodes based on /proc/partitions information.
1453 # Needs /proc mounted.
1454 # Can be called multiple times.
1455 initrd_gen_devices() {
1456 if is_yes "$proc_partitions"; then
1462 add_linuxrc <<-'EOF'
1463 : 'Making device nodes'
1464 cat /proc/partitions | (
1465 # ignore first two lines: header, empty line
1468 while read major minor blocks dev rest; do
1471 [ -e $node ] || mknod $node b $major $minor
1478 debug "Setting up mdadm..."
1480 if [ ! -x /sbin/mdadm -o ! -x /sbin/initrd-mdassemble ]; then
1481 die "/sbin/mdadm or /sbin/initrd-mdassemble is missing!"
1484 inst_exec /sbin/initrd-mdassemble /bin/mdassemble
1487 dev_list_extra=$(awk '/^DEVICE / { for (i=2; i<=NF; i++) { printf "%s ", $i; }; } ' /etc/mdadm.conf | xargs)
1488 if [ "$dev_list_extra" = "partitions" ]; then
1489 # FIXME: handle this case (see man mdadm.conf)
1490 echo "DEVICE partitions" >> "$DESTDIR/etc/mdadm.conf"
1493 for ex_dev in $dev_list_extra; do
1494 echo "DEVICE $ex_dev" >> "$DESTDIR/etc/mdadm.conf"
1498 for nr in `seq 1 $rootdev_nr`; do
1499 eval cr_rootdev="\$rootdev${nr}"
1500 eval cr_dev_list="\$dev_list${nr}"
1501 debug echo "Setting up array ($cr_rootdev = $cr_dev_list)"
1503 [ "$cr_rootdev" = "/dev/md0" ] && do_md0=0
1505 echo "DEVICE $cr_dev_list" >> "$DESTDIR/etc/mdadm.conf"
1506 cr_dev_list_md="$(echo "$cr_dev_list" | xargs | awk ' { gsub(/ +/,",",$0); print $0; }')"
1507 cr_md_conf=$(/sbin/mdadm --detail --brief --config=/etc/mdadm.conf $cr_rootdev | awk ' { gsub(/spares=[0-9]+/, "", $0); print $0; }')
1508 if [ -n "$cr_md_conf" ]; then
1509 echo "$cr_md_conf" >> "$DESTDIR/etc/mdadm.conf"
1511 echo "ARRAY $cr_rootdev devices=$cr_dev_list_md" >> "$DESTDIR/etc/mdadm.conf"
1514 for f in $cr_dev_list $cr_rootdev $dev_list_extra; do
1515 # mkdir in case of devfs name
1516 inst_d $(dirname $f)
1517 [ -e "$DESTDIR/$f" ] && continue
1518 # this works fine with and without devfs
1523 echo "mdassemble" | add_linuxrc
1525 # needed to determine md-version
1526 if [ "$do_md0" -eq 1 ]; then
1527 mknod $DESTDIR/dev/md0 b 9 0
1532 # use root=/dev/ram0 init=/linuxrc when starting kernel or you will
1533 # have problems like init(XX) being child process of swapper(1).
1534 debug "Adding rootfs on NFS support to initrd (dhcp)"
1535 mknod "$DESTDIR/dev/urandom" c 1 9
1536 mkdir "$DESTDIR/newroot"
1537 add_linuxrc <<-'EOF'
1538 ifconfig lo 127.0.0.1 up
1539 route add -net 127.0.0.0 mask 255.0.0.0 lo
1541 udhcpc -i eth0 -f -q -s /bin/setdhcp
1545 [ -x /sbin/chroot ] && exec /sbin/chroot . /sbin/init -i < dev/console > dev/console 2>&1
1546 exec /usr/sbin/chroot . /sbin/init -i < dev/console > dev/console 2>&1
1549 cat <<-'EOF' > "$DESTDIR/bin/setdhcp"
1551 [ "$1" != "bound" ] && exit
1552 [ -n "$broadcast" ] && BROADCAST="broadcast $broadcast"
1553 [ -n "$subnet" ] && NETMASK="netmask $subnet"
1554 ifconfig $interface $ip $BROADCAST $NETMASK up
1555 if [ -n "$router" ]; then
1556 for r in $router; do
1557 route add default gw $r dev $interface
1561 for o in $CMDLINE; do
1564 rootpath=${o#nfsroot=}
1569 if [ -n "$rootpath" ]; then
1570 mount -n -t nfs -o ro,nolock,posix,tcp,wsize=8192,rsize=8192 $rootpath /newroot
1572 echo "Missing rootpath in what DHCP server sent to us. Failing..."
1573 echo "All seen variables are listed below:"
1578 chmod 755 "$DESTDIR/bin/setdhcp"
1582 debug "Adding LVM support to initrd"
1583 inst_d /tmp /newroot
1584 inst_exec /sbin/initrd-lvm /bin/lvm.static
1586 # always make /dev on tmpfs for LVM2
1587 if [ "$LVMTOOLSVERSION" = "2" ]; then
1591 if ! is_yes "$dev_mounted"; then
1593 mknod $DESTDIR/dev/mapper/control c 10 63
1594 for device in $PVDEVICES; do
1595 # if LVM on RAID then device might be copied already in gen_md
1596 [ -e "$DESTDIR/dev/$(basename $device)" ] && continue
1602 if [ "$LVMTOOLSVERSION" = "1" ]; then
1605 for vg in $VGVOLUMES; do
1606 lvm vgchange -T -a y $vg
1610 echo "cat /etc/lvm.conf > /tmp/lvm.conf" | add_linuxrc
1611 echo "global {" > "$DESTDIR/etc/lvm.conf"
1612 echo " locking_type = 0" >> "$DESTDIR/etc/lvm.conf"
1613 echo " locking_dir = \"/tmp\"" >> "$DESTDIR/etc/lvm.conf"
1614 echo "}" >> "$DESTDIR/etc/lvm.conf"
1615 echo "devices {" >> "$DESTDIR/etc/lvm.conf"
1616 echo " sysfs_scan=0" >> "$DESTDIR/etc/lvm.conf"
1617 if is_yes "$have_md"; then
1618 echo " md_component_detection = 1" >> "$DESTDIR/etc/lvm.conf"
1620 if is_yes "$have_dmraid" || is_yes "$have_multipath"; then
1621 echo ' types = [ "device-mapper", 254 ]' >> "$DESTDIR/etc/lvm.conf"
1623 if [ "$lvm_ignore_devices" ]; then
1624 # TODO: think of merging with lvm dumpconfig output
1625 echo ' filter = [' >> "$DESTDIR/etc/lvm.conf"
1627 for dev in $lvm_ignore_devices; do
1628 debug "LVM v2: ignore device $dev"
1629 printf ' "r|^%s.*|",\n' $dev
1630 done >> "$DESTDIR/etc/lvm.conf"
1631 echo ']' >> "$DESTDIR/etc/lvm.conf"
1633 # XXX filter= must be on one line!
1634 lvm dumpconfig | awk '/filter=/' >> "$DESTDIR/etc/lvm.conf"
1635 echo "}" >> "$DESTDIR/etc/lvm.conf"
1640 export ROOTDEV=$rootdev
1641 export ROOTVG="$VGVOLUMES"
1642 export SUSPENDVG=$SUSPENDVG
1644 add_linuxrc <<-'EOF'
1645 # parse rootdev from kernel commandline if it begins with /
1648 if [ "$ROOT" != "$ROOTDEV" ]; then
1650 echo "LVM: Using 'root=$ROOTDEV' from kernel commandline"
1651 local tmp=${ROOTDEV#/dev/}
1652 if [ "$tmp" != "$ROOTDEV" ]; then
1654 echo "LVM: Using Volume Group '$ROOTVG' for rootfs"
1661 if [ "$SUSPENDVG" = "$ROOTVG" ]; then
1662 export VGVOLUMES="$ROOTVG"
1664 export VGVOLUMES="$SUSPENDVG $ROOTVG"
1667 # disable noise from LVM accessing devices that aren't ready.
1668 read printk < /proc/sys/kernel/printk
1669 if [ ! "$DEBUGINITRD" ]; then
1670 echo 0 > /proc/sys/kernel/printk
1673 export LVM_SYSTEM_DIR=/tmp
1674 : 'Scanning for Volume Groups'
1675 lvm.static vgscan --mknodes --ignorelockingfailure 2>/dev/null
1677 : 'Activating Volume Groups'
1678 for vol in $VGVOLUMES; do
1679 lvm.static vgchange --ignorelockingfailure -a y $vol 2>/dev/null
1682 echo "$printk" > /proc/sys/kernel/printk
1684 # Find out major/minor
1685 attrs="$(lvm.static lvdisplay --ignorelockingfailure -c $ROOTDEV 2>/dev/null)"
1686 if [ "$attrs" ]; then
1687 majmin="${attrs#*$ROOTDEV*:*:*:*:*:*:*:*:*:*:*:*}"
1688 if [ "$majmin" != "$attrs" ]; then
1689 major="${majmin%:*}"
1690 minor="${majmin#*:}"
1694 if [ "$major" -a "$minor" ]; then
1696 echo $((256 * $major + $minor)) > /proc/sys/kernel/real-root-dev
1698 echo 2>&1 "Error figuring out real root device for $ROOTDEV!"
1699 echo 2>&1 "System will not most likely boot up! So dropping you to a shell!"
1709 debug "Adding BLKID support to initrd"
1710 inst_exec /sbin/initrd-blkid /bin/blkid
1712 add_linuxrc <<-'EOF'
1713 # if built with blkid change ROOT=LABEL=something into ROOT=/dev/somethingelse -
1715 if [ "${ROOT##LABEL=}" != "${ROOT}" -o "${ROOT##UUID=}" != "${ROOT}" ]; then
1716 ROOT="$(/bin/blkid -t $ROOT -o device -l)"
1721 initrd_gen_setrootdev() {
1722 debug "Adding rootfs finding based on kernel cmdline root= option support."
1723 add_linuxrc <<-'EOF'
1724 if [ "${ROOT##/dev/}" != "${ROOT}" ]; then
1725 rootnr="$(busybox awk -v rootnode="${ROOT##/dev/}" '$4 == rootnode { print 256 * $1 + $2 }' /proc/partitions)"
1726 if [ -n "$rootnr" ]; then
1727 echo "$rootnr" > /proc/sys/kernel/real-root-dev
1733 initrd_gen_initramfs_switchroot() {
1735 if [ "$rootdev" = "/dev/nfs" ]; then
1736 echo "rootfs on NFS root=/dev/nfs"
1738 [ ! -e "$DESTDIR/$rootdev" ] && inst $rootdev $rootdev
1740 # Parsing root parameter
1741 # We support passing root as hda3 /dev/hda3 0303 0x0303 and 303
1742 add_linuxrc <<-'EOF'
1743 device=/dev/no_partition_found
1744 eval "$(busybox awk -v c="$ROOT" '
1746 num_pattern_short = "[0-9a-f][0-9a-f][0-9a-f]";
1747 num_pattern = "[0-9a-f]" num_pattern_short;
1748 dev_pattern = "[hms][a-z][a-z]([0-9])+";
1749 partition = "no_partition_found";
1753 if (c ~ "^" num_pattern_short "$") sub("^", "0", c);
1754 if (c ~ "^" num_pattern "$") {
1755 maj = sprintf("%s",substr(c,1,2));
1756 min = sprintf("%s",substr(c,3));
1758 if (c ~ "^\/dev\/" dev_pattern "$") sub("^/dev/","", c);
1759 if (c ~ "^" dev_pattern "$") partition = c;
1762 $4 ~ partition { maj = $1; min = $2; }
1763 $1 ~ maj && $2 ~ min { partition = $4; }
1766 print sprintf("device=/dev/%s\nmaj=%s\nmin=%s",
1767 partition, maj, min);
1769 ' /proc/partitions)"
1770 if [ "$device" != '/dev/no_partition_found' -a ! -b $device ]; then
1771 mknod $device b $maj $min
1780 add_linuxrc <<-'EOF'
1781 if [ "$device" = '/dev/no_partition_found' ]; then
1785 mount -t $rootfs -r $device /newroot
1786 init="$(echo "$CMDLINE" | busybox awk '/init=\// { gsub(/.*init=/,NIL,$0); gsub(/ .*/,NIL,$0); print }')"
1787 if [ -z "$init" -o ! -x "/newroot$init" ]; then
1793 busybox_applet switch_root
1794 add_linuxrc <<-'EOF'
1795 exec switch_root /newroot $init
1797 echo "Error! initramfs should not reach this place."
1798 echo "It probably means you've got old version of busybox, with broken"
1799 echo "initramfs support. Trying to boot anyway, but won't promise anything."
1801 exec chroot /newroot $init
1803 echo "Failed to chroot!"
1805 # we need /init being real file, not symlink, otherwise the initramfs will
1806 # not be ran by pid 1 which is required for switch_root
1807 mv $DESTDIR/linuxrc $DESTDIR/init
1808 ln -s init $DESTDIR/linuxrc
1812 if [ "$(id -u)" != 0 ]; then
1813 die "You need to be root to generate initrd"
1816 if [ -f /etc/udev/udev.conf -a -x /sbin/initrd-udevd ]; then
1818 . /etc/udev/udev.conf
1821 if [ -x /sbin/dmraid-initrd ]; then
1825 if [ -x /sbin/cryptsetup ]; then
1829 if [ -x /sbin/multipath ]; then
1833 if [ -x /sbin/initrd-blkid ]; then
1837 if [ -r /etc/sysconfig/geninitrd ]; then
1838 . /etc/sysconfig/geninitrd
1841 if [ ! -x /bin/initrd-busybox ]; then
1842 die "/bin/initrd-busybox is missing!"
1845 # backwards compatible
1846 if [ "$USE_SUSPEND2" ]; then
1847 USE_TUXONICE=$USE_SUSPEND2
1848 warn "USE_SUSPEND2 is deprecated, use USE_TUXONICE now instead."
1851 while [ $# -gt 0 ]; do
1861 modulefile=${1#--modules-conf=}
1867 --use-raidstart|--with-raidstart)
1870 --without-raidstart)
1873 --use-insmod-static|--with-insmod-static)
1876 --without-insmod-static)
1882 --without-bootsplash)
1894 --without-fbcondecor)
1903 --with-suspend2 | --with-tuxonice)
1906 --without-suspend2 | --without-tuxonice)
1909 --lvmtoolsversion=|--lvmversion=)
1910 LVMTOOLSVERSION=${1#--lvmtoolsversion=}
1911 LVMTOOLSVERSION=${1#--lvmversion=}
1913 --lvmtoolsversion|--lvmversion)
1926 --without-multipath)
1936 BASICMODULES="$BASICMODULES ${1#--with=}"
1939 BASICMODULES="$BASICMODULES $2"
1943 echo "$PROGRAM: version $VERSION"
1959 PREMODS="$PREMODS ${1#--preload=}"
1962 PREMODS="$PREMODS $2"
1966 warn "Warning: --fs option is obsoleted. Use --initrdfs instead"
1970 warn "Warning: --fs option is obsoleted. Use --initrdfs instead"
1975 INITRDFS=${1#--initrdfs=}
1988 if [ -z "$target" ]; then
1990 elif [ -z "$kernel" ]; then
2001 if [ -z "$target" -o -z "$kernel" ]; then
2005 if [ ! -f /boot/vmlinuz-"$kernel" ]; then
2006 warn "/boot/vmlinuz-$kernel doesn't exist, is your /boot mounted?"
2009 pack_version=$(echo "$kernel" | awk -F. '{print sprintf("%03d%03d",$1,$2)}')
2010 pack_version_long=$(echo "$kernel" | awk -F. '{print sprintf("%03d%03d%03d",$1,$2,$3)}')
2012 if [ -z "$INITRDFS" ]; then
2013 if [ -z "$FS" ]; then
2015 if [ "$pack_version" -ge "002005" ]; then
2016 INITRDFS="initramfs"
2021 warn "Warning: FS configuration options is obsoleted. Use INITRDFS instead"
2026 if [ "$pack_version" -lt "002006" ]; then
2031 if [ "$pack_version" -ge "002005" ]; then
2036 if is_yes "$USEINSMODSTATIC"; then
2037 insmod="insmod.static"
2038 INSMOD="/sbin/insmod.static"
2039 if [ "$pack_version" -lt "002005" -a -f /sbin/insmod.static.modutils ]; then
2040 INSMOD="/sbin/insmod.static.modutils"
2042 if [ ! -f "$INSMOD" ]; then
2043 die "insmod.static requested but /sbin/insmod.static not found!"
2049 if [ ! -x /sbin/mke2fs ]; then
2050 die "/sbin/mke2fs is missing"
2054 if [ ! -x /sbin/genromfs ]; then
2055 die "/sbin/genromfs is missing"
2059 if [ ! -x /sbin/mkcramfs ]; then
2060 die "/sbin/mkcramfs is missing"
2064 if [ ! -x /bin/cpio ]; then
2065 die "/bin/cpio is missing"
2067 if [ ! -x /usr/bin/find ]; then
2068 die "/usr/bin/find is missing"
2072 die "Filesystem $INITRDFS on initrd is not supported"
2076 if [ -L "$target" ]; then
2077 target=$(readlink -f "$target")
2080 if [ -n "$img_vers" ]; then
2081 target="$target-$kernel"
2084 if [ -z "$force" -a -f "$target" ]; then
2085 die "$target already exists."
2088 if [ ! -d "/lib/modules/$kernel" ]; then
2089 die "/lib/modules/$kernel is not a directory."
2092 if [ "$INITRDFS" != "initramfs" ]; then
2093 if is_yes "$FB_SPLASH"; then
2094 warn "Using fbsplash requires INITRDFS=initramfs; skipping fbsplash generation"
2097 if is_yes "$FB_CON_DECOR"; then
2098 warn "Using fbcondecor requires INITRDFS=initramfs; skipping fbcondecor generation"
2103 if is_yes "$USE_SUSPEND" && is_yes "$USE_TUXONICE"; then
2104 warn "Tuxonice and mainline suspend are exclusive!"
2107 if is_yes "$FB_SPLASH" && is_yes "$BOOT_SPLASH"; then
2108 warn "bootsplash and fbsplash are exclusive!"
2111 if [ ! -f /proc/mounts ]; then
2112 warn "/proc filesystem not mounted, may cause wrong results or failure."
2115 if [ -d /usr/lib64 ]; then
2120 debug "Using libdir: $_lib"
2124 for n in $PREMODS; do
2128 if [ "$FBMODULE" ]; then
2129 findmodule "$FBMODULE"
2132 # allow forcing loading SCSI and/or IDE modules
2133 if is_yes "$ADDSCSI"; then
2137 if is_yes "$ADDIDE"; then
2141 if is_yes "$USE_SUSPEND"; then
2142 find_modules_suspend
2145 find_root "$fstab" || exit
2146 debug "Using $rootdev as device for rootfs"
2148 find_modules_for_devpath "$rootdev"
2149 [ -n "$rootdev_add" ] && find_modules_for_devpath "$rootdev_add"
2151 findmodule "-$rootFs"
2153 for n in $BASICMODULES; do
2157 if is_yes "$USE_TUXONICE"; then
2161 if is_yes "$FB_SPLASH"; then
2165 if [ -n "$ifneeded" -a -z "$MODULES" ]; then
2166 debug "No modules are needed -- not building initrd image."
2170 DESTDIR=$(mktemp -d -t initrd.XXXXXX) || die "mktemp failed"
2171 RCFILE="$DESTDIR/linuxrc"
2173 chmod a+rx "$RCFILE"
2174 ln -s linuxrc $DESTDIR/init
2176 # create dirs that we really need
2177 inst_d /{lib,bin,etc,dev{,/pts,/shm},loopfs,var,proc,sys}
2179 modules_install "$MODULES"
2181 # mknod'ing the devices instead of copying them works both with and
2183 mknod "$DESTDIR/dev/console" c 5 1
2184 mknod "$DESTDIR/dev/null" c 1 3
2185 mknod "$DESTDIR/dev/zero" c 1 5
2187 inst_exec /bin/initrd-busybox /bin/initrd-busybox
2188 ln -s initrd-busybox $DESTDIR/bin/sh
2189 ln -s initrd-busybox $DESTDIR/bin/busybox # for older busyboxes who had /bin/busybox as EXEPATH
2191 if is_yes "$USEINSMODSTATIC"; then
2192 inst_exec "$INSMOD" /bin/insmod.static
2197 # initrd generated by:
2202 add_linuxrc <<-'EOF'
2203 read CMDLINE < /proc/cmdline; export CMDLINE
2205 for arg in $CMDLINE; do
2206 if [ "${arg}" = "debuginitrd" ]; then
2209 if [ "${arg##debuginitrd=}" != "${arg}" ]; then
2210 DEBUGINITRD=${arg##debuginitrd=}
2212 if [ "${arg##root=}" != "${arg}" ]; then
2217 # make debugshell() invoke subshell if $DEBUGINITRD=sh
2218 if [ "$DEBUGINITRD" = "sh" ]; then
2221 if is_yes "$RUN_SULOGIN_ON_ERR"; then
2222 add_linuxrc <<-'EOF'
2223 echo "debug shell disabled by /etc/sysconfig/system:RUN_SULOGIN_ON_ERR setting"
2226 add_linuxrc <<-'EOF'
2230 add_linuxrc <<-'EOF'
2238 if [ "$DEBUGINITRD" ]; then
2243 modules_add_linuxrc $MODULES
2245 # TODO: rewrite for busybox
2246 #if [ -n "$loopDev" ]; then
2247 # if [ ! -d /initrd ]; then
2251 # cp -a "$loopDev" "$DESTDIR/dev"
2252 # cp -a "$rootdev" "$DESTDIR/dev"
2253 # echo "echo Mounting device containing loopback root filesystem" >> "$RCFILE"
2254 # echo "mount -t $loopFs $loopDev /loopfs" >> "$RCFILE"
2255 # echo "echo Setting up loopback device $rootdev" >> $RCFILE
2256 # echo "losetup $rootdev /loopfs$loopFile" >> "$RCFILE"
2259 if is_yes "$USE_UDEV"; then
2263 if is_yes "$USE_TUXONICE"; then
2267 if is_yes "$need_v86d"; then
2271 if is_yes "$have_luks"; then
2275 if is_yes "$have_dmraid"; then
2279 if is_yes "$have_multipath"; then
2280 initrd_gen_multipath
2283 if is_yes "$USE_BLKID"; then
2287 if is_yes "$have_nfs"; then
2289 elif is_yes "$USERAIDSTART" && is_yes "$have_md"; then
2291 if is_yes "$have_lvm"; then
2294 initrd_gen_setrootdev
2296 elif is_yes "$have_lvm"; then
2299 initrd_gen_setrootdev
2302 if is_yes "$USE_SUSPEND"; then
2306 # additional devs always needed
2307 [ ! -e "$DESTDIR/$rootdev_add" ] && inst $rootdev_add /dev
2309 if [ "$INITRDFS" = "initramfs" ]; then
2310 initrd_gen_initramfs_switchroot
2315 if is_yes "$FB_SPLASH"; then
2319 if is_yes "$FB_CON_DECOR"; then
2320 initrd_gen_fbcondecor
2323 IMAGE=$(mktemp -t initrd.img-XXXXXX) || die "mktemp failed"
2325 debug "Creating $INITRDFS image $IMAGE"
2328 IMAGESIZE=$(du -ks $DESTDIR | awk '{print int(($1+1023+512)/1024)*1024}')
2329 debug "ext2 image size: $IMAGESIZE ($DESTDIR)"
2330 if [ "$IMAGESIZE" -gt 4096 ]; then
2331 warn "Your image size is larger than 4096, Be sure to boot kernel with ramdisk_size=$IMAGESIZE!"
2334 dd if=/dev/zero of="$IMAGE" bs=1k count="$IMAGESIZE" 2> /dev/null
2335 mke2fs -q -F -b 1024 -m 0 "$IMAGE" 2>/dev/null 1>&2
2336 tune2fs -i 0 "$IMAGE" >/dev/null 2>&1
2338 local tmpmnt=$(mktemp -d -t initrd.mnt-XXXXXX)
2339 debug "Mounting ext2 image $IMAGE to $tmpmnt"
2340 mount -o loop -t ext2 "$IMAGE" "$tmpmnt"
2341 # We don't need this directory, so let's save space
2342 rm -rf "$tmpmnt"/lost+found
2344 debug "Copy recursively $DESTDIR -> $tmpmnt"
2345 cp -a $DESTDIR/* $tmpmnt
2351 genromfs -f "$IMAGE" -d "$DESTDIR" -V "PLD initrd for kernel $kernel"
2352 IMAGESIZE=$(stat -c %s $IMAGE | awk '{print int((($1/1024)+1023)/1024)*1024}')
2353 debug "Image size for romfs: ${IMAGESIZE}KiB ($IMAGE)"
2354 if [ "$IMAGESIZE" -gt 4096 ]; then
2355 warn "Your image size is larger than 4096, Be sure to boot kernel with ramdisk_size=$IMAGESIZE!"
2359 mkcramfs "$DESTDIR" "$IMAGE"
2362 (cd $DESTDIR; find . | cpio --quiet -H newc -o > "$IMAGE")
2365 echo "Filesystem $INITRDFS not supported by $PROGRAM";
2368 if is_yes "$COMPRESS"; then
2369 tmp=$(mktemp "$target".XXXXXX) || die "mktemp failed"
2370 debug "Compressing $target"
2371 gzip -9 < "$IMAGE" > "$tmp"
2372 mv -f "$tmp" "$target"
2374 cp -a "$IMAGE" "$target"
2377 # XXX. check if bootsplash can output data to tmp dir not directly to initramfs image.
2378 if is_yes "$BOOT_SPLASH"; then
2379 initrd_gen_bootsplash "$target"
2382 rm -rf "$DESTDIR" "$IMAGE"
2384 # vim:ts=4:sw=4:noet:fdm=marker