Use entire PCI device range

Previously, vm-bhyve only distributed devices on PCI bus 0,
despite bhyve supporting multiple PCI buses. This limited the
number of virtual devices a VM could use.

This commit addresses that issue by using the entire range of
PCI buses.
This commit is contained in:
Arne Steinkamm
2025-01-06 13:29:20 +01:00
committed by Mariusz Zaborski
parent dc92eeaae9
commit 0ca0b56c79
4 changed files with 82 additions and 16 deletions

View File

@@ -36,7 +36,7 @@ vm::run(){
local _name _iso _iso_dev local _name _iso _iso_dev
local _cpu _memory _bootdisk _bootdisk_dev _guest _wiredmem local _cpu _memory _bootdisk _bootdisk_dev _guest _wiredmem
local _guest_support _uefi _uuid _debug _hostbridge _loader local _guest_support _uefi _uuid _debug _hostbridge _loader
local _opts _devices _slot _install_slot _func=0 _taplist _exit _passdev local _opts _devices _slot _bus=0 _maxslots=31 _install_slot _func=0 _taplist _exit _passdev
local _com _comports _comstring _logpath="/dev/null" _run=1 local _com _comports _comstring _logpath="/dev/null" _run=1
local _bhyve_options _action local _bhyve_options _action
@@ -220,6 +220,10 @@ vm::run(){
fi fi
fi fi
if [ ${_bus} -ge 1 ]; then
_opts="${_opts} -Y"
fi
util::log "guest" "${_name}" " [bhyve options: ${_opts}]" \ util::log "guest" "${_name}" " [bhyve options: ${_opts}]" \
" [bhyve devices: ${_devices}]" \ " [bhyve devices: ${_devices}]" \
" [bhyve console: ${_comstring}]" " [bhyve console: ${_comstring}]"
@@ -444,7 +448,7 @@ vm::bhyve_device_basic(){
# this can be overridden by setting the ahci_device_limit # this can be overridden by setting the ahci_device_limit
# guest option to an integer between 2 and 32. # guest option to an integer between 2 and 32.
# #
# @modifies _devices _slot # @modifies _devices _slot _bus
# #
vm::bhyve_device_disks(){ vm::bhyve_device_disks(){
local _disk _type _dev _path _opts _ahci _atype local _disk _type _dev _path _opts _ahci _atype
@@ -481,6 +485,11 @@ vm::bhyve_device_disks(){
_func=0 _func=0
_slot=$((_slot + 1)) _slot=$((_slot + 1))
fi fi
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
vm::get_disk_path "_path" "${_name}" "${_disk}" "${_dev}" vm::get_disk_path "_path" "${_name}" "${_disk}" "${_dev}"
@@ -500,7 +509,7 @@ vm::bhyve_device_disks(){
# we need to move to another controller if we get to the limit # we need to move to another controller if we get to the limit
if [ ${_ahci_num} -ge ${_ahci_limit} ]; then if [ ${_ahci_num} -ge ${_ahci_limit} ]; then
_devices="${_devices} -s ${_slot}:${_func},ahci${_ahci}" _devices="${_devices} -s ${_bus}:${_slot}:${_func},ahci${_ahci}"
_ahci="" _ahci=""
_ahci_num=0 _ahci_num=0
_add=1 _add=1
@@ -511,7 +520,7 @@ vm::bhyve_device_disks(){
_atype="" _atype=""
else else
_devices="${_devices} -s ${_slot}:${_func},${_type},${_path}" _devices="${_devices} -s ${_bus}:${_slot}:${_func},${_type},${_path}"
[ -n "${_opts}" ] && _devices="${_devices},${_opts}" [ -n "${_opts}" ] && _devices="${_devices},${_opts}"
_add=1 _add=1
fi fi
@@ -528,6 +537,12 @@ vm::bhyve_device_disks(){
_add="" _add=""
fi fi
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
_num=$((_num + 1)) _num=$((_num + 1))
done done
@@ -543,6 +558,11 @@ vm::bhyve_device_disks(){
_slot=$((_slot + 1)) _slot=$((_slot + 1))
_func=0 _func=0
fi fi
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
} }
# get bhyve device string for networking # get bhyve device string for networking
@@ -551,7 +571,7 @@ vm::bhyve_device_disks(){
# we add each tap to __taplist from vm::run which it will # we add each tap to __taplist from vm::run which it will
# use to desstroy them all on shutdown # use to desstroy them all on shutdown
# #
# @modifies _devices _slot _taplist _func # @modifies _devices _slot _bus _taplist _func
# #
vm::bhyve_device_networking(){ vm::bhyve_device_networking(){
local _emulation _num=0 local _emulation _num=0
@@ -565,6 +585,11 @@ vm::bhyve_device_networking(){
_func=0 _func=0
_slot=$((_slot + 1)) _slot=$((_slot + 1))
fi fi
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
switch::provision switch::provision
_num=$((_num + 1)) _num=$((_num + 1))
@@ -574,6 +599,11 @@ vm::bhyve_device_networking(){
_slot=$((_slot + 1)) _slot=$((_slot + 1))
_func=0 _func=0
fi fi
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
} }
# check if user wants a virtio-rand device # check if user wants a virtio-rand device
@@ -583,9 +613,14 @@ vm::bhyve_device_networking(){
vm::bhyve_device_rand(){ vm::bhyve_device_rand(){
if config::yesno "virt_random"; then if config::yesno "virt_random"; then
_devices="${_devices} -s ${_slot}:0,virtio-rnd" _devices="${_devices} -s ${_bus}:${_slot}:0,virtio-rnd"
_slot=$((_slot + 1)) _slot=$((_slot + 1))
fi fi
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
} }
# add frame buffer output # add frame buffer output
@@ -641,8 +676,13 @@ vm::bhyve_device_fbuf(){
echo "vnc=${_listen:-0.0.0.0}:${_port}" >> "${VM_DS_PATH}/${_name}/console" echo "vnc=${_listen:-0.0.0.0}:${_port}" >> "${VM_DS_PATH}/${_name}/console"
# add device # add device
_devices="${_devices} -s ${_slot}:0,fbuf,${_fbuf_conf}" _devices="${_devices} -s ${_bus}:${_slot}:0,fbuf,${_fbuf_conf}"
_slot=$((_slot + 1)) _slot=$((_slot + 1))
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
} }
# remove wait option if we're in auto mode # remove wait option if we're in auto mode
@@ -669,9 +709,14 @@ vm::bhyve_device_mouse(){
# add a tablet device if enabled # add a tablet device if enabled
if config::yesno "xhci_mouse"; then if config::yesno "xhci_mouse"; then
_devices="${_devices} -s ${_slot}:0,xhci,tablet" _devices="${_devices} -s ${_bus}:${_slot}:0,xhci,tablet"
_slot=$((_slot + 1)) _slot=$((_slot + 1))
fi fi
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
} }
vm::bhyve_device_sound(){ vm::bhyve_device_sound(){
@@ -680,7 +725,7 @@ vm::bhyve_device_sound(){
config::get "_rec" "sound_rec" config::get "_rec" "sound_rec"
if config::yesno "sound"; then if config::yesno "sound"; then
_devices="${_devices} -s ${_slot}:0,hda,play=${_play}" _devices="${_devices} -s ${_bus}:${_slot}:0,hda,play=${_play}"
if [ -n "${_rec}" ]; then if [ -n "${_rec}" ]; then
_devices="${_devices},rec=${_rec}" _devices="${_devices},rec=${_rec}"
@@ -688,6 +733,11 @@ vm::bhyve_device_sound(){
_slot=$((_slot + 1)) _slot=$((_slot + 1))
fi fi
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
} }
# add virtio_console devices to the guest # add virtio_console devices to the guest
@@ -715,15 +765,20 @@ vm::bhyve_device_console(){
config::get "_console" "virt_console${_curr}" config::get "_console" "virt_console${_curr}"
done done
_devices="${_devices} -s ${_slot}:0,virtio-console${_dev_str}" _devices="${_devices} -s ${_bus}:${_slot}:0,virtio-console${_dev_str}"
_slot=$((_slot + 1)) _slot=$((_slot + 1))
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
} }
# get any pci passthrough devices # get any pci passthrough devices
# FreeBSD 11 needs wired memory so update _opts in that case if # FreeBSD 11 needs wired memory so update _opts in that case if
# we have any pass through devices # we have any pass through devices
# #
# @modifies _devices _slot _opts _wiredmem # @modifies _devices _slot _bus _opts _wiredmem
# #
vm::bhyve_device_passthru(){ vm::bhyve_device_passthru(){
local _dev _orig_slot _func=0 local _dev _orig_slot _func=0
@@ -737,7 +792,7 @@ vm::bhyve_device_passthru(){
# see if there's an = sign # see if there's an = sign
# we allow A/B/C=D:E to force D:E as the guest SLOT:FUNC # we allow A/B/C=D:E to force D:E as the guest SLOT:FUNC
if echo "${_dev}" | grep -qs "="; then if echo "${_dev}" | grep -qs "="; then
_devices="${_devices} -s ${_dev##*=},passthru,${_dev%%=*}" _devices="${_devices} -s ${_bus}:${_dev##*=},passthru,${_dev%%=*}"
else else
_orig_slot=${_dev%%/*} _orig_slot=${_dev%%/*}
@@ -749,7 +804,13 @@ vm::bhyve_device_passthru(){
_func=0 _func=0
fi fi
_devices="${_devices} -s ${_slot}:${_func},passthru,${_dev}" if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
_devices="${_devices} -s ${_bus}:${_slot}:${_func},passthru,${_dev}"
_last_orig_slot=${_orig_slot} _last_orig_slot=${_orig_slot}
_func=$((_func + 1)) _func=$((_func + 1))
fi fi
@@ -763,6 +824,11 @@ vm::bhyve_device_passthru(){
# add wired memory for 10.3+ # add wired memory for 10.3+
[ ${VERSION_BSD} -ge 1003000 ] && _opts="${_opts} -S" && _wiredmem="1" [ ${VERSION_BSD} -ge 1003000 ] && _opts="${_opts} -S" && _wiredmem="1"
fi fi
if [ ${_slot} -ge ${_maxslots} ]; then
_slot=0
_bus=$((_bus + 1))
_maxslots=32
fi
} }
# get the path to a disk image depending on type. # get the path to a disk image depending on type.

View File

@@ -112,7 +112,7 @@ switch::netgraph::provision(){
switch::netgraph::id "_ngid" "${_switch}" switch::netgraph::id "_ngid" "${_switch}"
util::log "guest" "${_name}" "adding netgraph interface ${_ngid} (${_switch})" util::log "guest" "${_name}" "adding netgraph interface ${_ngid} (${_switch})"
_devices="${_devices} -s ${_slot}:${_func},${_emulation},${_ngid}" _devices="${_devices} -s ${_bus}:${_slot}:${_func},${_emulation},${_ngid}"
[ -n "${_mac}" ] && _devices="${_devices},mac=${_mac}" [ -n "${_mac}" ] && _devices="${_devices},mac=${_mac}"
_func=$((_func + 1)) _func=$((_func + 1))

View File

@@ -397,7 +397,7 @@ switch::standard::provision(){
fi fi
fi fi
_devices="${_devices} -s ${_slot}:${_func},${_emulation},${_tap}" _devices="${_devices} -s ${_bus}:${_slot}:${_func},${_emulation},${_tap}"
[ -n "${_mac}" ] && _devices="${_devices},mac=${_mac}" [ -n "${_mac}" ] && _devices="${_devices},mac=${_mac}"
_func=$((_func + 1)) _func=$((_func + 1))

View File

@@ -121,7 +121,7 @@ switch::vale::provision(){
switch::vale::id "_vale_id" "${_switch}" "${_mac}" switch::vale::id "_vale_id" "${_switch}" "${_mac}"
util::log "guest" "${_name}" "adding vale interface ${_tap} (${_switch})" util::log "guest" "${_name}" "adding vale interface ${_tap} (${_switch})"
_devices="${_devices} -s ${_slot}:${_func},${_emulation},${_vale_id}" _devices="${_devices} -s ${_bus}:${_slot}:${_func},${_emulation},${_vale_id}"
[ -n "${_mac}" ] && _devices="${_devices},mac=${_mac}" [ -n "${_mac}" ] && _devices="${_devices},mac=${_mac}"
_func=$((_func + 1)) _func=$((_func + 1))