2135 lines
64 KiB
Bash
2135 lines
64 KiB
Bash
#!/bin/bash --norc
|
|
# vim:sts=4:sw=4:ts=8:et
|
|
|
|
# mkdumprd
|
|
#
|
|
# Copyright 2005 Red Hat, Inc.
|
|
#
|
|
# Written by Erik Troan <ewt@redhat.com>
|
|
#
|
|
# Contributors:
|
|
# Elliot Lee <sopwith@cuc.edu>
|
|
# Miguel de Icaza <miguel@nuclecu.unam.mx>
|
|
# Christian 'Dr. Disk' Hechelmann <drdisk@ds9.au.s.shuttle.de>
|
|
# Michael K. Johnson <johnsonm@redhat.com>
|
|
# Pierre Habraken <Pierre.Habraken@ujf-grenoble.fr>
|
|
# Jakub Jelinek <jakub@redhat.com>
|
|
# Carlo Arenas Belon (carenas@chasqui.lared.net.pe>
|
|
# Keith Owens <kaos@ocs.com.au>
|
|
# Bernhard Rosenkraenzer <bero@redhat.com>
|
|
# Matt Wilson <msw@redhat.com>
|
|
# Trond Eivind Glomsrød <teg@redhat.com>
|
|
# Jeremy Katz <katzj@redhat.com>
|
|
# Preston Brown <pbrown@redhat.com>
|
|
# Bill Nottingham <notting@redhat.com>
|
|
# Guillaume Cottenceau <gc@mandrakesoft.com>
|
|
# Peter Jones <pjones@redhat.com>
|
|
# Neil Horman <nhorman@redhat.com>
|
|
# Jarod Wilson <jwilson@redhat.com>
|
|
cmdname=`basename $0`
|
|
|
|
umask 0022
|
|
|
|
export MALLOC_PERTURB_=204
|
|
|
|
PATH=/sbin:/usr/sbin:/bin:/usr/bin:$PATH
|
|
export PATH
|
|
|
|
. /etc/rc.d/init.d/functions
|
|
|
|
VERSION=5.0.39
|
|
|
|
PROBE="yes"
|
|
MODULES=""
|
|
PREMODS=""
|
|
DMRAIDS=""
|
|
MPATHS=""
|
|
|
|
|
|
CONFMODS="$MODULES"
|
|
MODULES=""
|
|
|
|
withusb=yes
|
|
compress=1
|
|
allowmissing=""
|
|
target=""
|
|
kernel=""
|
|
force=""
|
|
verbose=""
|
|
img_vers=""
|
|
builtins=""
|
|
modulefile=/etc/modules.conf
|
|
rc=0
|
|
|
|
IMAGESIZE=8000
|
|
PRESCSIMODS="sd_mod"
|
|
fstab="/etc/fstab"
|
|
|
|
vg_list=""
|
|
net_list=""
|
|
USING_METHOD=""
|
|
SAVE_PATH=/var/crash
|
|
bin=""
|
|
KDUMP_POST=""
|
|
extra_kdump_mods=""
|
|
|
|
TMPDISKLIST=`mktemp /tmp/disklist.XXXXXX`
|
|
|
|
vecho()
|
|
{
|
|
NONL=""
|
|
if [ "$1" == "-n" ]; then
|
|
NONL="-n"
|
|
shift
|
|
fi
|
|
[ -n "$verbose" ] && echo $NONL "$@"
|
|
}
|
|
|
|
error()
|
|
{
|
|
NONL=""
|
|
if [ "$1" == "-n" ]; then
|
|
NONL="-n"
|
|
shift
|
|
fi
|
|
echo $NONL "$@" >&2
|
|
}
|
|
|
|
usage () {
|
|
if [ "$1" == "-n" ]; then
|
|
cmd=echo
|
|
else
|
|
cmd=error
|
|
fi
|
|
|
|
$cmd "usage: $cmdname [--version] [--help] [-v] [-d] [-f] [--preload <module>]"
|
|
$cmd " [--image-version]"
|
|
$cmd " [--builtin=<module>] [--omit-dmraid]"
|
|
$cmd " [--fstab=<fstab>] [--nocompress] <initrd-image> <kernel-version>"
|
|
$cmd ""
|
|
$cmd " (ex: $cmdname /boot/initrd-2.2.5-15.img 2.2.5-15)"
|
|
|
|
if [ "$1" == "-n" ]; then
|
|
exit 0
|
|
else
|
|
exit 1
|
|
fi
|
|
}
|
|
|
|
moduledep() {
|
|
if [ ! -f "/lib/modules/$kernel/modules.dep" ]; then
|
|
error "No dep file found for kernel $kernel"
|
|
exit 1
|
|
fi
|
|
|
|
vecho -n "Looking for deps of module $1"
|
|
deps=$(awk 'BEGIN { searched=ARGV[2]; ARGV[2]=""; rc=1 } \
|
|
function modname(filename) { match(filename, /\/([^\/]+)\.k?o:?$/, ret); return ret[1] } \
|
|
function show() { if (orig == searched) { print dep; orig=""; rc=0; exit } } \
|
|
/^\/lib/ { show(); \
|
|
orig=modname($1); dep=""; \
|
|
if ($2) { for (i = 2; i <= NF; i++) { dep=sprintf("%s %s", dep, modname($i)); } } } \
|
|
/^ / { dep=sprintf("%s %s", dep, modname($1)); } \
|
|
END { show(); exit(rc) }' /lib/modules/$kernel/modules.dep $1)
|
|
[ -n "$deps" ] && vecho ":$deps" || vecho
|
|
}
|
|
|
|
findone() {
|
|
echo nash-find "$@" | /sbin/nash --force --quiet \
|
|
| /bin/awk '{ print $1; exit; }'
|
|
}
|
|
|
|
findall() {
|
|
find "$@"
|
|
}
|
|
|
|
dm_get_uuid() {
|
|
dmsetup info "$1" | awk '/^.*UUID.*/ {print $2}'
|
|
}
|
|
|
|
findmodule() {
|
|
skiperrors=""
|
|
|
|
if [ $1 == "--skiperrors" ]; then
|
|
skiperrors=--skiperrors
|
|
shift
|
|
fi
|
|
|
|
local modName=$1
|
|
|
|
if [ "$modName" = "off" -o "$modName" = "null" ]; then
|
|
return
|
|
fi
|
|
|
|
if [ $(echo $modName | cut -b1) = "-" ]; then
|
|
skiperrors=--skiperrors
|
|
modName=$(echo $modName | cut -b2-)
|
|
fi
|
|
|
|
case "$MODULES " in
|
|
*"/$modName.ko "*) return ;;
|
|
esac
|
|
|
|
if echo $builtins | egrep -q '(^| )'$modName'( |$)' ; then
|
|
vecho "module $modName assumed to be built in"
|
|
return
|
|
fi
|
|
|
|
# special cases
|
|
if [ "$modName" = "i2o_block" ]; then
|
|
findmodule i2o_core
|
|
findmodule -i2o_pci
|
|
modName="i2o_block"
|
|
elif [ "$modName" = "ppa" ]; then
|
|
findmodule parport
|
|
findmodule parport_pc
|
|
modName="ppa"
|
|
elif [ "$modName" = "sbp2" ]; then
|
|
findmodule ieee1394
|
|
findmodule ohci1394
|
|
modName="sbp2"
|
|
elif [ "$modName" = "raid6" ]; then
|
|
findmodule raid456
|
|
modName="raid456"
|
|
else
|
|
moduledep $modName
|
|
for i in $deps; do
|
|
findmodule $i
|
|
done
|
|
fi
|
|
|
|
fmPath=$(modprobe --set-version $kernel -l $modName 2>/dev/null)
|
|
|
|
if [ ! -f "$fmPath" ]; then
|
|
for modExt in o.gz o ko
|
|
do
|
|
for modDir in /lib/modules/$kernel/updates /lib/modules/$kernel
|
|
do
|
|
if [ -d $modDir ]
|
|
then
|
|
fmPath=$(findone $modDir -name $modName.$modExt)
|
|
if [ -f "$fmPath" ]
|
|
then
|
|
break 2
|
|
fi
|
|
fi
|
|
done
|
|
done
|
|
fi
|
|
|
|
if [ ! -f "$fmPath" ]; then
|
|
if [ -n "$skiperrors" ]; then
|
|
return
|
|
fi
|
|
|
|
# ignore the absence of the scsi modules
|
|
for n in $PRESCSIMODS; do
|
|
if [ "$n" = "$modName" ]; then
|
|
return;
|
|
fi
|
|
done;
|
|
|
|
if [ -n "$allowmissing" ]; then
|
|
error "WARNING: No module $modName found for kernel $kernel, continuing anyway"
|
|
return
|
|
fi
|
|
|
|
error "No module $modName found for kernel $kernel, aborting."
|
|
exit 1
|
|
fi
|
|
|
|
# only need to add each module once
|
|
MODULES="$MODULES $fmPath"
|
|
|
|
# need to handle prescsimods here -- they need to go _after_ scsi_mod
|
|
if [ "$modName" = "scsi_mod" ]; then
|
|
for n in $PRESCSIMODS ; do
|
|
findmodule $n
|
|
done
|
|
fi
|
|
}
|
|
|
|
|
|
inst() {
|
|
if [ "$#" != "2" ];then
|
|
echo "usage: inst <file> <destination>"
|
|
return
|
|
fi
|
|
vecho "$1 -> $2"
|
|
cp $1 $2
|
|
}
|
|
|
|
readlink() {
|
|
readlink "$1"
|
|
}
|
|
|
|
|
|
findstoragedriverinsys () {
|
|
while [ ! -L device ]; do
|
|
[ "$PWD" = "/sys" ] && return
|
|
cd ..
|
|
done
|
|
cd $(readlink ./device)
|
|
while [ ! -f modalias ]; do
|
|
[ "$PWD" = "/sys/devices" ] && return
|
|
cd ..
|
|
done
|
|
modalias=$(cat modalias)
|
|
for driver in $(modprobe --set-version $kernel --show-depends $modalias 2>/dev/null| awk '{ print gensub(".*/","","g",$2) }') ; do
|
|
findmodule ${driver%%.ko}
|
|
done
|
|
}
|
|
|
|
findstoragedriver () {
|
|
for device in $@ ; do
|
|
case " $handleddevices " in
|
|
*" $device "*)
|
|
continue ;;
|
|
*) handleddevices="$handleddevices $device" ;;
|
|
esac
|
|
if [[ "$device" == "md[0-9]+" ]]; then
|
|
vecho "Found RAID component $device"
|
|
handleraid "$device"
|
|
continue
|
|
fi
|
|
vecho "Looking for driver for device $device"
|
|
device=`echo $device | sed 's/\//\!/g'`
|
|
pushd $(readlink /sys/class/block/$device ) >/dev/null 2>&1 || return
|
|
findstoragedriverinsys
|
|
popd >/dev/null 2>&1
|
|
done
|
|
}
|
|
|
|
findnetdriver() {
|
|
for device in $@ ; do
|
|
case " $handleddevices " in
|
|
*" $device "*)
|
|
continue ;;
|
|
*) handleddevices="$handleddevices $device" ;;
|
|
esac
|
|
|
|
case "$device" in
|
|
bond*)
|
|
modalias=bonding
|
|
;;
|
|
eth*.*)
|
|
modalias=8021q
|
|
;;
|
|
*)
|
|
if [ -f /sys/class/net/$device/device/modalias ]
|
|
then
|
|
modalias=$(cat /sys/class/net/$device/device/modalias)
|
|
else
|
|
modalias=$(ethtool -i $device | awk '/^driver:/ { print $2 }')
|
|
fi
|
|
;;
|
|
esac
|
|
for driver in $(modprobe --set-version $kernel --show-depends $modalias 2>/dev/null| awk '{ print gensub(".*/","","g",$2) }') ; do
|
|
findmodule ${driver%%.ko}
|
|
done
|
|
done
|
|
}
|
|
|
|
handleraid() {
|
|
local start=0
|
|
|
|
if [ -n "$noraid" -o ! -f /proc/mdstat ]; then
|
|
return 0
|
|
fi
|
|
|
|
levels=$(grep "^$1[ ]*:" /proc/mdstat | \
|
|
awk '{ print $4 }')
|
|
devs=$(grep "^$1[ ]*:" /proc/mdstat | \
|
|
awk '{ print gensub("\\[[0-9]*\\]","","g",gensub("^md.*raid[0-9]*","","1")) }')
|
|
|
|
for level in $levels ; do
|
|
case $level in
|
|
linear)
|
|
findmodule linear
|
|
start=1
|
|
;;
|
|
multipath)
|
|
findmodule multipath
|
|
start=1
|
|
;;
|
|
raid[01456] | raid10)
|
|
findmodule $level
|
|
start=1
|
|
;;
|
|
*)
|
|
error "raid level $level (in /proc/mdstat) not recognized"
|
|
;;
|
|
esac
|
|
done
|
|
findstoragedriver $devs
|
|
if [ "$start" = 1 ]; then
|
|
raiddevices="$raiddevices $1"
|
|
fi
|
|
return $start
|
|
}
|
|
|
|
handlelvordev() {
|
|
local vg=`lvs --noheadings -o vg_name $1 2>/dev/null`
|
|
if [ -z "$vg" ]; then
|
|
vg=`lvs --noheadings -o vg_name $(echo $1 | sed -e 's#^/dev/mapper/\([^-]*\)-\(.*\)$#/dev/\1/\2#') 2>/dev/null`
|
|
fi
|
|
if [ -n "$vg" ]; then
|
|
vg=`echo $vg` # strip whitespace
|
|
case " $vg_list " in
|
|
*" $vg "*)
|
|
;;
|
|
*)
|
|
vg_list="$vg_list $vg"
|
|
for device in `vgdisplay -v $vg 2>/dev/null | sed -n 's/PV Name//p'`; do
|
|
IS_UUID=`echo $device | grep UUID`
|
|
IS_LABEL=`echo $device | grep LABEL`
|
|
if [ -n "$IS_UUID" -o -n "$IS_LABEL" ]
|
|
then
|
|
devname=`findfs $device`
|
|
else
|
|
devname=$device
|
|
fi
|
|
echo $devname | sed -e's/\/dev\///' -e's/[0-9]\+//' >> $TMPDISKLIST
|
|
findstoragedriver ${device##/dev/}
|
|
done
|
|
;;
|
|
esac
|
|
else
|
|
IS_UUID=`echo $1 | grep UUID`
|
|
IS_LABEL=`echo $1 | grep LABEL`
|
|
if [ -n "$IS_UUID" -o -n "$IS_LABEL" ]
|
|
then
|
|
devname=`findfs $1`
|
|
else
|
|
devname=$1
|
|
fi
|
|
|
|
echo $devname | sed -e's/\/dev\///' -e's/[0-9]\+//' >> $TMPDISKLIST
|
|
findstoragedriver ${1##/dev/}
|
|
fi
|
|
}
|
|
|
|
handlenetdev() {
|
|
local dev=$1
|
|
cp /etc/sysconfig/network-scripts/ifcfg-$dev $MNTIMAGE/etc
|
|
BOOTPROTO=""
|
|
VLAN=""
|
|
MASTER=""
|
|
SLAVE=""
|
|
. $MNTIMAGE/etc/ifcfg-$dev
|
|
|
|
findnetdriver $dev
|
|
|
|
|
|
if [ "$BOOTPROTO" == "dhcp" ]
|
|
then
|
|
echo iface $dev inet dhcp >> $MNTIMAGE/etc/network/interfaces
|
|
else
|
|
echo iface $dev inet static >> $MNTIMAGE/etc/network/interfaces
|
|
if [ -n "$IPADDR" ]
|
|
then
|
|
echo " " address $IPADDR >> $MNTIMAGE/etc/network/interfaces
|
|
fi
|
|
if [ -n "$NETMASK" ]
|
|
then
|
|
echo " " netmask $NETMASK >> $MNTIMAGE/etc/network/interfaces
|
|
fi
|
|
if [ -z "$GATEWAY" ]
|
|
then
|
|
GATEWAY=`/sbin/ip route show | awk '/^default/ {print $3}'`
|
|
fi
|
|
echo " " gateway $GATEWAY >> $MNTIMAGE/etc/network/interfaces
|
|
fi
|
|
|
|
#This lets us recursively handle stacked devices
|
|
case "$dev" in
|
|
bond*)
|
|
#This is a bond, pick up its slaves
|
|
for j in `cat /sys/class/net/$dev/bonding/slaves`
|
|
do
|
|
handlenetdev $j
|
|
done
|
|
echo "BUS_ID=\"Bonding\"" >> $MNTIMAGE/etc/ifcfg-$dev
|
|
;;
|
|
*)
|
|
|
|
if [ "$VLAN" == "yes" ]
|
|
then
|
|
#put code to handle vlan devices
|
|
echo "BUS_ID=\"Vlan\"" >> $MNTIMAGE/etc/ifcfg-$dev
|
|
#now make sure we pick up the driver to support the
|
|
#underlying interface
|
|
BASE_IFC=`echo $dev | cut -d"." -f1`
|
|
handlenetdev $BASE_IFC
|
|
else
|
|
BUS_ID=`ls -l /sys/class/net/$dev/device | sed -e's/\(.*\/\)\(.*$\)/\2/'`
|
|
echo "BUS_ID=\"$BUS_ID\"" >> $MNTIMAGE/etc/ifcfg-$dev
|
|
fi
|
|
;;
|
|
esac
|
|
}
|
|
|
|
while [ $# -gt 0 ]; do
|
|
case $1 in
|
|
--fstab*)
|
|
if echo $1 | grep -q '=' ; then
|
|
fstab=`echo $1 | sed 's/^--fstab=//'`
|
|
else
|
|
fstab=$2
|
|
shift
|
|
fi
|
|
;;
|
|
|
|
--with-usb)
|
|
withusb=yes
|
|
;;
|
|
|
|
--without-usb)
|
|
withusb=no
|
|
;;
|
|
|
|
--with*)
|
|
if echo $1 | grep -q '=' ; then
|
|
modname=`echo $1 | sed 's/^--with=//'`
|
|
else
|
|
modname=$2
|
|
shift
|
|
fi
|
|
|
|
basicmodules="$basicmodules $modname"
|
|
;;
|
|
|
|
--builtin*)
|
|
if echo $1 | grep -q '=' ; then
|
|
modname=`echo $1 | sed 's/^--builtin=//'`
|
|
else
|
|
modname=$2
|
|
shift
|
|
fi
|
|
builtins="$builtins $modname"
|
|
;;
|
|
|
|
--version)
|
|
echo "$cmdname: version $VERSION"
|
|
exit 0
|
|
;;
|
|
|
|
-v)
|
|
verbose=-v
|
|
;;
|
|
|
|
--nocompress)
|
|
compress=""
|
|
;;
|
|
|
|
--ifneeded)
|
|
# legacy
|
|
;;
|
|
|
|
-f)
|
|
force=1
|
|
;;
|
|
|
|
-d)
|
|
KDUMP_CONFIG_FILE=""
|
|
if [ -f /etc/kdump.conf ]; then
|
|
KDUMP_CONFIG_FILE="/etc/kdump.conf"
|
|
fi
|
|
;;
|
|
|
|
--preload*)
|
|
if echo $1 | grep -q '=' ; then
|
|
modname=`echo $1 | sed 's/^--preload=//'`
|
|
else
|
|
modname=$2
|
|
shift
|
|
fi
|
|
PREMODS="$PREMODS $modname"
|
|
;;
|
|
--force-scsi-probe)
|
|
forcescsi=1
|
|
;;
|
|
--omit-scsi-modules)
|
|
PRESCSIMODS=""
|
|
noscsi=1
|
|
;;
|
|
--force-raid-probe)
|
|
forceraid=1
|
|
;;
|
|
--omit-raid-modules)
|
|
noraid=1
|
|
;;
|
|
--force-lvm-probe)
|
|
forcelvm=1
|
|
;;
|
|
--omit-lvm-modules)
|
|
nolvm=1
|
|
;;
|
|
--omit-dmraid)
|
|
nodmraid=1
|
|
;;
|
|
--force-ide-probe)
|
|
forceide=1
|
|
;;
|
|
--image-version)
|
|
img_vers=yes
|
|
;;
|
|
--allow-missing)
|
|
allowmissing=yes
|
|
;;
|
|
--noresume)
|
|
noresume=1
|
|
;;
|
|
--help)
|
|
usage -n
|
|
;;
|
|
*)
|
|
if [ -z "$target" ]; then
|
|
target=$1
|
|
elif [ -z "$kernel" ]; then
|
|
kernel=$1
|
|
else
|
|
usage
|
|
fi
|
|
;;
|
|
esac
|
|
|
|
shift
|
|
done
|
|
|
|
if [ -z "$target" -o -z "$kernel" ]; then
|
|
usage
|
|
fi
|
|
|
|
if [ -n "$img_vers" ]; then
|
|
target="$target-$kernel"
|
|
fi
|
|
|
|
if [ -z "$force" -a -f $target ]; then
|
|
error "$target already exists."
|
|
exit 1
|
|
fi
|
|
|
|
if [ -n "$forcescsi" -a -n "$noscsi" ]; then
|
|
error "Can't both force scsi probe and omit scsi modules"
|
|
exit 1
|
|
fi
|
|
|
|
if [ -n "$forceraid" -a -n "$noraid" ]; then
|
|
error "Can't both force raid probe and omit raid modules"
|
|
exit 1
|
|
fi
|
|
|
|
if [ -n "$forcelvm" -a -n "$nolvm" ]; then
|
|
error "Can't both force LVM probe and omit LVM modules"
|
|
exit 1
|
|
fi
|
|
|
|
if [ ! -d /lib/modules/$kernel ]; then
|
|
error 'No modules available for kernel "'${kernel}'".'
|
|
exit 1
|
|
fi
|
|
|
|
if [ $UID != 0 ]; then
|
|
error "$cmdname must be run as root."
|
|
exit 1
|
|
fi
|
|
|
|
vecho "Creating initramfs"
|
|
modulefile=/etc/modprobe.conf
|
|
|
|
# find a temporary directory which doesn't use tmpfs
|
|
TMPDIR=""
|
|
for t in /tmp /var/tmp /root ${PWD}; do
|
|
if [ ! -d $t ]; then continue; fi
|
|
|
|
fs=$(df -T $t 2>/dev/null | awk '{line=$1;} END {printf $2;}')
|
|
if [ "$fs" != "tmpfs" ]; then
|
|
TMPDIR=$t
|
|
break
|
|
fi
|
|
done
|
|
|
|
if [ -z "$TMPDIR" ]; then
|
|
error "no temporary directory could be found."
|
|
exit 1
|
|
fi
|
|
|
|
if [ $TMPDIR = "/root" -o $TMPDIR = "${PWD}" ]; then
|
|
error "WARNING: using $TMPDIR for temporary files"
|
|
fi
|
|
|
|
for n in $PREMODS; do
|
|
findmodule $n
|
|
done
|
|
|
|
needusb=""
|
|
if [ -n "$withusb" -a "x$PROBE" == "xyes" ]; then
|
|
# If / or /boot is on a USB device include the driver. With root by
|
|
# label we could still get some odd behaviors
|
|
for fs in / /boot ; do
|
|
esc=$(echo $fs | sed 's,/,\\/,g')
|
|
dev=$(mount | awk "/ on ${esc} / { print \$1 }" | sed 's/[0-9]*$//' | cut -d/ -f3)
|
|
if [ "$(echo $dev | cut -c1-2)" = sd ]; then
|
|
if [ `which kudzu 2>/dev/null` ]; then
|
|
host=$(kudzu --probe -b scsi |
|
|
gawk '/^device: '${dev}'/,/^host:/ { if (/^host/) { print $2; exit; } }')
|
|
if [ -d /proc/scsi/usb-storage-${host} -o -f /proc/scsi/usb-storage/${host} ]; then
|
|
needusb=1
|
|
fi
|
|
fi
|
|
fi
|
|
done
|
|
fi
|
|
|
|
if [ -n "$needusb" -a "x$PROBE" == "xyes" ]; then
|
|
drivers=$(awk '/^alias[[:space:]]+usb-controller[0-9]* / { print $3}' < $modulefile)
|
|
useUSB=0
|
|
if [ -n "$drivers" ]; then
|
|
useUSB=1
|
|
for driver in $drivers; do
|
|
findmodule $driver
|
|
done
|
|
fi
|
|
for x in $(grep ^[eou]hci_hcd /proc/modules | awk '{ print $1 }' | tac) ; do
|
|
useUSB=1
|
|
findmodule $(echo $x | sed 's/_/-/')
|
|
done
|
|
if [ "$useUSB" == "1" ]; then
|
|
findmodule scsi_mod
|
|
findmodule sd_mod
|
|
findmodule usb-storage
|
|
fi
|
|
fi
|
|
|
|
if [ -n "$forcescsi" -o -z "$noscsi" -a "x$PROBE" == "xyes" ]; then
|
|
if [ ! -f $modulefile ]; then
|
|
modulefile=/etc/conf.modules
|
|
fi
|
|
|
|
if [ -f $modulefile ]; then
|
|
scsimodules=`grep "alias[[:space:]]\+scsi_hostadapter" $modulefile | grep -v '^[ ]*#' | LC_ALL=C sort -u | awk '{ print $3 }'`
|
|
|
|
if [ -n "$scsimodules" ]; then
|
|
for n in $scsimodules; do
|
|
# for now allow scsi modules to come from anywhere. There are some
|
|
# RAID controllers with drivers in block/
|
|
findmodule $n
|
|
done
|
|
fi
|
|
fi
|
|
fi
|
|
|
|
# If we have ide devices and module ide, do the right thing
|
|
ide=/proc/ide/ide*
|
|
if [ -n "$forceide" -o -n "$ide" -a "x$PROBE" == "xyes" ]; then
|
|
findmodule -ide-disk
|
|
fi
|
|
|
|
# If we have dasd devices, include the necessary modules (S/390)
|
|
if [ "x$PROBE" == "xyes" -a -d /proc/dasd ]; then
|
|
findmodule -dasd_mod
|
|
findmodule -dasd_eckd_mod
|
|
findmodule -dasd_fba_mod
|
|
fi
|
|
|
|
if [ "x$PROBE" == "xyes" ]; then
|
|
rootfs=$(awk '{ if ($1 !~ /^[ \t]*#/ && $2 == "/") { print $3; }}' $fstab)
|
|
rootopts=$(awk '{ if ($1 !~ /^[ \t]*#/ && $2 == "/") { print $4; }}' $fstab)
|
|
|
|
# in case the root filesystem is modular
|
|
findmodule -${rootfs}
|
|
|
|
rootdev=$(awk '/^[ \t]*[^#]/ { if ($2 == "/") { print $1; }}' $fstab)
|
|
# check if it's nfsroot
|
|
if [ "$rootfs" == "nfs" ]; then
|
|
remote=$(echo $rootdev | cut -d : -f 1)
|
|
# FIXME: this doesn't handle ips properly
|
|
remoteip=$(getent hosts $remote | cut -d ' ' -f 1)
|
|
netdev=`/sbin/ip route get to $remoteip |sed 's|.*dev \(.*\).*|\1|g' |awk {'print $1;'} |head -n 1`
|
|
net_list="$net_list $netdev"
|
|
# check if it's root by label
|
|
elif echo $rootdev | cut -c1-6 | grep -q "UUID=\|LABEL=" ; then
|
|
dev=`/sbin/findfs $rootdev | sed -e's/\(.*\/\)\(.*$\)/\2/' -e's/[0-9]\+//'`
|
|
if [ -n "$dev" ] ; then
|
|
vecho "Found root device $dev for $rootdev"
|
|
rootdev=$dev
|
|
fi
|
|
else
|
|
rootopts=$(echo $rootopts | sed -e 's/^r[ow],//' -e 's/,r[ow],$//' -e 's/,r[ow],/,/' \
|
|
-e 's/^r[ow]$/defaults/' -e 's/$/,ro/')
|
|
fi
|
|
[ "$rootfs" != "nfs" ] && handlelvordev $rootdev
|
|
|
|
fi
|
|
|
|
# If we use LVM or dm-based raid, include dm-mod
|
|
# XXX: dm not really supported yet.
|
|
testdm=""
|
|
[ -n "$vg_list" ] && testdm="yes"
|
|
[ -n "$forceraid" -o -n "$forcelvm" ] && testdm="yes"
|
|
[ -z "$nolvm" -o -z "$noraid" ] && testdm="yes"
|
|
[ "x$PROBE" != "xyes" ] && testdm=""
|
|
|
|
if [ -n "$testdm" ]; then
|
|
if [ -x /sbin/dmsetup -a -e /dev/mapper/control ]; then
|
|
dmout=$(/sbin/dmsetup ls 2>/dev/null)
|
|
if [ "$dmout" != "No devices found" -a "$dmout" != "" ]; then
|
|
findmodule -dm-mod
|
|
|
|
# DM requires all of these to be there in case someone used the
|
|
# feature. broken. (#132001)
|
|
findmodule -dm-mirror
|
|
findmodule -dm-zero
|
|
findmodule -dm-snapshot
|
|
fi
|
|
fi
|
|
if [ -x /sbin/dmraid -a -z "$nodmraid" ]; then
|
|
for raid in $(/sbin/dmraid -s -craidname 2>/dev/null | grep -vi "no raid disks" ) ; do
|
|
dmname=$(resolve_dm_name $raid)
|
|
if [ -n "$dmname" ]; then
|
|
DMRAIDS="$DMRAIDS $dmname"
|
|
fi
|
|
done
|
|
fi
|
|
fi
|
|
|
|
for n in $basicmodules; do
|
|
findmodule $n
|
|
done
|
|
|
|
for n in $CONFMODS; do
|
|
findmodule $n
|
|
done
|
|
|
|
vecho "Using modules:$MODULES"
|
|
|
|
MNTIMAGE=`mktemp -d ${TMPDIR}/initrd.XXXXXX`
|
|
IMAGE=`mktemp ${TMPDIR}/initrd.img.XXXXXX`
|
|
RCFILE=$MNTIMAGE/init
|
|
|
|
cemit()
|
|
{
|
|
cat >> $RCFILE
|
|
}
|
|
|
|
emit()
|
|
{
|
|
NONL=""
|
|
if [ "$1" == "-n" ]; then
|
|
NONL="-n"
|
|
shift
|
|
fi
|
|
echo $NONL "$@" >> $RCFILE
|
|
}
|
|
|
|
emitdm()
|
|
{
|
|
vecho "Adding dm map \"$1\""
|
|
UUID=$(dm_get_uuid "$1")
|
|
if [ -n "$UUID" ]; then
|
|
UUID="--uuid $UUID"
|
|
fi
|
|
emit "echo \"$(/sbin/dmsetup table $1)\" | /sbin/dmsetup create \"$1\" $UUID"
|
|
}
|
|
|
|
emitdms()
|
|
{
|
|
[ -z "$MPATHS" -a -z "$DMRAIDS" ] && return 0
|
|
echo dm list $MPATHS $DMRAIDS | nash --force --quiet | \
|
|
while read ACTION NAME ; do
|
|
case $ACTION in
|
|
rmparts)
|
|
emit rmparts "$NAME"
|
|
;;
|
|
create)
|
|
emitdm "$NAME"
|
|
;;
|
|
part)
|
|
emit /sbin/kpartx -pp -a \"/dev/mapper/$NAME\"
|
|
;;
|
|
esac
|
|
done
|
|
}
|
|
|
|
if [ -z "$MNTIMAGE" -o -z "$IMAGE" ]; then
|
|
error "Error creating temporaries. Try again"
|
|
exit 1
|
|
fi
|
|
|
|
|
|
#START BUILDING INITRD HERE
|
|
mkdir -p $MNTIMAGE
|
|
mkdir -p $MNTIMAGE/lib
|
|
mkdir -p $MNTIMAGE/bin
|
|
mkdir -p $MNTIMAGE/etc
|
|
mkdir -p $MNTIMAGE/dev
|
|
mkdir -p $MNTIMAGE/proc
|
|
mkdir -p $MNTIMAGE/sys
|
|
mkdir -p $MNTIMAGE/tmp
|
|
mkdir -p $MNTIMAGE/sysroot
|
|
mkdir -p $MNTIMAGE/modules
|
|
mkdir -p $MNTIMAGE/usr/share/udhcpc
|
|
mkdir -p $MNTIMAGE/var/run
|
|
mkdir -p $MNTIMAGE/etc/network/if-pre-up.d
|
|
mkdir -p $MNTIMAGE/etc/network/if-up.d
|
|
mkdir -p $MNTIMAGE/etc/network/if-pre-down.d
|
|
mkdir -p $MNTIMAGE/etc/network/if-down.d
|
|
mkdir -p $MNTIMAGE/etc/network/if-post-down.d
|
|
ln -s bin $MNTIMAGE/sbin
|
|
|
|
if [ -n "$KDUMP_CONFIG_FILE" ]; then
|
|
while read config_opt config_val; do
|
|
|
|
case "$config_opt" in
|
|
net)
|
|
#grab remote host and xlate into numbers
|
|
rhost=`echo $config_val | sed 's/.*@//' | cut -d':' -f1`
|
|
USE_SSH=`echo $config_val | grep @`
|
|
if [ -n "$USE_SSH" ]; then
|
|
USING_METHOD="ssh"
|
|
else
|
|
USING_METHOD="nfs"
|
|
fi
|
|
need_dns=`echo $rhost|grep [a-zA-Z]`
|
|
[ -n "$need_dns" ] && rhost=`getent hosts $rhost|cut -d' ' -f1`
|
|
|
|
#find ethernet device used to route to remote host, ie eth0
|
|
netdev=`/sbin/ip route get to $rhost 2>&1`
|
|
[ $? != 0 ] && echo "Bad kdump location: $config_val" && exit 1
|
|
#the field in the ip output changes if we go to another subnet
|
|
OFF_SUBNET=`echo $netdev | grep via`
|
|
if [ -n "$OFF_SUBNET" ]
|
|
then
|
|
# we are going to a different subnet
|
|
netdev=`echo $netdev|awk '{print $5;}'|head -n 1`
|
|
else
|
|
# we are on the same subnet
|
|
netdev=`echo $netdev|awk '{print $3}'|head -n 1`
|
|
fi
|
|
|
|
#add the ethernet device to the list of modules
|
|
mkdir -p $MNTIMAGE/etc/network/
|
|
handlenetdev $netdev
|
|
echo $netdev >> $MNTIMAGE/etc/iface_to_activate
|
|
|
|
#load nfs modules, if needed
|
|
echo $config_val | grep -v "@" > /dev/null && findmodule nfs
|
|
;;
|
|
raw)
|
|
USING_METHOD="raw"
|
|
if (echo $config_val | egrep -q "^(LABEL|UUID)="); then
|
|
config_val=$(findfs $config_val)
|
|
fi
|
|
handlelvordev $config_val
|
|
;;
|
|
core_collector)
|
|
if [ -x /sbin/makedumpfile ]; then
|
|
CORE_COLLECTOR=$config_val
|
|
grep -q control_d /proc/xen/capabilities 2>/dev/null
|
|
if [ $? -eq 0 ]
|
|
then
|
|
if [ -e /sys/kernel/vmcoreinfo ]
|
|
then
|
|
CORE_COLLECTOR=`echo $CORE_COLLECTOR | sed -e's/makedumpfile/makedumpfile --message-level 1/'`
|
|
else
|
|
CORE_COLLECTOR=`echo $CORE_COLLECTOR | sed -e's/makedumpfile/makedumpfile --xen-vmcoreinfo \/etc\/makedumpfile.config --message-level 1/'`
|
|
fi
|
|
else
|
|
if [ -e /sys/kernel/vmcoreinfo ]
|
|
then
|
|
CORE_COLLECTOR=`echo $CORE_COLLECTOR | sed -e's/makedumpfile/makedumpfile --message-level 1/'`
|
|
else
|
|
CORE_COLLECTOR=`echo $CORE_COLLECTOR | sed -e's/makedumpfile/makedumpfile -i \/etc\/makedumpfile.config --message-level 1/'`
|
|
fi
|
|
fi
|
|
else
|
|
echo "Cannot use the core_collector option on this arch"
|
|
rm -rf $MNTIMAGE
|
|
rm -rf $IMAGE
|
|
rm -f $TMPDISKLIST
|
|
exit 1
|
|
fi
|
|
;;
|
|
path)
|
|
SAVE_PATH=$config_val
|
|
;;
|
|
link_delay)
|
|
LINK_DELAY=$config_val
|
|
;;
|
|
kdump_post)
|
|
KDUMP_POST=$config_val
|
|
if [ ! -x "$KDUMP_POST" ]; then
|
|
echo "$KDUMP_POST not executable or not found"
|
|
exit 1
|
|
fi
|
|
bin="$bin $KDUMP_POST"
|
|
KDUMP_POST_INTERNAL=`echo $KDUMP_POST | sed -e's/\(^.*\/\)\(.*$\)/\/bin\/\2/'`
|
|
;;
|
|
kdump_pre)
|
|
KDUMP_PRE=$config_val
|
|
if [ ! -x "$KDUMP_PRE" ]; then
|
|
echo "$KDUMP_PRE not executable or not found"
|
|
exit 1
|
|
fi
|
|
bin="$bin $KDUMP_PRE"
|
|
KDUMP_PRE_INTERNAL=`echo $KDUMP_PRE | sed -e's/\(^.*\/\)\(.*$\)/\/bin\/\2/'`
|
|
;;
|
|
extra_bins)
|
|
bin="$bin $config_val"
|
|
;;
|
|
extra_modules)
|
|
extra_kdump_mods="$extra_kdump_mods $config_val"
|
|
;;
|
|
default)
|
|
DEFAULT_ACTION=$config_val
|
|
case $DEFAULT_ACTION in
|
|
reboot|shell)
|
|
FINAL_ACTION="reboot -f"
|
|
;;
|
|
halt)
|
|
FINAL_ACTION="halt -f"
|
|
;;
|
|
esac
|
|
;;
|
|
disk_timeout)
|
|
DISK_TIMEOUT=$config_val
|
|
;;
|
|
*)
|
|
IS_COMMENT=`echo $config_opt | grep ^#.*$`
|
|
if [ -n "$IS_COMMENT" -o -z "$config_val" ]
|
|
then
|
|
#don't process comments or blank line
|
|
continue
|
|
fi
|
|
USING_METHOD="filesystem"
|
|
if (echo $config_val | egrep -q "^(LABEL|UUID)="); then
|
|
config_val=$(findfs $config_val)
|
|
fi
|
|
handlelvordev $config_val
|
|
;;
|
|
esac
|
|
|
|
done < $KDUMP_CONFIG_FILE
|
|
fi
|
|
|
|
#if we are using makedumpfile here, then generate the config file
|
|
#also only build this config if we don't have vmcoreinfo on this kernel
|
|
if [ -n "$CORE_COLLECTOR" -a ! -e /sys/kernel/vmcoreinfo ]; then
|
|
if [ -z "$USING_METHOD" ]
|
|
then
|
|
echo "Warning! Lack of dump target specification means core_collector option is ignored!"
|
|
CORE_COLLECTOR=""
|
|
else
|
|
RUN_KERN_VER=`uname -r`
|
|
if [ ! -f /usr/lib/debug/lib/modules/$RUN_KERN_VER/vmlinux ]
|
|
then
|
|
echo "kernel-debuginfo-$RUN_KERN_VER is not installed. You need this to use makedumpfile!"
|
|
echo "please install it and restart the kdump service"
|
|
rm -rf $MNTIMAGE
|
|
rm -rf $IMAGE
|
|
rm -f $TMPDISKLIST
|
|
exit 1
|
|
fi
|
|
XEN_OPTS=""
|
|
grep -q control_d /proc/xen/capabilities 2>/dev/null
|
|
if [ $? -eq 0 ]
|
|
then
|
|
# This is a dom0 xen kernel so we need to add xen-syms to the
|
|
# makedumpefile config
|
|
RUN_XEN_VER=${RUN_KERN_VER%xen}
|
|
if [ ! -f /usr/lib/debug/boot/xen-syms-$RUN_XEN_VER.debug ]
|
|
then
|
|
echo "xen-syms.debug not found and is needed on this kernel to use makedumpfile!"
|
|
echo "please install it and restart the kdump service"
|
|
rm -rf $MNTIMAGE
|
|
rm -rf $IMAGE
|
|
rm -f $TMPDISKLIST
|
|
exit 1
|
|
fi
|
|
|
|
XEN_OPTS="--xen-syms /usr/lib/debug/boot/xen-syms-$RUN_XEN_VER.debug"
|
|
/sbin/makedumpfile -g $MNTIMAGE/etc/makedumpfile.config $XEN_OPTS > /dev/null 2>&1
|
|
else
|
|
/sbin/makedumpfile -g $MNTIMAGE/etc/makedumpfile.config -x /usr/lib/debug/lib/modules/$RUN_KERN_VER/vmlinux > /dev/null 2>&1
|
|
fi
|
|
if [ $? != 0 ]; then
|
|
echo "could not generate makedumpfile configuration. aborting"
|
|
rm -rf $MNTIMAGE
|
|
rm -rf $IMAGE
|
|
rm -f $TMPDISKLIST
|
|
exit 1;
|
|
fi
|
|
fi
|
|
fi
|
|
|
|
#include extra user-specified modules for kdump initrd
|
|
for n in $extra_kdump_mods; do
|
|
findmodule $n
|
|
done
|
|
|
|
if [ -z "$FINAL_ACTION" ]; then
|
|
FINAL_ACTION="reboot -f"
|
|
else
|
|
if [ -z "$USING_METHOD" ]; then
|
|
echo "Warning! Lack of dump target specification means default option is ignored!"
|
|
DEFAULT_ACTION=""
|
|
FINAL_ACTION="reboot -f"
|
|
fi
|
|
fi
|
|
|
|
#copy in busybox and make symlinks to its supported utilities
|
|
cp /sbin/busybox $MNTIMAGE/sbin/busybox
|
|
bin="$bin /sbin/busybox"
|
|
cd $MNTIMAGE/sbin
|
|
for i in `/sbin/busybox |
|
|
awk 'BEGIN {found=0} /.*/ { if (found) print $0 } /Currently/ {found=1}' |
|
|
sed -e's/,//g' -e's/busybox//g'`
|
|
do
|
|
ln -s busybox $MNTIMAGE/sbin/$i
|
|
done
|
|
cd - > /dev/null 2>&1
|
|
|
|
if [ -f /etc/mdadm.conf ]
|
|
then
|
|
cp /etc/mdadm.conf $MNTIMAGE/etc
|
|
bin="$bin /sbin/mdadm"
|
|
for i in `cat /etc/mdadm.conf | grep ARRAY | sed -e's/\(^.*level=\)\(.*$\)/\2/' | cut -d" " -f1`
|
|
do
|
|
findmodule $i
|
|
done
|
|
fi
|
|
|
|
#this provides us with a list of disks that we need to make sure we have available before we capture our core
|
|
mv $TMPDISKLIST $MNTIMAGE/etc/critical_disks
|
|
|
|
#THIS IS WHERE WE GENERATE OUR ADDITINONAL UTILITIES
|
|
#Busybox doesn't have a /bin/sh applet,
|
|
#so we build a reasonable faximilie here
|
|
cat >> $MNTIMAGE/bin/sh << EOF
|
|
#!/bin/msh
|
|
#drop the -c from the command line
|
|
shift 1
|
|
#now execute the passed command
|
|
#don't exec this or $@ won't work
|
|
/bin/msh -c "\$@"
|
|
EOF
|
|
|
|
chmod 755 $MNTIMAGE/bin/sh
|
|
|
|
cat >> $MNTIMAGE/usr/share/udhcpc/default.script << EOF
|
|
#!/bin/msh
|
|
[ -z "\$1" ] && echo "Error: should be called from udhcpc" && exit 1
|
|
|
|
|
|
case "\$1" in
|
|
deconfig)
|
|
/sbin/ifconfig \$interface 0.0.0.0
|
|
;;
|
|
|
|
renew|bound)
|
|
/sbin/ifconfig \$interface \$ip netmask \$subnet
|
|
|
|
if [ -n "\$router" ] ; then
|
|
echo "deleting routers"
|
|
while route del default gw 0.0.0.0 dev \$interface ; do
|
|
:
|
|
done
|
|
|
|
for i in \$router ; do
|
|
route add default gw \$i dev \$interface
|
|
done
|
|
fi
|
|
|
|
echo -n > /etc/resolv.conf
|
|
[ -n "\$domain" ] && echo search $domain >> /etc/resolv.conf
|
|
for i in \$dns ; do
|
|
echo adding dns \$i
|
|
echo nameserver \$i >> /etc/resolv.conf
|
|
done
|
|
;;
|
|
esac
|
|
|
|
exit 0
|
|
EOF
|
|
|
|
#NETWORKING SCRIPT DIRECTORIES
|
|
cat >> $MNTIMAGE/etc/network/if-pre-up.d/pre-up-script << EOF
|
|
#!/bin/msh
|
|
PATH=\$PATH:/scriptfns
|
|
. /etc/ifcfg-\$IFACE
|
|
|
|
LINK_DELAY=$LINK_DELAY
|
|
if [ "\$BUS_ID" != "Vlan" ]
|
|
then
|
|
ifconfig \$IFACE up
|
|
if [ -n "\$LINK_DELAY" ]
|
|
then
|
|
echo "\$IFACE Link Up. Waiting \$LINK_DELAY Seconds"
|
|
sleep \$LINK_DELAY
|
|
echo "Continuing"
|
|
fi
|
|
fi
|
|
|
|
if [ "\$BUS_ID" == "Bonding" ]
|
|
then
|
|
#this is a bond find and bring up the slaves
|
|
echo searching for slaves
|
|
find_activate_slaves \$IFACE
|
|
elif [ "\$BUS_ID" == "Vlan" ]
|
|
then
|
|
#bring up the base interface first
|
|
BASE_DEV=\`echo \$IFACE | cut -d"." -f1\`
|
|
VLAN_ID=\`echo \$IFACE | cut -d"." -f2\`
|
|
ifconfig \$BASE_DEV up
|
|
if [ -n "\$LINK_DELAY" ]
|
|
then
|
|
echo "\$IFACE Link Up. Waiting \$LINK_DELAY Seconds"
|
|
sleep \$LINK_DELAY
|
|
echo "Continuing"
|
|
fi
|
|
vconfig add \$BASE_DEV \$VLAN_ID
|
|
ifconfig \$IFACE up
|
|
fi
|
|
exit 0
|
|
EOF
|
|
|
|
for i in `ls $MNTIMAGE/etc/network/if-pre-up.d`
|
|
do
|
|
chmod 755 $MNTIMAGE/etc/network/if-pre-up.d/$i
|
|
done
|
|
|
|
cat >> $MNTIMAGE/etc/network/if-up.d/up-script << EOF
|
|
#!/bin/msh
|
|
PATH=\$PATH:/scriptfns
|
|
if [ "\$METHOD" != "dhcp" ]
|
|
then
|
|
. /etc/ifcfg-\$IFACE
|
|
ifconfig \$IFACE \$IPADDR netmask \$NETMASK
|
|
route add default gw \$GATEWAY dev \$IFACE
|
|
fi
|
|
exit 0
|
|
EOF
|
|
|
|
for i in `ls $MNTIMAGE/etc/network/if-up.d`
|
|
do
|
|
chmod 755 $MNTIMAGE/etc/network/if-up.d/$i
|
|
done
|
|
|
|
chmod 755 $MNTIMAGE/usr/share/udhcpc/default.script
|
|
|
|
# WE DONT HAVE FUNCTIONS AVAILABLE IN MSH
|
|
# SO WE IMPLEMENT THEM HERE AS scripts
|
|
SCRIPTDIR=$MNTIMAGE/scriptfns
|
|
mkdir -p $SCRIPTDIR
|
|
|
|
cat >> $SCRIPTDIR/map_interface << EOF
|
|
#!/bin/msh
|
|
if [ -e /tmp/tmpcnt ]
|
|
then
|
|
TMPCNT=\`cat /tmp/tmpcnt\`
|
|
else
|
|
TMPCNT=0
|
|
fi
|
|
#erase previously recorded map
|
|
RENAMED=""
|
|
REAL_DEV=""
|
|
NETDEV=\$1
|
|
. /etc/ifcfg-\$NETDEV
|
|
for j in \`ifconfig -a | awk '/.*Link encap.*/ {print \$1}'\`
|
|
do
|
|
case "\$BUS_ID" in
|
|
Bonding)
|
|
REAL_DEV=bond0
|
|
RENAMED="yes"
|
|
;;
|
|
Vlan)
|
|
BASE_DEV=\`echo \$NETDEV | cut -d"." -f1\`
|
|
VLAN_ID=\`echo \$NETDEV | cut -d"." -f2\`
|
|
REAL_BASE=\`grep "^\$BASE_DEV " /etc/iface_map | cut -d" " -f2\`
|
|
#Note we add the \ to our vlan values to escape the . for sed-ability
|
|
#Note we also convert . to _ to avoid problems with busybox ifup
|
|
REAL_DEV=\$REAL_BASE\\\\.\$VLAN_ID
|
|
NETDEV=\$BASE_DEV\\\\.\$VLAN_ID
|
|
RENAMED="yes"
|
|
;;
|
|
*)
|
|
INFO=\`ls -l /sys/class/net/\$j/device 2>/dev/null | sed -e's/\\(.*\\/\\)\\(.*$\\)/\\2/'\`
|
|
if [ "\$INFO" == "\$BUS_ID" -a -z "\$REAL_DEV" ]
|
|
then
|
|
REAL_DEV=\$j
|
|
RENAMED="yes"
|
|
fi
|
|
;;
|
|
esac
|
|
done
|
|
|
|
if [ -z "\$RENAMED" ]
|
|
then
|
|
echo "Could not find a mapping for device \$NETDEV"
|
|
exit 1
|
|
fi
|
|
|
|
#build the interface rename map
|
|
echo \$NETDEV \$REAL_DEV tmp\$TMPCNT >> /etc/iface_map
|
|
TMPCNT=\`echo \$TMPCNT 1 + p | dc\`
|
|
echo \$TMPCNT > /tmp/tmpcnt
|
|
echo mapping \$NETDEV to \$REAL_DEV
|
|
EOF
|
|
|
|
cat >> $SCRIPTDIR/rename_interfaces << EOF
|
|
#!/bin/msh
|
|
MAP_COUNT=\`wc -l /etc/iface_map | cut -d" " -f7 \`
|
|
#now do all the renaming - first to temp space
|
|
for j in \`seq 1 1 \$MAP_COUNT\`
|
|
do
|
|
CURRENT=\`awk -v MATCH=\$j '{if (NR == MATCH) print \$1}' /etc/iface_map\`
|
|
NEW=\`awk -v MATCH=\$j '{if (NR == MATCH) print \$2}' /etc/iface_map\`
|
|
INTERIM=\`awk -v MATCH=\$j '{if (NR == MATCH) print \$3}' /etc/iface_map\`
|
|
mv /etc/ifcfg-\$CURRENT /etc/ifcfg-\$INTERIM
|
|
for i in /etc/ifcfg-\$INTERIM /etc/iface_to_activate /etc/network/interfaces
|
|
do
|
|
# the double quotes lets us expand the variables
|
|
sed -e"s/\$CURRENT/\$INTERIM/g" \$i > \$i.tmp
|
|
mv \$i.tmp \$i
|
|
done
|
|
done
|
|
|
|
|
|
for j in \`seq 1 1 \$MAP_COUNT\`
|
|
do
|
|
CURRENT=\`awk -v MATCH=\$j '{if (NR == MATCH) print \$1}' /etc/iface_map\`
|
|
NEW=\`awk -v MATCH=\$j '{if (NR == MATCH) print \$2}' /etc/iface_map\`
|
|
INTERIM=\`awk -v MATCH=\$j '{if (NR == MATCH) print \$3}' /etc/iface_map\`
|
|
mv /etc/ifcfg-\$INTERIM /etc/ifcfg-\$NEW
|
|
for i in /etc/ifcfg-\$NEW /etc/iface_to_activate /etc/network/interfaces
|
|
do
|
|
# the double quotes lets us expand the variables
|
|
sed -e"s/\$INTERIM/\$NEW/g" \$i > \$i.tmp
|
|
mv \$i.tmp \$i
|
|
done
|
|
done < /etc/iface_map
|
|
|
|
exit 0
|
|
EOF
|
|
|
|
cat >> $SCRIPTDIR/find_activate_slaves << EOF
|
|
#!/bin/msh
|
|
BOND_MASTER=\$1
|
|
|
|
for j in \`ifconfig -a | awk '/.*Link encap.*/ {print \$1}'\`
|
|
do
|
|
MASTER=""
|
|
. /etc/ifcfg-\$j
|
|
if [ "\$MASTER" == "\$BOND_MASTER" ]
|
|
then
|
|
#this is a slave of the rising interface
|
|
echo enslaving \$j to \$BOND_MASTER
|
|
echo +\$j > /sys/class/net/\$BOND_MASTER/bonding/slaves
|
|
fi
|
|
done
|
|
EOF
|
|
|
|
cat >> $SCRIPTDIR/monitor_dd_progress << EOF
|
|
#!/bin/msh
|
|
SRC_FILE_SIZE=\`ls -l /proc/vmcore | awk '{print \$5}'\`
|
|
BLOCK_SIZE=\$1
|
|
SRC_FILE_MB=\`dc \$SRC_FILE_SIZE 1048576 / p\`
|
|
|
|
while true
|
|
do
|
|
DD_PID=\`ps | grep -v awk | awk '/dd/ {print \$1}'\`
|
|
if [ -n "\$DD_PID" ]
|
|
then
|
|
break
|
|
fi
|
|
done
|
|
|
|
while true
|
|
do
|
|
sleep 5
|
|
if [ ! -d /proc/\$CP_PID ]
|
|
then
|
|
break
|
|
fi
|
|
|
|
kill -SIGUSR1 \$DD_PID
|
|
CURRENT_SIZE=\`tail -n 1 /tmp/dd_progress_file | sed "s/[^0-9].*//g"\`
|
|
CURRENT_MB=\`dc \$CURRENT_SIZE \$BLOCK_SIZE \* 1048576 / p\`
|
|
echo -n -e "Copied \$CURRENT_MB MB / \$SRC_FILE_MB MB\\\r"
|
|
done
|
|
|
|
rm -f /tmp/dd_progres_file
|
|
EOF
|
|
|
|
cat >> $SCRIPTDIR/monitor_scp_progress << EOF
|
|
#!/bin/msh
|
|
SRC_FILE_SIZE=\`ls -l /proc/vmcore | awk '{print \$5}'\`
|
|
LOCATION=\$1
|
|
REMOTE_FILE=\$2
|
|
|
|
SRC_FILE_MB=\`dc \$SRC_FILE_SIZE 1048576 / p\`
|
|
|
|
while true
|
|
do
|
|
SCP_PID=\`ps | grep -v awk | awk '/scp/ {print \$1}'\`
|
|
if [ -n "\$SCP_PID" ]
|
|
then
|
|
break
|
|
fi
|
|
done
|
|
|
|
while true
|
|
do
|
|
sleep 5
|
|
if [ ! -d /proc/\$SCP_PID ]
|
|
then
|
|
break
|
|
fi
|
|
|
|
SSH_OUTPUT=\`ssh -q -o BatchMode=yes -o StrictHostKeyChecking=no \$LOCATION ls -l \$REMOTE_FILE\`
|
|
REMOTE_SIZE=\`echo \$SSH_OUTPUT | awk '{print \$5}'\`
|
|
REMOTE_SIZE_MB=\`dc \$REMOTE_SIZE 1048576 / p\`
|
|
echo -n -e "Copied \$REMOTE_SIZE_MB MB / \$SRC_FILE_MB MB\\\r"
|
|
done
|
|
|
|
EOF
|
|
|
|
cat >> $SCRIPTDIR/monitor_cp_progress <<EOF
|
|
#!/bin/msh
|
|
SRC_FILE_SIZE=\`ls -l /proc/vmcore | awk '{print \$5}'\`
|
|
DST_FILE=\$1
|
|
|
|
SRC_FILE_MB=\`dc \$SRC_FILE_SIZE 1048576 / p\`
|
|
|
|
while true
|
|
do
|
|
CP_PID=\`ps | grep -v awk | awk '/cp / {print \$1}'\`
|
|
if [ -n "\$CP_PID" ]
|
|
then
|
|
break
|
|
fi
|
|
done
|
|
|
|
while true
|
|
do
|
|
sleep 5
|
|
if [ ! -d /proc/\$CP_PID ]
|
|
then
|
|
break
|
|
fi
|
|
|
|
LS_SIZE=\`ls -l \$DST_FILE | awk '{print \$5}'\`
|
|
LS_MB=\`dc \$LS_SIZE 1048576 / p\`
|
|
echo -n -e "Copied \$LS_MB MB / \$SRC_FILE_MB MB\\\r"
|
|
done
|
|
|
|
EOF
|
|
|
|
#DONT ADD STUFF to SCRIPTDIR PAST HERE
|
|
for i in `ls $SCRIPTDIR/*`
|
|
do
|
|
chmod 755 $i
|
|
done
|
|
|
|
if [ -e /etc/fstab.sys ]; then
|
|
inst /etc/fstab.sys "$MNTIMAGE/etc/fstab.sys"
|
|
fi
|
|
|
|
#build a good passwd file
|
|
cat >> $MNTIMAGE/etc/passwd << EOF
|
|
root:x:0:0:root:/root:/bin/bash
|
|
EOF
|
|
|
|
for MODULE in $MODULES; do
|
|
if [ -x /usr/bin/strip ]; then
|
|
/usr/bin/strip -g $verbose $MODULE -o $MNTIMAGE/lib/$(basename $MODULE)
|
|
else
|
|
cp $verbose -a $MODULE $MNTIMAGE/lib
|
|
fi
|
|
done
|
|
|
|
# mknod'ing the devices instead of copying them works both with and
|
|
# without devfs...
|
|
mkdir $MNTIMAGE/dev/mapper
|
|
|
|
mknod $MNTIMAGE/dev/ram0 b 1 0
|
|
mknod $MNTIMAGE/dev/ram1 b 1 1
|
|
ln -sf ram1 $MNTIMAGE/dev/ram
|
|
|
|
mknod $MNTIMAGE/dev/null c 1 3
|
|
mknod $MNTIMAGE/dev/zero c 1 5
|
|
mknod $MNTIMAGE/dev/systty c 4 0
|
|
for i in 0 1 2 3 4 5 6 7 8 9 10 11 12 ; do
|
|
mknod $MNTIMAGE/dev/tty$i c 4 $i
|
|
done
|
|
for i in 0 1 2 3 ; do
|
|
mknod $MNTIMAGE/dev/ttyS$i c 4 $(($i + 64))
|
|
done
|
|
mknod $MNTIMAGE/dev/tty c 5 0
|
|
mknod $MNTIMAGE/dev/console c 5 1
|
|
mknod $MNTIMAGE/dev/ptmx c 5 2
|
|
mknod $MNTIMAGE/dev/rtc c 10 135
|
|
if [ "$(uname -m)" == "ia64" ]; then
|
|
mknod $MNTIMAGE/dev/efirtc c 10 136
|
|
fi
|
|
|
|
# FIXME -- this can really go poorly with clvm or duplicate vg names.
|
|
# nash should do lvm probing for us and write its own configs.
|
|
if [ -n "$vg_list" ]; then
|
|
inst /sbin/lvm "$MNTIMAGE/bin/lvm"
|
|
bin="$bin /sbin/lvm"
|
|
if [ -f /etc/lvm/lvm.conf ]; then
|
|
cp $verbose --parents /etc/lvm/lvm.conf $MNTIMAGE/
|
|
fi
|
|
fi
|
|
|
|
echo -n >| $RCFILE
|
|
cat >> $MNTIMAGE/init << EOF
|
|
#!/bin/msh
|
|
export PATH=$PATH:/scriptfns
|
|
mount -t proc /proc /proc
|
|
echo Mounting proc filesystem
|
|
echo Mounting sysfs filesystem
|
|
mount -t sysfs /sys /sys
|
|
echo 1 > /proc/sys/vm/dirty_background_ratio
|
|
echo 5 > /proc/sys/vm/dirty_ratio
|
|
echo 10 > /proc/sys/vm/dirty_writeback_centisecs
|
|
echo 50 > /proc/sys/vm/dirty_expire_centisecs
|
|
echo Creating /dev
|
|
mount -o mode=0755 -t tmpfs /dev /dev
|
|
mkdir /dev/pts
|
|
mount -t devpts -o gid=5,mode=620 /dev/pts /dev/pts
|
|
mkdir /dev/shm
|
|
mkdir /dev/mapper
|
|
echo Creating initial device nodes
|
|
mknod /dev/null c 1 3
|
|
mknod /dev/zero c 1 5
|
|
mknod /dev/systty c 4 0
|
|
mknod /dev/tty c 5 0
|
|
mknod /dev/console c 5 1
|
|
mknod /dev/ptmx c 5 2
|
|
mknod /dev/rtc c 10 135
|
|
mknod /dev/urandom c 1 9
|
|
EOF
|
|
|
|
# XXX really we need to openvt too, in case someting changes the
|
|
# color palette and then changes vts on fbcon before gettys start.
|
|
# (yay, fbcon bugs!)
|
|
for i in 0 1 2 3 4 5 6 7 8 9 10 11 12 ; do
|
|
emit "mknod /dev/tty$i c 4 $i"
|
|
done
|
|
|
|
for i in 0 1 2 3 ; do
|
|
emit "mknod /dev/ttyS$i c 4 $(($i + 64))"
|
|
done
|
|
emit "mknod /dev/mem c 1 1"
|
|
for MODULE in $MODULES; do
|
|
text=""
|
|
module=`echo $MODULE | sed "s|.*/||" | sed "s/.k\?o$//"`
|
|
fullmodule=`echo $MODULE | sed "s|.*/||"`
|
|
|
|
options=`sed -n -e "s/^options[ ][ ]*$module[ ][ ]*//p" $modulefile 2>/dev/null`
|
|
|
|
if [ -n "$options" ]; then
|
|
vecho "Adding module $module$text with options $options"
|
|
else
|
|
vecho "Adding module $module$text"
|
|
fi
|
|
emit "echo \"Loading $fullmodule module\""
|
|
emit "insmod /lib/$fullmodule $options"
|
|
|
|
# Hack - we need a delay after loading usb-storage to give things
|
|
# time to settle down before we start looking a block devices
|
|
if [ "$module" = "usb-storage" ]; then
|
|
emit "echo Waiting 8 seconds for driver initialization."
|
|
emit "sleep 8"
|
|
fi
|
|
if [ "$module" = "zfcp" -a -f /etc/zfcp.conf ]; then
|
|
emit "echo Waiting 2 seconds for driver initialization."
|
|
emit "sleep 2"
|
|
cat /etc/zfcp.conf | grep -v "^#" | tr "A-Z" "a-z" | while read DEVICE SCSIID WWPN SCSILUN FCPLUN; do
|
|
cemit <<EOF
|
|
echo -n $WWPN > /sys/bus/ccw/drivers/zfcp/${DEVICE/0x/}/port_add
|
|
echo -n $FCPLUN > /sys/bus/ccw/drivers/zfcp/${DEVICE/0x/}/$WWPN/unit_add
|
|
echo -n 1 > /sys/bus/ccw/drivers/zfcp/${DEVICE/0x/}/online
|
|
EOF
|
|
done
|
|
fi
|
|
done
|
|
|
|
|
|
# Before we create our block devices, we need to make sure that we have all the needed block devices discovered
|
|
# Thats seems like a chicken and egg problem, I know, but we generated a critcal_disks list when we build this initramfs
|
|
# that tell us what devices we need to wait to see in /sys/block
|
|
|
|
cat >> $MNTIMAGE/init << EOF
|
|
echo "Waiting for required block device discovery"
|
|
timeout_count=0
|
|
for i in \`cat /etc/critical_disks\`
|
|
do
|
|
echo -n Waiting for \$i...
|
|
while [ ! -d /sys/block/\$i ]
|
|
do
|
|
sleep 1
|
|
if [ -n "$DISK_TIMEOUT" -a "\$timeout_count" -ge "$DISK_TIMEOUT" ]
|
|
then
|
|
break 2
|
|
fi
|
|
timeout_count=\`expr \$timeout_count + 1\`
|
|
done
|
|
echo Found
|
|
done
|
|
EOF
|
|
|
|
# HACK: module loading + device creation isn't necessarily synchronous...
|
|
# this will make sure that we have all of our devices before trying
|
|
# things like RAID or LVM
|
|
emit "echo Creating Block Devices"
|
|
emit "mkdir /dev/cciss"
|
|
emit "mkdir /dev/ida"
|
|
emit "for i in \`ls /sys/block\`; do"
|
|
emit " MAJOR_NUM=\`cat /sys/block/\$i/dev | cut -d":" -f1\`"
|
|
emit " MINOR_NUM=\`cat /sys/block/\$i/dev | cut -d":" -f2\`"
|
|
emit " MINOR_RANGE=\`cat /sys/block/\$i/range | cut -d":" -f2\`"
|
|
emit " PART_SEP=''"
|
|
emit " i=\`echo \$i | sed 's/\!/\//g'\`"
|
|
emit " if echo \$i | grep -q '^cciss'; then"
|
|
emit " PART_SEP='p'"
|
|
emit " elif echo \$i | grep -q '^ida'; then"
|
|
emit " PART_SEP='p'"
|
|
emit " fi"
|
|
emit " echo Creating block device \$i"
|
|
emit " mknod /dev/\$i b \$MAJOR_NUM \$MINOR_NUM"
|
|
emit " if [ \"\$MINOR_RANGE\" -gt 1 ]"
|
|
emit " then"
|
|
emit " MINOR_END=\`echo \$MINOR_NUM \$MINOR_RANGE + p | dc\`"
|
|
emit " MINOR_START=\`echo \$MINOR_NUM 1 + p | dc\`"
|
|
emit " PART_NUM=1"
|
|
emit " for j in \`seq \$MINOR_START 1 \$MINOR_END\`"
|
|
emit " do"
|
|
emit " if [ ! -e /dev/\$i\$PART_NUM ]"
|
|
emit " then"
|
|
emit " mknod /dev/\$i\$PART_SEP\$PART_NUM b \$MAJOR_NUM \$j"
|
|
emit " fi"
|
|
emit " PART_NUM=\`expr \$PART_NUM + 1\`"
|
|
emit " done"
|
|
emit " fi"
|
|
emit "done"
|
|
#now do any software raid devices we might have
|
|
emit "if [ -f /etc/mdadm.conf ]"
|
|
emit "then"
|
|
emit " for i in \`awk '/.*ARRAY.*/{print \$2}' /etc/mdadm.conf\`"
|
|
emit " do"
|
|
emit " MD_MIN=\`echo \$i | sed -e's/\(^.*\)\([0-9]\+$\)/\2/'\`"
|
|
emit " mknod \$i b 9 \$MD_MIN"
|
|
emit " done"
|
|
emit "fi"
|
|
|
|
if [ -n "$vg_list" ]; then
|
|
emit "echo Making device-mapper control node"
|
|
emit "DM_MAJ=\`cat /proc/devices | grep misc | cut -d\" \" -f2\`"
|
|
emit "DM_MIN=\`cat /proc/misc | grep device-mapper | cut -d\" \" -f2\`"
|
|
emit "mknod /dev/mapper/control b \$DM_MAJ \$DM_MIN"
|
|
fi
|
|
|
|
if [ -n "$net_list" ]; then
|
|
for netdev in $net_list; do
|
|
emit "echo Bringing up $netdev"
|
|
handle_netdev $netdev
|
|
#emit $network
|
|
done
|
|
fi
|
|
|
|
emitdms
|
|
|
|
if [ -n "$raiddevices" ]; then
|
|
for dev in $raiddevices; do
|
|
cp -a /dev/${dev} $MNTIMAGE/dev
|
|
emit "\#need code here to set up md devs"
|
|
done
|
|
fi
|
|
|
|
emit "if [ -f /etc/mdadm.conf ]"
|
|
emit "then"
|
|
emit " mdadm -A -s"
|
|
emit "fi"
|
|
|
|
if [ -n "$vg_list" ]; then
|
|
emit "echo Scanning logical volumes"
|
|
emit "lvm vgscan --ignorelockingfailure --mknodes"
|
|
emit "echo Activating logical volumes"
|
|
emit "lvm vgchange -a y --ignorelockingfailure"
|
|
emit "DM_NUM=0"
|
|
emit "lvm lvs --noheadings -o lv_name,vg_name | while read i"
|
|
emit "do"
|
|
emit " LV=\`echo \$i | awk '{ print \$1 }'\`"
|
|
emit " VGRP=\`echo \$i | awk '{ print \$2 }'\`"
|
|
emit " mkdir -p /dev/\$VGRP"
|
|
emit " if [ ! -e /dev/\$VGRP/\$LV ]"
|
|
emit " then"
|
|
emit " ln -s /dev/mapper/\$VGRP-\$LV /dev/\$VGRP/\$LV"
|
|
emit " DM_NUM=\`echo \$DM_NUM 1 + p | dc\`"
|
|
emit " if [ -z \"\$noresume\" ]"
|
|
emit " then"
|
|
emit " /sbin/dmsetup resume /dev/mapper/\$VGRP-\$LV"
|
|
emit " fi"
|
|
emit " fi"
|
|
emit "done"
|
|
fi
|
|
|
|
kdump_chk()
|
|
{
|
|
rc=`eval $1` && return $rc
|
|
echo "$KDUMP_CONFIG_FILE: $2"
|
|
exit 1
|
|
}
|
|
|
|
if [ -n "$KDUMP_CONFIG_FILE" ]; then
|
|
memtotal=`cat /proc/meminfo | grep MemTotal | awk '{print $2}'`
|
|
|
|
#timezone info for date which outputs YYYY-MM-DD-hh:mm
|
|
cp /etc/localtime $MNTIMAGE/etc/localtime
|
|
cp /etc/sysconfig/clock $MNTIMAGE/etc
|
|
emit ". /etc/clock"
|
|
emit " if [ \"\$UTC\" == "true" ]"
|
|
emit " then"
|
|
emit " TIME_FORMAT=-u"
|
|
emit " else"
|
|
emit " TIME_FORMAT=-l"
|
|
emit "fi"
|
|
emit "hwclock --hctosys \$TIME_FORMAT"
|
|
emit "DATE=\`date +%Y-%m-%d-%T\`"
|
|
|
|
bin="$bin /sbin/dmsetup /sbin/kpartx"
|
|
|
|
if [ -n "$CORE_COLLECTOR" ]; then
|
|
bin="$bin /sbin/makedumpfile"
|
|
fi
|
|
|
|
#ssh, scp require libraries that aren't found with ldd
|
|
ARCH=`uname -m`
|
|
lib=/lib && [ -d "/lib64" -a "$ARCH" != "ppc64" ] && lib=/lib64
|
|
k_extras="/$lib/libnss_compat.so.2 /$lib/libnss_files.so.2"
|
|
|
|
#traverse the config file and setup each dump location
|
|
while read config_opt config_val; do
|
|
[ -z "$config_opt" ] && continue #skip empty lines
|
|
[ "`echo $config_opt | grep ^# `" ] && continue #skip comments
|
|
kdump_chk "test -n \"$config_val\"" "Need a location for $config_opt"
|
|
|
|
case "$config_opt" in
|
|
\#*) continue;; #skip comments
|
|
|
|
raw)
|
|
#test raw partition
|
|
kdump_chk "dd if=$config_val count=1 of=/dev/null > /dev/null 2>&1" \
|
|
"Bad raw partition $config_val"
|
|
#check for available size is greater than $memtotal
|
|
available_size=$(fdisk -s $config_val)
|
|
if [ $available_size -lt $memtotal ]; then
|
|
echo "Warning: There is not space enough to save a vmcore."
|
|
echo " The size of $config_val should be much greater than $memtotal kilo bytes."
|
|
fi
|
|
|
|
#setup raw case
|
|
if [ -n "$KDUMP_PRE" ]
|
|
then
|
|
emit "$KDUMP_PRE"
|
|
emit "if [ \$? -ne 0 ]"
|
|
emit "then"
|
|
emit " echo kdump_pre script exited with non-zero status"
|
|
emit " $FINAL_ACTION"
|
|
emit "fi"
|
|
fi
|
|
emit "echo Saving to partition $config_val"
|
|
emit "monitor_dd_progress 512 &"
|
|
if [ -z "$CORE_COLLECTOR" ]
|
|
then
|
|
emit "dd if=/proc/vmcore of=$config_val bs=512 >> /tmp/dd_progress_file 2>&1"
|
|
else
|
|
CORE_COLLECTOR=`echo $CORE_COLLECTOR | sed -e's/\(^makedumpfile\)\(.*$\)/\1 -F \2/'`
|
|
emit "$CORE_COLLECTOR /proc/vmcore | dd of=$config_val bs=512 >> /tmp/dd_progress_file 2>&1"
|
|
fi
|
|
emit "exitcode=\$?"
|
|
emit "if [ \$exitcode == 0 ]"
|
|
emit "then"
|
|
emit " echo -e \"\\\033[0JSaving core complete\""
|
|
emit "fi"
|
|
if [ -x "$KDUMP_POST" ]; then
|
|
emit "$KDUMP_POST \$exitcode"
|
|
fi
|
|
emit "[ \$exitcode == 0 ] && $FINAL_ACTION"
|
|
;;
|
|
|
|
net)
|
|
#build an /etc/passwd for scp to work properly
|
|
grep "^root" /etc/passwd > $MNTIMAGE/etc/passwd
|
|
|
|
# bring up the network
|
|
emit "for i in \`ls /etc/ifcfg-*\`"
|
|
emit "do"
|
|
emit " NETDEV=\`echo \$i | cut -d\"-\" -f2\`"
|
|
emit " map_interface \$NETDEV"
|
|
emit "done"
|
|
emit "rename_interfaces"
|
|
emit "IFACE=\`cat /etc/iface_to_activate\`"
|
|
emit "ifup \$IFACE"
|
|
#lets make sure we're up
|
|
emit "IFADDR=\`ifconfig \$IFACE | awk '/inet addr/ {print \$2}' | cut -d\":\" -f 2\`"
|
|
emit "if [ -z \"\$IFADDR\" ]"
|
|
emit "then"
|
|
emit " echo \"\$IFACE failed to come up\""
|
|
if [ "$DEFAULT_ACTION" == "shell" ]
|
|
then
|
|
emit " echo \"Dropping to shell. exit to reboot\""
|
|
emit " /bin/msh"
|
|
fi
|
|
emit " $FINAL_ACTION"
|
|
emit "fi"
|
|
#grab remote host and xlate into numbers
|
|
rhost=`echo $config_val | sed 's/.*@//' | cut -d':' -f1`
|
|
need_dns=`echo $rhost|grep [a-zA-Z]`
|
|
[ -n "$need_dns" ] && rhost=`getent hosts $rhost|cut -d' ' -f1`
|
|
|
|
#find the local ip being used as a route to remote ip
|
|
netdev=`/sbin/ip route get to $rhost 2>&1`
|
|
[ $? != 0 ] && echo "Bad kdump location: $config_val" && exit 1
|
|
OFF_SUBNET=`echo $netdev | grep via`
|
|
if [ -n "$OFF_SUBNET" ]
|
|
then
|
|
# we are going to a different subnet
|
|
lhost=`echo $netdev|awk '{print $7}'|head -n 1`
|
|
else
|
|
# we are on the same subnet
|
|
lhost=`echo $netdev|awk '{print $5}'|head -n 1`
|
|
fi
|
|
|
|
emit "echo Saving to remote location $config_val"
|
|
if [ -z "`echo $config_val|grep @`" ]; then
|
|
#NFS path
|
|
#test nfs mount and directory creation
|
|
rlocation=`echo $config_val| sed 's/.*:/'"$rhost"':/'`
|
|
tmnt=`mktemp -dq`
|
|
kdump_chk "mount -t nfs -o nolock $rlocation $tmnt" \
|
|
"Bad NFS mount $config_val"
|
|
mkdir -p $tmnt/$SAVE_PATH
|
|
tdir=`mktemp -dqp $tmnt/$SAVE_PATH`
|
|
available_size=$(df -P $tdir | tail -1 | tr -s ' ' ':' | cut -d: -f5)
|
|
|
|
rc=$? && rm -rf $tdir
|
|
umount $tmnt
|
|
if [ $? != 0 ]; then
|
|
echo "Cannot unmount the temporary directory"
|
|
exit 1
|
|
fi
|
|
rm -rf $tmnt
|
|
if [ $rc != "0" ]; then
|
|
echo "Cannot create directory in $config_val: $SAVE_PATH"
|
|
exit 1
|
|
fi
|
|
|
|
if [ -z "$CORE_COLLECTOR" ]; then
|
|
CORE_COLLECTOR="cp"
|
|
fi
|
|
|
|
#check for available size is greater than $memtotal
|
|
if [ $available_size -lt $memtotal ]; then
|
|
echo "Warning: There is not space enough to save a vmcore."
|
|
echo " The size of $config_val should be much greater than $memtotal kilo bytes."
|
|
fi
|
|
|
|
#setup nfs case
|
|
if [ -n "$KDUMP_PRE" ]
|
|
then
|
|
emit "$KDUMP_PRE"
|
|
emit "if [ \$? -ne 0 ]"
|
|
emit "then"
|
|
emit " echo kdump_pre script exited with non-zero status"
|
|
emit " $FINAL_ACTION"
|
|
emit "fi"
|
|
fi
|
|
|
|
mkdir -p $MNTIMAGE/mnt
|
|
emit "mount -t nfs -o nolock $rlocation /mnt"
|
|
emit "if [ \$? == 0 ]"
|
|
emit "then"
|
|
emit " mkdir -p /mnt/$SAVE_PATH/$lhost-\$DATE"
|
|
emit " VMCORE=/mnt/$SAVE_PATH/$lhost-\$DATE/vmcore"
|
|
emit " export VMCORE"
|
|
emit " monitor_cp_progress \$VMCORE-incomplete &"
|
|
emit " $CORE_COLLECTOR /proc/vmcore \$VMCORE-incomplete >/dev/null"
|
|
emit " exitcode=\$?"
|
|
emit " if [ \$exitcode == 0 ]"
|
|
emit " then"
|
|
emit " mv \$VMCORE-incomplete \$VMCORE"
|
|
emit " echo -e \"\\\033[0JSaving core complete\""
|
|
emit " fi"
|
|
if [ -x "$KDUMP_POST" ]; then
|
|
emit " $KDUMP_POST \$exitcode"
|
|
fi
|
|
emit " umount /mnt"
|
|
emit " [ \$exitcode == 0 ] && $FINAL_ACTION"
|
|
emit "fi"
|
|
else
|
|
#SSH path
|
|
#rebuild $config_val replacing machine name with ip address
|
|
if [ -n "$CORE_COLLECTOR" ]
|
|
then
|
|
CORE_COLLECTOR=`echo $CORE_COLLECTOR | sed -e's/\(^makedumpfile\)\(.*$\)/\1 -F \2/'`
|
|
fi
|
|
|
|
bin="$bin /usr/bin/ssh /usr/bin/scp"
|
|
rlocation=`echo $config_val|sed 's/@.*/@'"$rhost"'/'`
|
|
#test ssh path and directory creation
|
|
s_opts="-o BatchMode=yes -o StrictHostKeyChecking=no"
|
|
kdump_chk "ssh -q $s_opts $rlocation mkdir -p $SAVE_PATH </dev/null" \
|
|
"Could not create $config_val:$SAVE_PATH, you probably need to run \"service kdump propagate\""
|
|
tdir=`ssh -q $s_opts $rlocation mktemp -dqp $SAVE_PATH </dev/null`
|
|
if [ $? != "0" ]; then
|
|
echo "$KDUMP_CONFIG_FILE: Could not create temp directory in $config_val:$SAVE_PATH"
|
|
exit 1
|
|
fi
|
|
|
|
remote_df=`ssh -q $s_opts $rlocation df -P $tdir | tail -1`
|
|
available_size=$(echo $remote_df | tr -s ' ' '|' | cut -d\| -f4)
|
|
|
|
#check for available size is greater than $memtotal
|
|
if [ $available_size -lt $memtotal ]; then
|
|
echo "Warning: There is not space enough to save a vmcore."
|
|
echo " The size of $rlocation:$tdir should be much greater than $memtotal kilo bytes."
|
|
fi
|
|
#We do this to remove the temp directory from above
|
|
ssh -q $s_opts $rlocation rmdir $tdir
|
|
|
|
#setup ssh case, quick check to see if setup already
|
|
if [ -n "$KDUMP_PRE" ]
|
|
then
|
|
emit "$KDUMP_PRE"
|
|
emit "if [ \$? -ne 0 ]"
|
|
emit "then"
|
|
emit " echo kdump_pre script exited with non-zero status"
|
|
emit " $FINAL_ACTION"
|
|
emit "fi"
|
|
fi
|
|
|
|
if [ ! -r $MNTIMAGE/dev/urandom ]; then
|
|
#only need to do these once
|
|
mkdir -p $MNTIMAGE/root
|
|
cp -a /root/.ssh $MNTIMAGE/root/
|
|
cp -a /etc/ssh $MNTIMAGE/etc
|
|
mknod $MNTIMAGE/dev/urandom c 1 9
|
|
fi
|
|
emit "dd if=/dev/mem of=/dev/urandom count=1 bs=512 skip=100"
|
|
emit "ssh -q -o BatchMode=yes -o StrictHostKeyChecking=no $rlocation mkdir $SAVE_PATH/$lhost-\$DATE"
|
|
emit "VMCORE=$SAVE_PATH/$lhost-\$DATE/vmcore"
|
|
emit "export VMCORE"
|
|
emit "monitor_scp_progress $rlocation $SAVE_PATH/$lhost-\$DATE/vmcore-incomplete &"
|
|
if [ -z "$CORE_COLLECTOR" ]
|
|
then
|
|
emit "scp -q -o BatchMode=yes -o StrictHostKeyChecking=no /proc/vmcore $rlocation:\$VMCORE-incomplete"
|
|
else
|
|
emit "$CORE_COLLECTOR /proc/vmcore | ssh -o BatchMode=yes -o StrictHostKeyChecking=no $rlocation \"cat > $SAVE_PATH/$lhost-\$DATE/vmcore-incomplete\""
|
|
fi
|
|
emit "exitcode=\$?"
|
|
emit "if [ \$exitcode == 0 ]"
|
|
emit "then"
|
|
if [ -z "$CORE_COLLECTOR" ]
|
|
then
|
|
emit " ssh -q -o BatchMode=yes -o StrictHostKeyChecking=no $rlocation mv \$VMCORE-incomplete \$VMCORE"
|
|
else
|
|
emit " ssh -q -o BatchMode=yes -o StrictHostKeyChecking=no $rlocation mv \$VMCORE-incomplete \$VMCORE.flat"
|
|
fi
|
|
emit " echo -e \"\\\033[0JSaving core complete\""
|
|
emit "fi"
|
|
if [ -x "$KDUMP_POST" ]; then
|
|
emit "$KDUMP_POST \$exitcode"
|
|
fi
|
|
emit "[ \$exitcode == 0 ] && $FINAL_ACTION"
|
|
fi
|
|
;;
|
|
core_collector)
|
|
;;
|
|
kdump_pre)
|
|
;;
|
|
kdump_post)
|
|
;;
|
|
extra_bins)
|
|
;;
|
|
extra_modules)
|
|
;;
|
|
disk_timeout)
|
|
;;
|
|
default)
|
|
;;
|
|
link_delay)
|
|
;;
|
|
path)
|
|
;;
|
|
*)
|
|
#test filesystem and directory creation
|
|
kdump_chk "test -f /sbin/fsck.$config_opt" "Unsupported type $config_opt"
|
|
tmnt=`mktemp -dq`
|
|
kdump_chk "mount -t $config_opt $config_val $tmnt" "Bad mount point $config_val"
|
|
mkdir -p $tmnt/$SAVE_PATH
|
|
tdir=`mktemp -dqp $tmnt/$SAVE_PATH`
|
|
rc=$?
|
|
available_size=$(df $tdir | tail -1 | tr -s ' ' ':' | cut -d: -f4)
|
|
rm -rf $tdir > /dev/null 2>&1
|
|
umount $tmnt > /dev/null 2>&1
|
|
if [ $rc != "0" ]; then
|
|
echo "Cannot create directory in $config_val: $SAVE_PATH"
|
|
exit 1
|
|
fi
|
|
#check for available size is greater than $memtotal
|
|
if [ $available_size -lt $memtotal ]; then
|
|
echo "Warning: There is not space enough to save a vmcore."
|
|
echo " The size of $config_val should be much greater than $memtotal kilo bytes."
|
|
fi
|
|
|
|
|
|
#setup filesystem case
|
|
|
|
if [ -n "$KDUMP_PRE" ]
|
|
then
|
|
emit "$KDUMP_PRE"
|
|
emit "if [ \$? -ne 0 ]"
|
|
emit "then"
|
|
emit " echo kdump_pre script exited with non-zero status"
|
|
emit " $FINAL_ACTION"
|
|
emit "fi"
|
|
fi
|
|
|
|
mkdir -p $MNTIMAGE/mnt
|
|
touch $MNTIMAGE/etc/mtab
|
|
if [ -z "$CORE_COLLECTOR" ]; then
|
|
CORE_COLLECTOR="cp"
|
|
fi
|
|
emit "echo Saving to the local filesystem $config_val"
|
|
emit "DUMPDEV=$config_val"
|
|
emit "IS_LABEL=\`echo \$DUMPDEV | grep LABEL\`"
|
|
emit "IS_UUID=\`echo \$DUMPDEV | grep UUID\`"
|
|
emit "if [ -n \"\$IS_LABEL\" -o -n \"\$IS_UUID\" ] "
|
|
emit "then"
|
|
emit " DUMPDEV=\`findfs \$DUMPDEV\`"
|
|
emit "fi"
|
|
emit "fsck.$config_opt \$DUMPDEV"
|
|
emit "mount -t $config_opt \$DUMPDEV /mnt"
|
|
emit "if [ \$? == 0 ]"
|
|
emit "then"
|
|
emit " mkdir -p /mnt/$SAVE_PATH/127.0.0.1-\$DATE"
|
|
emit " VMCORE=/mnt/$SAVE_PATH/127.0.0.1-\$DATE/vmcore"
|
|
emit " export VMCORE"
|
|
if [ "$CORE_COLLECTOR" == "cp" ]; then
|
|
emit " monitor_cp_progress \$VMCORE-incomplete &"
|
|
fi
|
|
emit " $CORE_COLLECTOR /proc/vmcore \$VMCORE-incomplete >/dev/null"
|
|
emit " exitcode=\$?"
|
|
emit " if [ \$exitcode == 0 ]"
|
|
emit " then"
|
|
emit " mv \$VMCORE-incomplete \$VMCORE"
|
|
emit " echo -e \"\\\033[0JSaving core complete\""
|
|
emit " fi"
|
|
if [ -x "$KDUMP_POST" ]; then
|
|
emit " $KDUMP_POST \$exitcode"
|
|
fi
|
|
emit "fi"
|
|
emit "umount /mnt"
|
|
emit "[ \$exitcode == 0 ] && $FINAL_ACTION"
|
|
;;
|
|
esac
|
|
done < $KDUMP_CONFIG_FILE
|
|
|
|
#now handle the default action
|
|
if [ "$DEFAULT_ACTION" == "shell" ]
|
|
then
|
|
emit "echo dropping to initramfs shell"
|
|
emit "echo exiting this shell will reboot your system"
|
|
emit "/bin/msh"
|
|
fi
|
|
case $DEFAULT_ACTION in
|
|
reboot|halt|shell)
|
|
emit "$FINAL_ACTION"
|
|
;;
|
|
*)
|
|
emit "echo Attempting to enter user-space to capture vmcore"
|
|
;;
|
|
esac
|
|
|
|
#find the shared libraries. this snippet taken from kboot
|
|
TEMPLDCFG=`mktemp`
|
|
for lib in `ls /etc/ld.so.conf.d/* 2>/dev/null | grep -v kernelcap`
|
|
do
|
|
echo "include " $lib >> $TEMPLDCFG
|
|
done
|
|
/sbin/ldconfig -f $TEMPLDCFG
|
|
kdump_libs=`for n in $bin; do
|
|
ldd "$n" 2>/dev/null | tr -s '\011' ' ' |
|
|
sed 's/.*=> *//;s/^ *//;/ *(0x.*)/s///p;d'
|
|
done | sort | uniq | sed '/^ *$/d'`
|
|
/sbin/ldconfig
|
|
rm -f $TEMPLDCFG
|
|
|
|
#copy the binaries and their shared libraries to the archive
|
|
for n in $bin $kdump_libs $k_extras; do
|
|
mkdir -p $MNTIMAGE/`dirname $n`
|
|
cp $n $MNTIMAGE/$n
|
|
done
|
|
fi
|
|
|
|
emit "echo Creating root device."
|
|
emit "#check to see if we have root= on the command line"
|
|
emit "ROOTDEV=\`cat /proc/cmdline | grep root=\`"
|
|
emit "if [ -n \"\$ROOTDEV\" ]"
|
|
emit "then"
|
|
emit " ROOTDEV=\`cat /proc/cmdline | sed 's/^.*root=//' | cut -d\" \" -f1\`"
|
|
emit " IS_LABEL=\`echo \$ROOTDEV | grep LABEL\`"
|
|
emit " IS_UUID=\`echo \$ROOTDEV | grep UUID\`"
|
|
emit " if [ -n \"\$IS_LABEL\" -o -n \"\$IS_UUID\" ] "
|
|
emit " then"
|
|
emit " ROOTDEV=\`findfs \$ROOTDEV\`"
|
|
emit " fi"
|
|
emit "else"
|
|
emit " #we need to get the root major/minor from real-root-dev"
|
|
emit " ROOT_DEV_NR=\`cat /proc/sys/kernel/real-root-dev\`"
|
|
emit " ROOT_MIN=\`echo \$ROOT_DEV_NR | sed -e's/\\([0-9a-f]\\{1,2\\}\\)\\([0-9a-f]\\{2\\}\\)/\\2/'\`"
|
|
emit " ROOT_MAJ=\`echo \$ROOT_DEV_NR | sed -e's/\\([0-9a-f]\\{1,2\\}\\)\\([0-9a-f]\\{2\\}\\)/\\1/'\`"
|
|
emit " mknod /dev/rootdev b 0x\$ROOT_MAJ 0x\$ROOT_MIN"
|
|
emit " ROOTDEV=/dev/rootdev"
|
|
emit "fi"
|
|
|
|
emit "echo Checking root filesystem."
|
|
emit "fsck \$ROOTDEV"
|
|
emit "echo Mounting root filesystem: mount -t $rootfs \$ROOTDEV /sysroot"
|
|
emit "mount -t $rootfs \$ROOTDEV /sysroot >/dev/null 2>&1 "
|
|
emit "if [ \$? != 0 ]"
|
|
emit "then"
|
|
emit " echo unable to mount rootfs. Dropping to shell"
|
|
emit " /bin/msh"
|
|
emit "fi"
|
|
|
|
emit "#move various filesystems and prime the rootfs to boot properly"
|
|
emit "umount /proc"
|
|
emit "mount -t proc proc /sysroot/proc"
|
|
emit "umount /sys"
|
|
emit "mount -t sysfs sysfs /sysroot/sys"
|
|
emit "mount -o bind /dev /sysroot/dev"
|
|
emit "touch /sysroot/fastboot"
|
|
emit "echo Switching to new root and running init."
|
|
emit "exec switch_root /sysroot /sbin/init"
|
|
|
|
# END OF INIT SCRIPT
|
|
|
|
chmod +x $RCFILE
|
|
|
|
(cd $MNTIMAGE; findall . | cpio --quiet -c -o) >| $IMAGE || exit 1
|
|
|
|
if [ -n "$compress" ]; then
|
|
gzip -9 < $IMAGE >| $target || rc=1
|
|
else
|
|
cp -a $IMAGE $target || rc=1
|
|
fi
|
|
rm -rf $MNTIMAGE $IMAGE $TMPDISKLIST
|
|
if [ -n "$MNTPOINT" ]; then rm -rf $MNTPOINT ; fi
|
|
exit $rc
|