# bash command-line completion for virtualbox # # This version of bash completion was born due to the need of fast and easy # access to the maze of commands and parameters VBoxManage provides. Based on # Sebastian[1] script I've managed to improve it and adapt to newest stable # version available in Gentoo Portage. # # [1] Sebastian T. Hafner # # [ ] extpack # [ ] getextradata # [ ] guestcontrol # [ ] guestproperty # [ ] hostonlyif # [ ] import # [ ] metrics # [ ] modifyhd # [ ] modifyvm # [ ] natnetwork # [ ] registervm # [ ] setextradata # [ ] setproperty # [ ] sharedfolder _VBoxManage() { local cur prev opts cmd subcommand tmp items name index result # Generate registered hard disk files. # NOTE: This function may introduce some quirks, if there is a space or # other characters which usually are treated as IFS - like space. Pipe # character used in disk filename will ruin this completions. _hdd_comp() { local cur=$1 local hdds local item hdds=$(VBoxManage list hdds | \ grep -A 1 'normal (base)' | \ grep "Location:" | \ sed 's/Location:\s\+//' | \ sed 's/\s/\\ /g' | \ tr '\n' '|' | \ sed 's/|$//') IFS='|' read -ra hdds <<< "$hdds" for item in "${hdds[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _floppy_comp() { local cur=$1 local floppies local item floppies=$(VBoxManage list floppies | \ grep "Location:" | \ sed 's/Location:\s\+//' | \ sed 's/\s/\\ /g' | \ tr '\n' '|' | \ sed 's/|$//') IFS='|' read -ra floppies <<< "$floppies" for item in "${floppies[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _dvds_comp() { local cur=$1 local dvds local item dvds=$(VBoxManage list dvds | \ grep "Location:" | \ sed 's/Location:\s\+//' | \ sed 's/\s/\\ /g' | \ tr '\n' '|' | \ sed 's/|$//') IFS='|' read -ra dvds <<< "$dvds" for item in "${dvds[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } # Complete registered VM names. # Issues are the same as in above function. _vms_comp() { local command=$1 local cur=$2 local vms local item compopt -o filenames vms=$(VBoxManage list $command | \ awk -F ' {' '{ print $1 }' | \ tr '\n' '|' | \ sed 's/|$//' | \ sed 's/"//g') IFS='|' read -ra vms <<< "$vms" for item in "${vms[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _vms_state_comp() { local command=$1 local cur=$2 local vms local item compopt -o filenames vms=$(VBoxManage list vms -l | \ egrep '^Name|State' | \ egrep -B1 'State:\s+saved' | \ grep Name |sed 's/Name:\s\+//' | \ tr '\n' '|' | \ sed 's/|$//' | \ sed 's/"//g') IFS='|' read -ra vms <<< "$vms" for item in "${vms[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _list_comp() { local cur=$1 local list list=$(VBoxManage list | \ grep '|' | \ sed 's/\[.*\]//g'| \ sed 's/VBoxManage list//' | \ tr "\\n" " " | \ sed 's/$/\n/' | \ sed 's/\s\+//g' | \ sed 's/|/ /g') COMPREPLY=( $(compgen -W "$list" -- ${cur}) ) } _group_comp() { local cur=$1 local list local item list=$(VBoxManage list groups | \ tr '\n' '|' | \ sed 's/|$//' | \ sed 's/\s/\\ /g'| \ sed 's/"//g') IFS='|' read -ra list <<< "$list" for item in "${list[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _os_comp() { local cur=$1 local list local item list=$(VBoxManage list ostypes | \ egrep ^ID: | \ sed 's/ID:\s\+//' | \ tr '\n' '|' | \ sed 's/|$//') IFS='|' read -ra list <<< "$list" for item in "${list[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _dhcp_comp() { local cur=$1 local list local item list=$(VBoxManage list dhcpservers | \ grep NetworkName: | \ sed 's/NetworkName:\s\+//' | \ sed 's/\s/\\ /g'| \ tr '\n' '|' | \ sed 's/|$//') IFS='|' read -ra list <<< "$list" for item in "${list[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _hostonlyif_comp() { local cur=$1 local list local item list=$(VBoxManage list hostonlyifs | \ egrep ^Name: | \ sed 's/Name:\s\+//' | \ sed 's/\s/\\ /g'| \ tr '\n' '|' | \ sed 's/|$//') IFS='|' read -ra list <<< "$list" for item in "${list[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } # Check the COMP_WORDS looking for name of the vm. If name contain space or # is enclosed in quotes, glue name together in variable name. Variable index # will hold the last index of COMP_WORDS array which contain the end of the # name. _find_item_name() { local idx=$1 name="" while true do name="${name}${COMP_WORDS[$idx]}" [[ ${COMP_WORDS[$idx]} = *'"' ]] && break if [[ ${COMP_WORDS[$idx]} = '"'* || ${COMP_WORDS[$idx]} = *'\ ' ]] then idx=$((++idx)) continue fi break done index=$idx } _get_excluded_items() { local i result="" for i in $@; do [[ " ${COMP_WORDS[@]} " == *" $i "* ]] && continue result="$result $i" done } _bandwidthctl_comp() { local rules cur=$1 local item _find_item_name 2 rules=$(VBoxManage bandwidthctl "${name//\\/}" \ list --machinereadable | \ awk -F ',' '{print $1}' | \ awk -F '=' '{print $2}' | \ tr '\n' '|' | \ sed 's/|$//' | \ sed 's/\s/\\ /g') IFS='|' read -ra rules <<< "$rules" for item in "${rules[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _snapshot_comp() { local snap cur=$1 local item _find_item_name 2 snap=$(VBoxManage snapshot "${name//\\/}" \ list | \ grep UUID | awk -F ': ' '{print $2}' | \ sed 's/ (.*//' | \ tr '\n' '|' | \ sed 's/|$//' | \ sed 's/\s/\\ /g') IFS='|' read -ra snap <<< "$snap" for item in "${snap[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _webcam_comp() { local devs cur=$1 local item _find_item_name 2 devs=$(VBoxManage controlvm "${name//\\/}" \ webcam list | \ tr '\n' ' ' | \ sed 's/|s$//') read -ra devs <<< "$devs" for item in "${devs[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _webcam_avail_comp() { local devs cur=$1 local item _find_item_name 2 devs=$(VBoxManage list webcams | \ grep dev | \ tr '\n' ' ' | \ sed 's/|s$//') read -ra devs <<< "$devs" for item in "${devs[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done } _list_comp() { local list list=$(VBoxManage list | \ grep '|' | \ sed 's/\[.*\]//g'| \ sed 's/VBoxManage list//' | \ tr "\\n" " " | \ sed 's/$/\n/' | \ sed 's/\s\+//g' | \ sed 's/|/ /g') COMPREPLY=( $(compgen -W "$list" -- ${cur}) ) } COMP_WORDBREAKS=${COMP_WORDBREAKS//|/} # remove pipe from comp word breaks COMPREPLY=() cur="${COMP_WORDS[COMP_CWORD]}" prev="${COMP_WORDS[COMP_CWORD-1]}" lastbutone="${COMP_WORDS[COMP_CWORD-2]}" if [[ COMP_CWORD -ge 2 ]]; then cmd="${COMP_WORDS[1]}" if [[ $cmd == "-q" ]]; then cmd="${COMP_WORDS[2]}" fi fi # all possible commands for the VBoxManage opts=$(VBoxManage -q help | \ egrep -o "^\s\s[a-z]+ " | \ grep -v VBoxManage | \ awk '{print $1}'| \ sort | \ uniq) if [[ ${cur} == "-q" || ${COMP_CWORD} -eq 1 ]] ; then COMPREPLY=( $(compgen -W "${opts}" -- ${cur}) ) return 0 fi case "${cmd}" in adoptstate) _find_item_name 2 COMPREPLY=() [[ -z "${name}" ]] && _vms_state_comp ${cur} ;; bandwidthctl) local items=(add set remove list) if [[ ${prev} == ${cmd} ]]; then _vms_comp vms ${cur} else _find_item_name 2 subcommand=${COMP_WORDS[$((index+1))]} if [[ " ${items[@]} " == *" $subcommand "* ]]; then case "${subcommand}" in add) items=(--type --limit) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; set) if [[ ${prev} == "set" ]]; then _bandwidthctl_comp ${cur} else [[ " ${COMP_WORDS[@]} " != *" --limit "* ]] && \ COMPREPLY=( $(compgen -W "--limit" -- \ ${cur}) ) fi ;; remove) if [[ ${prev} == "remove" ]]; then _bandwidthctl_comp ${cur} fi ;; list) if [[ ${prev} == "list" ]]; then COMPREPLY=( $(compgen -W "--machinereadable" \ -- ${cur}) ) fi ;; esac case "${prev}" in --type) COMPREPLY=( $(compgen -W "disk network" -- ${cur}) ) ;; esac else [[ ${#COMPREPLY[@]} -eq 0 ]] && \ COMPREPLY=( $(compgen -W "${items[*]}" -- ${cur}) ) fi fi ;; clonehd) if [[ ${prev} == ${cmd} ]]; then _hdd_comp ${cur} else _find_item_name 2 items=(--format --variant --existing) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) case "${prev}" in --format) COMPREPLY=( $(compgen -W "VDI VMDK VHD RAW" -- ${cur}) ) ;; --variant) COMPREPLY=( $(compgen -W "Standard Fixed Split2G Stream ESX" -- ${cur}) ) ;; esac fi ;; clonevm) if [[ ${prev} == ${cmd} ]]; then _vms_comp vms ${cur} else _find_item_name 2 items=(--snapshot --mode --options --name --groups --basefolder --uuid --register) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) case "${prev}" in --snapshot) COMPREPLY=() _snapshot_comp ${cur} ;; --mode) COMPREPLY=( $(compgen -W "machine machineandchildren all" -- ${cur}) ) ;; --options) COMPREPLY=( $(compgen -W "link keepallmacs keepnatmacs keepdisknames" -- ${cur}) ) ;; --groups) COMPREPLY=() _group_comp ${cur} ;; --basefolder) COMPREPLY=( $(compgen -o dirnames -- ${cur}) ) ;; esac fi ;; closemedium) if [[ ${prev} == ${cmd} ]]; then COMPREPLY=( $(compgen -W "disk dvd floppy" -- ${cur}) ) else case "${prev}" in disk) _hdd_comp ${cur} ;; dvd) _dvds_comp ${cur} ;; floppy) _floppy_comp ${cur} ;; *) items=(--delete) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; esac fi ;; controlvm) if [[ ${prev} == ${cmd} ]]; then _vms_comp runningvms ${cur} else local items=(acpipowerbutton acpisleepbutton clipboard cpuexecutioncap draganddrop guestmemoryballoon keyboardputscancode natpf1 nic1 nicpromisc1 nicproperty1 nictrace1 nictracefile1 natpf2 nic2 nicpromisc2 nicproperty2 nictrace2 nictracefile2 natpf3 nic3 nicpromisc3 nicproperty3 nictrace3 nictracefile3 natpf4 nic4 nicpromisc4 nicproperty4 nictrace4 nictracefile4 natpf5 nic5 nicpromisc5 nicproperty5 nictrace5 nictracefile5 natpf6 nic6 nicpromisc6 nicproperty6 nictrace6 nictracefile6 natpf7 nic7 nicpromisc7 nicproperty7 nictrace7 nictracefile7 natpf8 nic8 nicpromisc8 nicproperty8 nictrace8 pause plugcpu poweroff reset resume savestate screenshotpng setcredentials setlinkstate1 setlinkstate2 setlinkstate3 setlinkstate4 setlinkstate5 setlinkstate6 setlinkstate7 setlinkstate8 setvideomodehint teleport unplugcpu usbattach usbdetach vcpenabled vcpscreens vrde vrdeport vrdeproperty vrdevideochannelquality webcam) _find_item_name 2 subcommand=${COMP_WORDS[$((index+1))]} if [[ " ${items[@]} " == *" $subcommand "* ]]; then case "${subcommand}" in nictracefile[1-8]) [[ ${prev} == "nictracefile"* ]] && \ COMPREPLY=( $(compgen -f -- ${cur}) ) ;; nictrace[1-8]) [[ ${prev} == "nictrace"* ]] && \ COMPREPLY=( $(compgen -W "on off" -- ${cur}) ) ;; nicpromisc[1-8]) [[ ${prev} == "nicpromisc"* ]] && \ COMPREPLY=( $(compgen -W "deny allow-vms allow-all" -- ${cur}) ) ;; nic[1-8]) [[ ${prev} == "nic"* ]] && \ COMPREPLY=( $(compgen -W "null nat bridged intnet hostonly generic natnetwork" -- ${cur}) ) ;; natpf[1-8]) [[ ${prev} == "natpf"* ]] && \ COMPREPLY=( $(compgen -W "delete tcp udp" -- ${cur}) ) ;; setlinkstate[1-8]) [[ ${prev} == "setlinkstate"* ]] && \ COMPREPLY=( $(compgen -W "on off" -- ${cur}) ) ;; clipboard) [[ ${prev} == "clipboard" ]] && \ COMPREPLY=( $(compgen -W "disabled hosttoguest guesttohost bidirectional" -- ${cur}) ) ;; draganddrop) [[ ${prev} == "draganddrop" ]] && \ COMPREPLY=( $(compgen -W "disabled hosttoguest" -- ${cur}) ) ;; vrde|vcpenabled) [[ ${prev} == "vrde" || ${prev} == "vcpenabled" ]] && \ COMPREPLY=( $(compgen -W "on off" -- ${cur}) ) ;; vcpscreens) [[ ${prev} == "vcpscreens" ]] && \ COMPREPLY=( $(compgen -W "all none" -- ${cur}) ) ;; setcredentials) tmp=(--passwordfile --allowlocallogon) _get_excluded_items "${tmp[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; teleport) tmp=(--host --port --maxdowntime --passwordfile --password) _get_excluded_items "${tmp[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; webcam) [[ ${prev} == "webcam" ]] && \ COMPREPLY=( $(compgen -W "attach detach list" -- ${cur}) ) [[ ${prev} == "detach" ]] && \ _webcam_comp ${cur} [[ ${prev} == "attach" ]] && \ _webcam_avail_comp ${cur} ;; esac else [[ ${#COMPREPLY[@]} -eq 0 ]] && \ COMPREPLY=( $(compgen -W "${items[*]}" -- ${cur}) ) fi fi ;; convertfromraw) local items=(--format --variant --uuid) if [[ ${prev} == ${cmd} ]]; then COMPREPLY=( $(compgen -W "${items[*]}" -- ${cur}) ) else _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) case "${prev}" in --format) COMPREPLY=( $(compgen -W "VDI VMDK VHD" -- ${cur}) ) ;; --variant) COMPREPLY=( $(compgen -W "Standard Fixed Split2G Stream ESX" -- ${cur}) ) ;; esac fi ;; createhd) items=(--filename --size --sizebyte --diffparent --format --variant) if [[ ${prev} == ${cmd} ]]; then COMPREPLY=( $(compgen -W "${items[*]}" -- ${cur}) ) else [[ " ${COMP_WORDS[@]} " == *" --size "* || " ${COMP_WORDS[@]} " == *" --sizebyte "* ]] && items=(--filename --diffparent --format --variant) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) case "${prev}" in --filename) COMPREPLY=( $(compgen -- ${cur}) ) ;; --diffparent) COMPREPLY=() _hdd_comp ${cur} ;; --format) COMPREPLY=( $(compgen -W "VDI VMDK VHD" -- ${cur}) ) ;; --variant) COMPREPLY=( $(compgen -W "Standard Fixed Split2G Stream ESX" -- ${cur}) ) ;; esac fi ;; createvm) items=(--name --groups --ostype --register --basefolder --uuid) if [[ ${prev} == ${cmd} ]]; then COMPREPLY=( $(compgen -W "${items[*]}" -- ${cur}) ) else _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) case "${prev}" in --groups) COMPREPLY=() _group_comp ${cur} ;; --ostype) COMPREPLY=() _os_comp ${cur} ;; --basefolder) COMPREPLY=( $(compgen -o dirnames -- ${cur}) ) ;; --variant) COMPREPLY=( $(compgen -W "Standard Fixed Split2G Stream ESX" -- ${cur}) ) ;; esac fi ;; debugvm) items=(dumpguestcore info injectnmi log logdest logflags osdetect osinfo getregisters setregisters show statistics) if [[ ${prev} == ${cmd} ]]; then _vms_comp runningvms ${cur} else _find_item_name 2 subcommand=${COMP_WORDS[$((index+1))]} if [[ " ${items[@]} " == *" $subcommand "* ]]; then case "${subcommand}" in dumpguestcore) _get_excluded_items "--filename" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; log|logdest|logflags) items=(--release --debug) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; getregisters|setregisters) _get_excluded_items "--cpu" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; show) items=(--human-readable --sh-export --sh-eval --cmd-set) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; statistics) items=(--reset --pattern) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; esac _get_excluded_items "--descriptions" COMPREPLY+=( $(compgen -W "$result" -- ${cur}) ) else [[ "${prev}" == "--filename" ]] && \ COMPREPLY=( $(compgen -- ${cur}) ) [[ ${#COMPREPLY[@]} -eq 0 ]] && \ COMPREPLY=( $(compgen -W "${items[*]}" -- ${cur}) ) fi fi ;; dhcpserver) items=(add modify remove) subcommand=${COMP_WORDS[2]} if [[ " ${items[@]} " == *" $subcommand "* ]]; then case "${subcommand}" in add|modify) items=(--ip --netmask --lowerip --upperip) [[ " ${COMP_WORDS[@]} " != *" --ifname"* && " ${COMP_WORDS[@]} " != *" --netname"* ]] && items+=(--netname --ifname) [[ " ${COMP_WORDS[@]} " != *" --enable"* && " ${COMP_WORDS[@]} " != *" --disable"* ]] && items+=(--enable --disable) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; remove) case "${prev}" in --netname) COMPREPLY=() _dhcp_comp ${cur} ;; --ifname) COMPREPLY=() _hostonlyif_comp ${cur} ;; esac if [[ " ${COMP_WORDS[@]} " != *" --ifname"* && " ${COMP_WORDS[@]} " != *" --netname"* ]]; then items=(--netname --ifname) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) fi ;; esac else [[ ${#COMPREPLY[@]} -eq 0 ]] && \ COMPREPLY=( $(compgen -W "${items[*]}" -- ${cur}) ) fi ;; discardstate) _find_item_name 2 COMPREPLY=() [[ -z "${name}" ]] && _vms_state_comp ${cur} ;; "export") items=( --manifest --iso --options --vsys) if [[ ${prev} == ${cmd} ]]; then _vms_comp vms ${cur} else [[ " ${COMP_WORDS[@]} " != *" -o "* && " ${COMP_WORDS[@]} " != *" --output "* ]] && items+=(-o --output) [[ " ${COMP_WORDS[@]} " != *" --legacy09 "* && " ${COMP_WORDS[@]} " != *" --ovf09 "* && " ${COMP_WORDS[@]} " != *" --ovf10 "* && " ${COMP_WORDS[@]} " != *" --ovf20 "* ]] && items+=(--legacy09 --ovf09 --ovf10 --ovf20) [[ " ${COMP_WORDS[@]} " == *" --vsys "* ]] && items+=(--product --producturl --vendor --vendorurl --version --description --eula --eulafile) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) case "${prev}" in --options) COMPREPLY=( $(compgen -W "manifest iso nomacs nomacsbutnat" -- ${cur}) ) ;; esac [[ ${#COMPREPLY[@]} -eq 0 ]] && \ COMPREPLY=( $(compgen -W "${items[*]}" -- ${cur}) ) fi ;; extpack) ;; getextradata) ;; guestcontrol) ;; guestproperty) ;; hostonlyif) ;; import) ;; list) if [[ ${prev} == ${cmd} ]]; then _list_comp ${cur} else case "${prev}" in --long|-l) COMPREPLY=() ;; *) COMPREPLY=( $(compgen -W "-l --long" -- ${cur}) ) ;; esac fi ;; metrics) ;; modifyhd) ;; modifyvm) ;; natnetwork) ;; registervm) ;; setextradata) ;; setproperty) ;; sharedfolder) ;; showhdinfo) _hdd_comp ${cur} ;; showvminfo) if [[ ${prev} == ${cmd} ]]; then _vms_comp vms ${cur} else if [[ " ${COMP_WORDS[@]} " == *" --log "* ]]; then COMPREPLY=() elif [[ " ${COMP_WORDS[@]} " == *" --details "* || " ${COMP_WORDS[@]} " == *" --machinereadable "* ]]; then local items=(--details --machinereadable) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) else local items=(--details --machinereadable --log) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) fi fi ;; snapshot) items=(take delete restore restorecurrent edit list showvminfo) if [[ ${prev} == ${cmd} ]]; then _vms_comp vms ${cur} else _find_item_name 2 subcommand=${COMP_WORDS[$((index+1))]} if [[ " ${items[@]} " == *" $subcommand "* ]]; then case "${subcommand}" in take) items=(--description --live) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; delete|restore|showvminfo) _snapshot_comp ${cur} ;; restorecurrent) COMPREPLY=() ;; edit) if [[ ${prev} == "edit" && ${#COMP_WORDS[@]} == 5 ]]; then _snapshot_comp ${cur} COMPREPLY+=("--current") else items=(--name --description) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) fi ;; list) items=(--details --machinereadable) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; esac else [[ ${#COMPREPLY[@]} -eq 0 ]] && \ COMPREPLY=( $(compgen -W "${items[*]}" -- ${cur}) ) fi fi ;; startvm) if [[ ${prev} == ${cmd} ]]; then _vms_comp vms ${cur} elif [[ "${prev}" == "--type" ]]; then COMPREPLY=( $(compgen -W "gui sdl headless" -- ${cur}) ) else local items=(--type) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) fi ;; storageattach) if [[ ${prev} == ${cmd} ]]; then _vms_comp vms ${cur} else _find_item_name 2 local items=(--storagectl --port --device --type --medium --mtype --comment --setuuid --setparentuuid --passthrough --tempeject --nonrotational --discard --bandwidthgroup --forceunmount --server --target --tport --lun --encodedlun --username --password --initiator --intnet) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) case "${prev}" in --type) COMPREPLY=( $(compgen -W "dvddrive hdd fdd" -- ${cur}) ) ;; --medium) COMPREPLY=() local tmp=(none emptydrive additions) _hdd_comp ${cur} _floppy_comp ${cur} _dvds_comp ${cur} for item in "${tmp[@]}" do [[ ${item^^} == ${cur^^}* ]] && COMPREPLY+=("$item") done ;; --mtype) COMPREPLY=( $(compgen -W "normal writethrough immutable shareable readonly multiattach" -- ${cur}) ) ;; --passthrough|--tempeject|--nonrotational|--discard) COMPREPLY=( $(compgen -W "on off" -- ${cur}) ) ;; esac fi ;; storagectl) local items=(--name --add --controller --portcount --hostiocache --bootable --remove) if [[ ${prev} == ${cmd} ]]; then _vms_comp vms ${cur} else _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) case "${prev}" in --add) COMPREPLY=( $(compgen -W "ide sata scsi floppy sas" -- ${cur}) ) ;; --controller) COMPREPLY=( $(compgen -W "LSILogic LSILogicSAS BusLogic IntelAHCI PIIX3 PIIX4 ICH6 I82078" -- ${cur}) ) ;; --bootable|--hostiocache) COMPREPLY=( $(compgen -W "on off" -- ${cur}) ) ;; esac fi ;; unregistervm) if [[ ${prev} == ${cmd} ]]; then _vms_comp vms ${cur} else local items=(--delete) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) fi ;; usbfilter) if [[ COMP_CWORD -ge 3 ]]; then subcommand="${COMP_WORDS[2]}" if [[ $subcommand == "${cmd}" ]]; then subcommand="${COMP_WORDS[3]}" fi fi if [[ ${prev} == ${cmd} ]]; then COMPREPLY=( $(compgen -W "add modify remove" -- ${cur}) ) else case "${prev}" in --target) _vms_comp vms ${cur} COMPREPLY+=( $(compgen -W "global" -- ${cur}) ) ;; --action) COMPREPLY=( $(compgen -W "ignore hold" -- ${cur}) ) ;; --active|--remote) COMPREPLY=( $(compgen -W "yes no" -- ${cur}) ) ;; esac if [[ ${#COMPREPLY[@]} -eq 0 ]]; then case "${subcommand}" in add|modify) local items=(--target --name --action --active --vendorid --productid --revision --manufacturer --product --remote --serialnumber --maskedinterfaces) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; remove) local items=(--target) _get_excluded_items "${items[@]}" COMPREPLY=( $(compgen -W "$result" -- ${cur}) ) ;; esac fi fi ;; esac } complete -o default -F _VBoxManage VBoxManage # vim: set ft=sh tw=80 sw=4 et :