On 12/5/2013 3:08 PM, John Hupp wrote:
On 12/5/2013 11:31 AM, John Hupp wrote:
I'm still troubleshooting the problem in which (on *buntu 13.10) client
boot fails after the splash screen with 'Error: socket failed:
connection refused.'

My current working premise is that this is an nbd error.

So I want to see the nbd-client command line and configuration in the
client initramfs.  I'm assuming that loads from the initramfs /init
script, but 'cat /init' produces rather useless scrolls-by-in-a-flash
output, and the initramfs does not support 'cat /init | less.'

Can I locate the init script somewhere on the server?
I found out that I can view the init script from /boot/initrd.img-* via
a procedure like:

       $ mkdir -p /tmp/initrd
       $ cd /tmp/initrd
       $ cp /boot/initrd.img-<rest of your filename> ./initrd.gz
       $ gzip -d initrd.gz
       $ cpio -i < initrd

After that the contents of the initrd are going to be unpacked into the
/tmp/initrd directory.

But that is not the same initrd used on the LTSP client, is it?  If so,
there is no mention of nbd anywhere in its init script.


After thinking about it overnight, I realized that the server syslog would tell me where the initrd is. It is at /var/lib/tftpboot/ltsp/<arch>.

And in a slightly simplified procedure, I simply copied the initrd archive from there to /tmp and there ran (to unpack it):
$  zcat initrd.img-3.11.0-12-generic | cpio -div

But it is not so simple from there. I found that /init does not launch nbd-client directly but via other scripts. The relevant ones seem to be:
/scripts/local-top/nbd
/scripts/local-top/nbd-ltsp
/sbin/nbd-client-proxy

Even knowing this much now, my script knowledge is poor, so I haven't yet been able to parse exactly what nbd-client command is being run.

Can anyone decipher this?  I attach the scripts.

I also thought about just trying to run an nbd-client command directly from the busybox shell to see if it produces the same error as originally reported. But the nbd-client-proxy comments seem to indicate that this won't work. Perhaps someone can say more about that.
#!/bin/sh

[ -d /dev ] || mkdir -m 0755 /dev
[ -d /root ] || mkdir -m 0700 /root
[ -d /sys ] || mkdir /sys
[ -d /proc ] || mkdir /proc
[ -d /tmp ] || mkdir /tmp
mkdir -p /var/lock
mount -t sysfs -o nodev,noexec,nosuid sysfs /sys
mount -t proc -o nodev,noexec,nosuid proc /proc
# Some things don't work properly without /etc/mtab.
ln -sf /proc/mounts /etc/mtab

grep -q '\<quiet\>' /proc/cmdline || echo "Loading, please wait..."

# Note that this only becomes /dev on the real filesystem if udev's scripts
# are used; which they will be, but it's worth pointing out
if ! mount -t devtmpfs -o mode=0755 udev /dev; then
        echo "W: devtmpfs not available, falling back to tmpfs for /dev"
        mount -t tmpfs -o mode=0755 udev /dev
        [ -e /dev/console ] || mknod -m 0600 /dev/console c 5 1
        [ -e /dev/null ] || mknod /dev/null c 1 3
fi
mkdir /dev/pts
mount -t devpts -o noexec,nosuid,gid=5,mode=0620 devpts /dev/pts || true
mount -t tmpfs -o "noexec,nosuid,size=10%,mode=0755" tmpfs /run
mkdir /run/initramfs
# compatibility symlink for the pre-oneiric locations
ln -s /run/initramfs /dev/.initramfs

# Export the dpkg architecture
export DPKG_ARCH=
. /conf/arch.conf

# Set modprobe env
export MODPROBE_OPTIONS="-qb"

# Export relevant variables
export ROOT=
export ROOTDELAY=
export ROOTFLAGS=
export ROOTFSTYPE=
export IP=
export BOOT=
export BOOTIF=
export UBIMTD=
export break=
export init=/sbin/init
export quiet=n
export readonly=y
export rootmnt=/root
export debug=
export panic=
export blacklist=
export resume=
export resume_offset=
export recovery=

# mdadm needs hostname to be set. This has to be done before the udev rules are 
called!
if [ -f "/etc/hostname" ]; then
        /bin/hostname -b -F /etc/hostname 2>&1 1>/dev/null
fi

# Bring in the main config
. /conf/initramfs.conf
for conf in conf/conf.d/*; do
        [ -f ${conf} ] && . ${conf}
done
. /scripts/functions

# Parse command line options
for x in $(cat /proc/cmdline); do
        case $x in
        init=*)
                init=${x#init=}
                ;;
        root=*)
                ROOT=${x#root=}
                case $ROOT in
                LABEL=*)
                        ROOT="${ROOT#LABEL=}"

                        # support any / in LABEL= path (escape to \x2f)
                        case "${ROOT}" in
                        */*)
                        if command -v sed >/dev/null 2>&1; then
                                ROOT="$(echo ${ROOT} | sed 's,/,\\x2f,g')"
                        else
                                if [ "${ROOT}" != "${ROOT#/}" ]; then
                                        ROOT="\x2f${ROOT#/}"
                                fi
                                if [ "${ROOT}" != "${ROOT%/}" ]; then
                                        ROOT="${ROOT%/}\x2f"
                                fi
                                IFS='/'
                                newroot=
                                for s in $ROOT; do
                                        
newroot="${newroot:+${newroot}\\x2f}${s}"
                                done
                                unset IFS
                                ROOT="${newroot}"
                        fi
                        esac
                        ROOT="/dev/disk/by-label/${ROOT}"
                        ;;
                UUID=*)
                        ROOT="/dev/disk/by-uuid/${ROOT#UUID=}"
                        ;;
                /dev/nfs)
                        [ -z "${BOOT}" ] && BOOT=nfs
                        ;;
                esac
                ;;
        rootflags=*)
                ROOTFLAGS="-o ${x#rootflags=}"
                ;;
        rootfstype=*)
                ROOTFSTYPE="${x#rootfstype=}"
                ;;
        rootdelay=*)
                ROOTDELAY="${x#rootdelay=}"
                case ${ROOTDELAY} in
                *[![:digit:].]*)
                        ROOTDELAY=
                        ;;
                esac
                ;;
        resumedelay=*)
                RESUMEDELAY="${x#resumedelay=}"
                ;;
        loop=*)
                LOOP="${x#loop=}"
                ;;
        loopflags=*)
                LOOPFLAGS="-o ${x#loopflags=}"
                ;;
        loopfstype=*)
                LOOPFSTYPE="${x#loopfstype=}"
                ;;
        cryptopts=*)
                cryptopts="${x#cryptopts=}"
                ;;
        nfsroot=*)
                NFSROOT="${x#nfsroot=}"
                ;;
        netboot=*)
                NETBOOT="${x#netboot=}"
                ;;
        ip=*)
                IP="${x#ip=}"
                ;;
        boot=*)
                BOOT=${x#boot=}
                ;;
        ubi.mtd=*)
                UBIMTD=${x#ubi.mtd=}
                ;;
        resume=*)
                RESUME="${x#resume=}"
                ;;
        resume_offset=*)
                resume_offset="${x#resume_offset=}"
                ;;
        noresume)
                noresume=y
                ;;
        panic=*)
                panic="${x#panic=}"
                case ${panic} in
                *[![:digit:].]*)
                        panic=
                        ;;
                esac
                ;;
        quiet)
                quiet=y
                ;;
        ro)
                readonly=y
                ;;
        rw)
                readonly=n
                ;;
        debug)
                debug=y
                quiet=n
                exec >/run/initramfs/initramfs.debug 2>&1
                set -x
                ;;
        debug=*)
                debug=y
                quiet=n
                set -x
                ;;
        break=*)
                break=${x#break=}
                ;;
        break)
                break=premount
                ;;
        blacklist=*)
                blacklist=${x#blacklist=}
                ;;
        netconsole=*)
                netconsole=${x#netconsole=}
                ;;
        BOOTIF=*)
                BOOTIF=${x#BOOTIF=}
                ;;
        hwaddr=*)
                BOOTIF=${x#BOOTIF=}
                ;;
        recovery)
                recovery=y
                ;;
        esac
done

if [ -n "${noresume}" ]; then
        export noresume
        unset resume
else
        resume=${RESUME:-}
fi

maybe_break top

# export BOOT variable value for compcache,
# so we know if we run from casper
export BOOT

# Don't do log messages here to avoid confusing graphical boots
run_scripts /scripts/init-top

maybe_break modules
[ "$quiet" != "y" ] && log_begin_msg "Loading essential drivers"
load_modules
[ "$quiet" != "y" ] && log_end_msg

[ -n "${netconsole}" ] && modprobe netconsole netconsole="${netconsole}"

maybe_break premount
[ "$quiet" != "y" ] && log_begin_msg "Running /scripts/init-premount"
run_scripts /scripts/init-premount
[ "$quiet" != "y" ] && log_end_msg

maybe_break mount
log_begin_msg "Mounting root file system"
. /scripts/${BOOT}
parse_numeric ${ROOT}
maybe_break mountroot
mountroot
log_end_msg

maybe_break bottom
[ "$quiet" != "y" ] && log_begin_msg "Running /scripts/init-bottom"
run_scripts /scripts/init-bottom
[ "$quiet" != "y" ] && log_end_msg

# Preserve information on old systems without /run on the rootfs
if [ -d ${rootmnt}/run ]; then
        mount -n -o move /run ${rootmnt}/run
else
        # The initramfs udev database must be migrated:
        if [ -d /run/udev ] && [ ! -d /dev/.udev ]; then
                mv /run/udev /dev/.udev
        fi
        # The initramfs debug info must be migrated:
        if [ -d /run/initramfs ] && [ ! -d /dev/.initramfs ]; then
                mv /run/initramfs /dev/.initramfs
        fi
        umount /run
fi

# Move virtual filesystems over to the real filesystem
mount -n -o move /sys ${rootmnt}/sys
mount -n -o move /proc ${rootmnt}/proc

validate_init() {
        checktarget="${1}"

        # Work around absolute symlinks
        if [ -d "${rootmnt}" ] && [ -h "${rootmnt}${checktarget}" ]; then
                case $(readlink "${rootmnt}${checktarget}") in /*)
                        checktarget="$(chroot ${rootmnt} readlink 
${checktarget})"
                        ;;
                esac
        fi

        # Make sure the specified init can be executed
        if [ ! -x "${rootmnt}${checktarget}" ]; then
                return 1
        fi

        # Upstart uses /etc/init as configuration directory :-/
        if [ -d "${rootmnt}${checktarget}" ]; then
                return 1
        fi
}

# Check init bootarg
if [ -n "${init}" ]; then
        if ! validate_init "$init"; then
                echo "Target filesystem doesn't have requested ${init}."
                init=
        fi
fi

# Common case: /sbin/init is present
if [ ! -x "${rootmnt}/sbin/init" ]; then
        # ... if it's not available search for valid init
        if [ -z "${init}" ] ; then
                for inittest in /sbin/init /etc/init /bin/init /bin/sh; do
                        if validate_init "${inittest}"; then
                                init="$inittest"
                                break
                        fi
                done
        fi

        # No init on rootmount
        if ! validate_init "${init}" ; then
                panic "No init found. Try passing init= bootarg."
        fi
fi

maybe_break init

# don't leak too much of env - some init(8) don't clear it
# (keep init, rootmnt)
unset debug
unset MODPROBE_OPTIONS
unset DPKG_ARCH
unset ROOTFLAGS
unset ROOTFSTYPE
unset ROOTDELAY
unset ROOT
unset IP
unset BOOT
unset BOOTIF
unset UBIMTD
unset blacklist
unset break
unset noresume
unset panic
unset quiet
unset readonly
unset resume
unset resume_offset

# Chain to real filesystem
exec run-init ${rootmnt} ${init} "$@" ${recovery:+--startup-event=recovery} 
<${rootmnt}/dev/console >${rootmnt}/dev/console 2>&1
panic "Could not execute run-init."
#!/bin/sh

# We don't have any prerequisites
case $1 in
prereqs)
        exit 0
        ;;
esac

for x in $(cat /proc/cmdline); do
        case "$x" in
                nbddev=*)
                        nbddev="${x#nbddev=}"
                        ;;
                nbdroot=*)
                        nbdroot="${x#nbdroot=}"
                        ;;
                root=/dev/nbd*)
                        nbddev="${x#root=}"
                        ;;
        esac
done

# if nbd root is not requested exit early and silently
if [ -z "$nbdroot" ] && [ -z "$nbddev" ]
then
        exit 0
fi

. /scripts/functions

log_begin_msg "Setting up nbd-client"

configure_networking

# Support setting stuff using DHCP by overloading 'option root-path'
case "$nbdroot" in
        ''|dhcp)
                nbdroot=$ROOTPATH
                ;;
esac

nbdrootdev="$nbddev"
nbdbasedev="${nbddev#/dev/}"

case "$nbdroot" in
        *,*,*)
                nbdsrv="${nbdroot%%,*}"
                nbdport="${nbdroot%,*}"
                nbdport="${nbdport##*,}"
                # root= parameter overrides three-option nbdroot= parameter
                if [ -z "$nbdrootdev" ]
                then
                        nbdbasedev="${nbdroot##*,}"
                        nbdrootdev=/dev/$nbdbasedev
                fi
                ;;
        *,*)
                nbdsrv="${nbdroot%,*}"
                nbdport="${nbdroot#*,}"
                ;;
        \[*\]*)
                # [ipv6]:port/path
                nbdsrv=${nbdroot%\]*}
                nbdsrv=${nbdsrv#\[}
                nbdportpath=${nbdroot#\[$nbdsrv\]}
                nbdportpath=${nbdportpath#:}
                nbdport=${nbdportpath%%/*}
                nbdpath=${nbdportpath#$nbdport}
                ;;
        *)
                # ipv4:port/path
                nbdsrv=${nbdroot%%[:/]*}
                nbdportpath=${nbdroot#$nbdsrv}
                nbdportpath=${nbdportpath#:}
                nbdport=${nbdportpath%%/*}
                nbdpath=${nbdportpath#$nbdport}
                ;;
esac

case "$nbdport" in
        *[^0-9]*)
                # non-numeric characters, assume a name rather than a port
                nbdpath="$nbdport"
                unset nbdport
                ;;
esac

nbdrootdev=${nbdrootdev%p*}
nbdbasedev=${nbdbasedev%p*}
# If host is omitted, use ROOTSERVER from DHCP.
case "$nbdsrv" in
        ''|dhcp)
                nbdsrv=$ROOTSERVER
                ;;
esac

if [ -z "$nbdsrv" ] || [ -z "$nbdrootdev" ] || ( [ -z "$nbdpath" ] && [ -z 
"$nbdport" ] )
then
        log_failure_msg "Insufficient information to set up nbd, quitting 
(nbdroot=$nbdroot, host=$nbdsrv, name=$nbdpath, port=$nbdport, 
nbd-device=$nbdrootdev)"
        exit 0
fi

# Support defining an alternate launch script with env variable NBDCLIENT.
NBDCLIENT=${NBDCLIENT:-/sbin/nbd-client}
$NBDCLIENT $nbdsrv ${nbdpath:+-N} $nbdpath $nbdport $nbdrootdev -swap -persist

# This should be removed once the cfq scheduler no longer deadlocks nbd
# devices
if grep -q '\[cfq\]' /sys/block/$nbdbasedev/queue/scheduler
then
        echo deadline > /sys/block/$nbdbasedev/queue/scheduler
fi
#!/bin/sh

# Work around LP bug #696435
if [ "$ROOT" = /dev/nbd0 ] && [ -z "$FSTYPE" ]; then
    FSTYPE=$(blkid -s TYPE -o value "${ROOT}")
    if [ -n "$FSTYPE" ]; then
        echo "FSTYPE='$FSTYPE'" > /conf/param.conf
    fi
fi
#!/bin/sh

# This is just a wrapper script that accepts the same parameters as nbd-client,
# and launches nbd-proxy to connect to the specified server,
# and nbd-client to connect to the nbd-proxy in localhost.
# Maybe at some point nbd-proxy itself can accept that syntax, so the wrapper
# won't be needed anymore.
# It might be ran from the initramfs, so only busybox utilities should be used.

if [ $# -eq 0 ]; then
    echo "Usage: $0 host port nbd_device [-block-size|-b block size] 
[-timeout|-t timeout] [-swap|-s] [-sdp|-S] [-persist|-p] [-nofork|-n]
For more info, see the nbd-client man page." >&2
    exit 1
fi

# Make sure the loopback interface has an address for nbd-proxy
ip addr add dev lo 127.0.0.1
ip link set lo up

# To make the initramfs nbd script call nbd-client-proxy instead of nbd-client,
# specify NBDCLIENT=nbd-client-proxy in the kernel command line.
# Then the local-top/nbd initramfs script will call nbd-client-proxy this way:
# $NBDCLIENT $nbdsrv ${nbdpath:+-N} $nbdpath $nbdport $nbdrootdev -swap -persist
host="$1"
if [ "$2" = "-N" ]; then
    port=10809
else
    port="$2"
fi

nbd-proxy "$host" "$port" "$port"

# Remove the host parameter and chain to nbd-client with the rest of the command
# line.
shift
exec nbd-client 127.0.0.1 "$@"
------------------------------------------------------------------------------
Sponsored by Intel(R) XDK 
Develop, test and display web and hybrid apps with a single code base.
Download it for free now!
http://pubads.g.doubleclick.net/gampad/clk?id=111408631&iu=/4140/ostg.clktrk
_____________________________________________________________________
Ltsp-discuss mailing list.   To un-subscribe, or change prefs, goto:
      https://lists.sourceforge.net/lists/listinfo/ltsp-discuss
For additional LTSP help,   try #ltsp channel on irc.freenode.net

Reply via email to