#!/bin/bash set -eux action="$1" vm="$2" device="${3-0}" part="${4-}" function xe_min() { local cmd="$1" shift xe "$cmd" --minimal "$@" } function run_udev_settle() { which_udev=$(which udevsettle) || true if [ -n "$which_udev" ]; then udevsettle else udevadm settle fi } vm_uuid=$(xe_min vm-list name-label="$vm") vdi_uuid=$(xe_min vbd-list params=vdi-uuid vm-uuid="$vm_uuid" \ userdevice="$device") dom0_uuid=$(xe_min vm-list is-control-domain=true) function get_mount_device() { vbd_uuid=$1 dev=$(xe_min vbd-list params=device uuid="$vbd_uuid") if [[ "$dev" =~ "sm/" ]]; then DEBIAN_FRONTEND=noninteractive \ apt-get --option "Dpkg::Options::=--force-confold" --assume-yes \ install kpartx &> /dev/null || true mapping=$(kpartx -av "/dev/$dev" | sed -ne 's,^add map \([a-z0-9\-]*\).*$,\1,p' | sed -ne "s,^\(.*${part}\)\$,\1,p") if [ -z "$mapping" ]; then echo "Failed to find mapping" exit -1 fi echo "/dev/mapper/${mapping}" else echo "/dev/$dev$part" fi } function clean_dev_mappings() { dev=$(xe_min vbd-list params=device uuid="$vbd_uuid") if [[ "$dev" =~ "sm/" ]]; then kpartx -dv "/dev/$dev" fi } function open_vdi() { vbd_uuid=$(xe vbd-create vm-uuid="$dom0_uuid" vdi-uuid="$vdi_uuid" \ device=autodetect) mp=$(mktemp -d) xe vbd-plug uuid="$vbd_uuid" run_udev_settle mount_device=$(get_mount_device "$vbd_uuid") mount "$mount_device" "$mp" echo "Your vdi is mounted at $mp" } function close_vdi() { vbd_uuid=$(xe_min vbd-list vm-uuid="$dom0_uuid" vdi-uuid="$vdi_uuid") mount_device=$(get_mount_device "$vbd_uuid") run_udev_settle umount "$mount_device" clean_dev_mappings xe vbd-unplug uuid=$vbd_uuid xe vbd-destroy uuid=$vbd_uuid } if [ "$action" == "open" ]; then open_vdi elif [ "$action" == "close" ]; then close_vdi fi