Package: nbd-client Version: 1:2.9.15-1 Severity: minor Tags: patch If KILLALL is set false in /etc/nbd-client, then the init script attempts to umount all listed devices, even those that are selected to be swap devices. This means an error and a long wait for every network swap device.
My patch corrects this by being selective about which devices to umount and which to swapoff. The only change when KILLALL is not false is to swapoff only devices listed in /proc/swaps if that exists. If /proc/swaps does not exist, then we get the old behaviour of swapoff all devices. As I use nbd only for swaps, and have no filesystems other than NFS in my kernel (diskless embedded device) it would be worth verifying with filesystems before committing - sorry I'm not in a position to have tested that. But I'm pretty confident I haven't broken it. Here's the patch:
--- etc/init.d/nbd-client.dpkg-dist 2010-03-24 22:08:02.000000000 +0000 +++ etc/init.d/nbd-client 2010-05-24 12:33:11.000000000 +0100 @@ -38,6 +38,57 @@ test -x $DAEMON || exit 0 +get_devices() { + DEVICES= + i=0 + while [ ! -z ${NBD_DEVICE[$i]} ] + do + if [ ${NBD_TYPE[$i]} == "$1" ] + then + DEVICES="$DEVICES ${NBD_DEVICE[$i]}" + fi + i=$(($i + 1)) + done +} + +get_all_devices() { + if [ "$KILLALL" == "false" ] + then + DEVICES=${NBD_DEVICE[*]} + else + if [ -d /dev/nbd ] + then + DEVICES=/dev/nbd/* + else + DEVICES=/dev/nb* + fi + fi +} + +get_swap_devices() { + if [ "$KILLALL" == "false" ] + then + get_devices s + else + if [ -f /proc/swaps ] + then + DEVICES=`grep '^/dev/nb' /proc/swaps | cut -d ' ' -f1` + else + get_all_devices + fi + fi +} + +get_mount_devices() { + if [ "$KILLALL" == "false" ] + then + get_devices f + else + DEVICES=`mount | cut -d " " -f 1 | grep /dev/nbd` + fi +} + + case "$1" in connect) # I don't use start-stop-daemon: nbd-client only does some setup @@ -134,19 +185,14 @@ ;; stop) echo "Stopping $DESC: " - echo "umounting all filesystems for nbd-blockdevices..." - if [ "$KILLALL" != "false" ] - then - DEVICES=`mount | cut -d " " -f 1 | grep /dev/nbd` - else - DEVICES=${NBD_DEVICE[*]} - fi + get_mount_devices for dev in $DEVICES do # Ignore devices with _netdev option (sysvinit takes care of those) line=$(grep $dev /etc/fstab | grep "_netdev") if [ -z "$line" ] then + echo "umounting filesystem from $dev..." umount $dev 2>/dev/null if [ $? -eq 1 ] then @@ -162,20 +208,16 @@ fi echo $dev done - if [ "$KILLALL" != "false" ] - then - if [ -d /dev/nbd ] + get_swap_devices + if [ "$DEVICES" ] then - DEVICES=/dev/nbd/* - else - DEVICES=/dev/nb* - fi + echo "Invoking swapoff on $DEVICES..." + swapoff $DEVICES 2>/dev/null fi - echo "Invoking swapoff on NBD devices..." - swapoff $DEVICES 2>/dev/null - echo "Disconnecting $DESCes..." + get_all_devices for i in $DEVICES - do + do + echo "Disconnecting $i" $DAEMON -d $i 2>/dev/null >/dev/null done rmmod nbd