From ba9b0250b392c4cbaa4a9f85d89e4c4a84797065 Mon Sep 17 00:00:00 2001 From: jandob Date: Thu, 7 Jan 2016 15:16:37 +0100 Subject: change hooks variable scoping; introduce /etc/openslx config --- .../prepare-kernel-command-line-parameter.sh | 33 +++++----- .../dnbd3-rootfs/hooks/mount/mount-root-device.sh | 17 +++-- .../dnbd3-rootfs/hooks/pre-mount/fetch-config.sh | 57 +++++++++++----- .../hooks/pre-mount/prepare-root-partition.sh | 76 +++++++++++++++------- builder/dnbd3-rootfs/scripts/rebash | 2 +- 5 files changed, 123 insertions(+), 62 deletions(-) diff --git a/builder/dnbd3-rootfs/hooks/cmdline/prepare-kernel-command-line-parameter.sh b/builder/dnbd3-rootfs/hooks/cmdline/prepare-kernel-command-line-parameter.sh index e81cf43d..c038aecc 100755 --- a/builder/dnbd3-rootfs/hooks/cmdline/prepare-kernel-command-line-parameter.sh +++ b/builder/dnbd3-rootfs/hooks/cmdline/prepare-kernel-command-line-parameter.sh @@ -1,8 +1,10 @@ +#!/usr/bin/env bash +( # subshell for variable scoping SLX_INITIAL_KERNEL_COMMAND_LINE="$(cat /proc/cmdline | tr --delete '\n')" # This location will be used to have a writable kernel command line file # location. -local writeable_proc_cmdline_path='/writable_proc_cmdline/' +writeable_proc_cmdline_path='/writable_proc_cmdline/' mkdir --parents "$writeable_proc_cmdline_path" # NOTE: The fake writeable overlay have to be a temporary filesystem for the # hack to work. @@ -15,19 +17,17 @@ echo -e \ "${SLX_INITIAL_KERNEL_COMMAND_LINE}\n" \ '----------------------------------------------------------------------' -local parameter for parameter in $(getargs BOOTIF=); do info "PXE given boot interface $parameter" - local dracut_interface_name="bootnet:$(echo $parameter | \ + dracut_interface_name="bootnet:$(echo $parameter | \ sed --regexp-extended 's/.{2}[:\-]((.{2}[:\-]){5}.{2})/\1/' | \ sed s/-/:/g)" info "Dracut interface name is: $dracut_interface_name" echo -n " ifname=$dracut_interface_name" >> \ "${writeable_proc_cmdline_path}cmdline" done -local parameter for parameter in $(getargs ip=); do - local temp="$parameter:" + temp="$parameter:" set -- while [ -n "$temp" ]; do set -- "$@" "${temp%%:*}" @@ -40,7 +40,7 @@ for parameter in $(getargs ip=); do [ -n "$4" ] && net_mask=$4 info "PXE given net configuration: ip: $ip server_ip: $server_ip gateway_ip: $gateway_ip net_mask: $net_mask" - local dracut_ip_configuration="$ip::$gateway_ip:$net_mask::bootnet:off" + dracut_ip_configuration="$ip::$gateway_ip:$net_mask::bootnet:off" info "Dracut ip configuration is: $dracut_ip_configuration" sed --regexp-extended "s/ip=[^ ]*/ip=$dracut_ip_configuration/g" \ --in-place "${writeable_proc_cmdline_path}cmdline" @@ -54,21 +54,22 @@ if [ -z "$dracut_interface_name" ]; then fi mount --options bind "${writeable_proc_cmdline_path}cmdline" /proc/cmdline -for parameter in $(getargs slxsrv=); do - SLX_SERVER="$parameter" -done -for parameter in $(getargs slxbase=); do - SLX_SERVER_BASE="$parameter" -done -if [ -z "$SLX_SERVER" ]; then +if [ -z $(getargs "$SLX_SERVER") ]; then warn 'No "slxsrv" parameter found in the kernel command line.' - return 1 + exit 1 fi -if [ -z "$SLX_SERVER_BASE" ]; then +if [ -z $(getargs "$SLX_SERVER_BASE") ]; then warn 'No "slxbase" parameter found in the kernel command line.' - return 1 + exit 1 fi echo '-----------------------Dracut-Kernel-Command-Line:----------------------' cat /proc/cmdline echo '------------------------------------------------------------------------' +) || exit $? +# region vim modline + +# vim: set tabstop=4 shiftwidth=4 expandtab: +# vim: foldmethod=marker foldmarker=region,endregion: + +# endregion diff --git a/builder/dnbd3-rootfs/hooks/mount/mount-root-device.sh b/builder/dnbd3-rootfs/hooks/mount/mount-root-device.sh index 97059aae..da5237f0 100755 --- a/builder/dnbd3-rootfs/hooks/mount/mount-root-device.sh +++ b/builder/dnbd3-rootfs/hooks/mount/mount-root-device.sh @@ -1,4 +1,13 @@ -mount /dev/mapper/root "$NEWROOT" $SLX_MOUNT_ROOT_OPTIONS && \ -# Write fstab for recognized system partition. -sed --in-place --quiet "/${SLX_SYSTEM_PARTITION_IDENTIFIER}.*/!s/.*//" \ - "$NEWROOT/etc/fstab" +( # subshell for variable scoping +source "/etc/openslx" +mkdir --parents "$SLX_CONFIGURATION_LOCATION" +cp "/etc/openslx" "$SLX_CONFIGURATION_LOCATION" +mount /dev/mapper/root "$NEWROOT" $SLX_MOUNT_ROOT_OPTIONS +genfstab "$NEWROOT" > "$NEWROOT/etc/fstab" +) || exit $? +# region vim modline + +# vim: set tabstop=4 shiftwidth=4 expandtab: +# vim: foldmethod=marker foldmarker=region,endregion: + +# endregion diff --git a/builder/dnbd3-rootfs/hooks/pre-mount/fetch-config.sh b/builder/dnbd3-rootfs/hooks/pre-mount/fetch-config.sh index 4930c94a..3cbe6996 100755 --- a/builder/dnbd3-rootfs/hooks/pre-mount/fetch-config.sh +++ b/builder/dnbd3-rootfs/hooks/pre-mount/fetch-config.sh @@ -1,22 +1,43 @@ -local configuration_file_name='config' -info 'Getting configuration file.' -local IFS_backup="$IFS" +#!/usr/bin/env bash +( # subshell for variable scoping +# region imports +type getarg >/dev/null 2>&1 || source /lib/dracut-lib.sh +source "/usr/lib/rebash/core.sh" +core.import exceptions +exceptions.activate +core.import utils +core.import logging +# endregion +logging.set_commands_log_level debug +logging.set_log_level debug + +# TODO make configurable via kernel command line +configuration_file_name='config' + +slx_server="$(getargs slxsrv=)" +slx_server_base="$(getargs slxbase=)" + +logging.info 'Getting configuration file.' +IFS_backup="$IFS" IFS="," -local host -for host in ${SLX_SERVER}; do - info "Trying host \"$host\"." - wget --timeout 5 --quiet "http://${host}/${SLX_SERVER_BASE}${configuration_file_name}" \ - --output-document "/$configuration_file_name" - local return_code="$?" - [[ $return_code == 0 ]] && break - continue +host +for host in ${slx_server}; do + logging.info "Trying host \"$host\"." + if wget --timeout 5 "http://${host}/${slx_server_base}${configuration_file_name}" \ + --output-document "/etc/openslx"; then + break + fi done IFS="$IFS_backup" -if [[ $return_code != 0 ]]; then - warn "Downloading OpenSLX configuration file from any of the servers \"${SLX_SERVER}\" at location \"${SLX_SERVER_BASE}${configuration_file_name}\" failed. Return code: $return_code" - emergency_shell -n "$0" - return 1 + +if [[ ! -e "/etc/openslx" ]]; then + logging.warn "Downloading OpenSLX configuration file from any of the servers \"${slx_server}\" at location \"${slx_server_base}${configuration_file_name}\" failed. Return code: $return_code" + exit 1 fi -source "/$configuration_file_name" -mkdir --parents "$SLX_CONFIGURATION_LOCATION" -mv "/$configuration_file_name" "$SLX_CONFIGURATION_LOCATION" +) || exit $? +# region vim modline + +# vim: set tabstop=4 shiftwidth=4 expandtab: +# vim: foldmethod=marker foldmarker=region,endregion: + +# endregion diff --git a/builder/dnbd3-rootfs/hooks/pre-mount/prepare-root-partition.sh b/builder/dnbd3-rootfs/hooks/pre-mount/prepare-root-partition.sh index 2e62434d..4e70db35 100755 --- a/builder/dnbd3-rootfs/hooks/pre-mount/prepare-root-partition.sh +++ b/builder/dnbd3-rootfs/hooks/pre-mount/prepare-root-partition.sh @@ -1,4 +1,7 @@ +#!/usr/bin/env bash +( # subshell for variable scoping # region imports +source /lib/dracut-lib.sh source "/usr/lib/rebash/core.sh" core.import exceptions exceptions.activate @@ -8,54 +11,82 @@ logging.set_commands_log_level debug logging.set_log_level debug # endregion +SLX_SERVER_BASE="$(getargs slxbase=)" +source /etc/openslx + # region connect dnbd3 -local IFS_backup="$IFS" +IFS_backup="$IFS" IFS="," -local host +return_code=1 for host in ${SLX_DNBD3_SERVERS}; do logging.info "Trying host '$host'." if systemd-preserve-process-marker dnbd3-client --host "$host" --image \ "${SLX_SERVER_BASE#/}${SLX_DNBD3_IMAGE}" --device "$SLX_DNBD3_DEVICE" \ --rid "$SLX_DNBD3_RID" then + return_code=0 break fi done IFS="$IFS_backup" if [[ $return_code != 0 ]]; then - warn "Failed to connect '${SLX_SERVER_BASE#/}${SLX_DNBD3_IMAGE}' from" \ + logging.warn "Failed to connect '${SLX_SERVER_BASE#/}${SLX_DNBD3_IMAGE}' from" \ "one of '$SLX_DNBD3_SERVERS' to '$SLX_DNBD3_DEVICE'." - emergency_shell -n "Error in $0" - return 1 + exit 1 fi # endregion # region detect read-only partition -local read_only_device="$SLX_DNBD3_DEVICE" +read_only_device="$SLX_DNBD3_DEVICE" if ! qemu-img info --output json "$read_only_device" | grep '"format": "raw"' then read_only_device='/dev/nbd0' systemd-preserve-process-marker qemu-nbd --connect="$read_only_device" \ - "$SLX_DNBD3_DEVICE" --read-only + "$SLX_DNBD3_DEVICE" --read-only --persistent + + # XXX better way to wait for the device to be made? + i=0 + while [ ! -b "$read_only_device" ]; do + [ $i -ge 20 ] && exit 1 + if [ $UDEVVERSION -ge 143 ]; then + udevadm settle --exit-if-exists="$read_only_device" + else + sleep 0.1 + fi + i=$(($i + 1)) + done + + # NBD doesn't emit uevents when it gets connected, so kick it + echo change > /sys/block/nbd0/uevent + udevadm settle # wait for partitions TODO make nicer :) + #touch $read_only_device + #udevadm settle +else + # workaround to detect partitions on raw disks + # can be omited when the dnbd3 kernel module supports it (like the nbd + # kernel module with parameter 'max_part') + loop_device="$(losetup -f)" touch $read_only_device + losetup "$loop_device" "$read_only_device" --partscan udevadm settle + read_only_device="$loop_device" fi -local read_only_partition -if ! read_only_partition=$(utils.find_block_device \ - "$SLX_SYSTEM_PARTITION_IDENTIFIER" "$read_only_device"); then - logging.warn "Failed to find unique device with identifier" \ +while ! read_only_partition=$(utils.find_block_device \ + "$SLX_SYSTEM_PARTITION_IDENTIFIER" "$read_only_device"); do +#if ! read_only_partition=$(utils.find_block_device \ + #"$SLX_SYSTEM_PARTITION_IDENTIFIER" "$read_only_device"); then + logging.warn "Trying to find unique device with identifier" \ "'${SLX_SYSTEM_PARTITION_IDENTIFIER}'; matched devices:" \ "'${read_only_partition}'" - emergency_shell -fi + sleep 0.5 +done # endregion # region detect writable partition -local persistent_device if ! persistent_device=$(utils.find_block_device \ "$SLX_WRITABLE_DEVICE_IDENTIFIER"); then logging.warn "Failed to find unique device with identifier" \ @@ -64,22 +95,21 @@ if ! persistent_device=$(utils.find_block_device \ fi # TODO move somewhere else -#local tmp_device="$(utils.find_block_device \ +#tmp_device="$(utils.find_block_device \ #'$SLX_TMP_PARTITION_IDENTIFIER')" #if [ -n $tmp_device ]; then #mount --type auto "$tmp_device" "$NEWROOT/tmp" #fi -local persistent='N' # 'P' for persistent storage, 'N' for not persistent -local writable_device +persistent='N' # 'P' for persistent storage, 'N' for not persistent if [ -n "$persistent_device" ]; then writable_device="$persistent_device" if [ "$SLX_WRITABLE_DEVICE_PERSISTENT" = "yes" ]; then persistent='P' fi else - local ramdisk_size="$SLX_RAMDISK_SIZE" + ramdisk_size="$SLX_RAMDISK_SIZE" if [ "$ramdisk_size" = "" ]; then ramdisk_size="$(cat /proc/meminfo | awk '/MemTotal/ {print $2}')" fi @@ -97,18 +127,18 @@ fi # endregion # region combine devices with device mapper -local partition_size="$(blockdev --getsz "$read_only_partition")" -local writable_partition_name='root' +partition_size="$(blockdev --getsz "$read_only_partition")" +writable_partition_name='root' logging.info "Using read-only device: $read_only_partition" logging.info "Using writable device $writable_device, persistency: $persistent" -local chunksize='1' +chunksize='1' modprobe dm_snapshot dmsetup create "$writable_partition_name" --noudevsync --table \ "0 $partition_size snapshot $read_only_partition $writable_device $persistent $chunksize" dmsetup mknodes --noudevsync "$writable_partition_name" exceptions.deactivate -# enregion - +# endregion +) || exit $? # region vim modline # vim: set tabstop=4 shiftwidth=4 expandtab: diff --git a/builder/dnbd3-rootfs/scripts/rebash b/builder/dnbd3-rootfs/scripts/rebash index 5a708c0c..b77bbd65 160000 --- a/builder/dnbd3-rootfs/scripts/rebash +++ b/builder/dnbd3-rootfs/scripts/rebash @@ -1 +1 @@ -Subproject commit 5a708c0c68be05b50fdb77d211912110f910c519 +Subproject commit b77bbd65f70f56c5941f0368c2e488c470072af2 -- cgit v1.2.3-55-g7522