24.6.使用 FreeBSD 上的 bhyve 虚拟机

bhyve BSD 授权的虚拟化管理程序成为了 FreeBSD 10.0-RELEASE 基础系统的一部分。这个虚拟化管理程序支持多个客户机操作系统,包括 FreeBSD、OpenBSD、许多 Linux®发行版和 Microsoft Windows®。默认情况下,bhyve 提供串行控制台访问,而不模拟图形控制台。新 CPU 的虚拟化卸载功能用于避免传统的指令转换方法和手动管理内存映射。

设计要求 bhyve

  • 支持 Intel 扩展页表(EPT)的英特尔®处理器,

  • 或支持 AMD 快速虚拟化索引(RVI)或嵌套页表(NPT)的 AMD®处理器,

  • 或者是 ARM® aarch64 CPU。

ARM 上仅支持纯 ARMv8.0 虚拟化,暂不支持虚拟化主机扩展。在托管 Linux®客户或具有多个 vCPU 的 FreeBSD 客户时,需要 VMX 无限制模式支持(UG)。

要确定 Intel 或 AMD 处理器是否支持 bhyve 的最简单方法是运行 dmesg 或查看/var/run/dmesg.boot,查看 AMD®处理器的 Features2 行或 Intel®处理器的 VT-x 行的 POPCNT 处理器特性标志以及 EPT 和 UG。

24.6.1. 准备主机

在 bhyve 中创建虚拟机的第一步是配置主机系统。首先,加载 bhyve 内核模块:

# kldload vmm

将虚拟机客户端连接到主机网络有几种方式;其中一个简单的方法是为虚拟机的网络设备创建一个 tap 接口以供连接。为了让网络设备参与网络,还需创建一个包含 tap 接口和物理接口的桥接口作为成员。在这个示例中,物理接口是 igb0:

# ifconfig tap0 create
# sysctl net.link.tap.up_on_open=1
net.link.tap.up_on_open: 0 -> 1
# ifconfig bridge0 create
# ifconfig bridge0 addm igb0 addm tap0
# ifconfig bridge0 up

创建一个 FreeBSD 客户端

创建一个文件用作虚拟机的虚拟磁盘。指定虚拟磁盘的大小和名称:

# truncate -s 16G guest.img

下载一个 FreeBSD 安装镜像以进行安装:

# fetch https://download.freebsd.org/releases/ISO-IMAGES/14.0/FreeBSD-14.0-RELEASE-amd64-bootonly.iso
FreeBSD-14.0-RELEASE-amd64-bootonly.iso                426 MB   16 MBps    22s

FreeBSD 带有一个示例脚本 vmrun.sh,用于在 bhyve 中运行虚拟机。它将启动虚拟机,并在循环中运行,因此如果崩溃,它将自动重启。vmrun.sh 采用多个选项来控制机器的配置,包括:

  • -c 控制虚拟 CPU 的数量,

  • -m 限制了提供给客户端的内存量,

  • -t 定义要使用的 tap 设备,

  • -d 指示要使用的磁盘镜像,

  • -i 告诉 bhyve 从 CD 镜像而不是磁盘启动,

  • -I 定义要使用的 CD 映像。

最后一个参数是虚拟机的名称,用于跟踪运行中的虚拟机。以下命令列出所有可用的程序参数选项:

# sh /usr/share/examples/bhyve/vmrun.sh -h

此示例启动安装模式的虚拟机。

# sh /usr/share/examples/bhyve/vmrun.sh -c 1 -m 1024M -t tap0 -d guest.img \
     -i -I FreeBSD-14.0-RELEASE-amd64-bootonly.iso guestname

虚拟机将引导并启动安装程序。在虚拟机中安装系统后,当系统在安装结束时询问是否选择进入 shell 时,请选择是。

重启虚拟机。当虚拟机重启导致 bhyve 退出时,vmrun.sh 脚本将在循环中运行 bhyve 并将自动重启它。当这发生时,请从引导加载程序菜单中选择重启选项以退出循环。现在可以从虚拟磁盘启动客户机:

# sh /usr/share/examples/bhyve/vmrun.sh -c 4 -m 1024M -t tap0 -d guest.img guestname

24.6.3. 创建 Linux® 客户端

Linux 客户机可以像任何其他常规 UEFI 客户机一样引导,或者,你可以使用 sysutils/grub2-bhyve port。

要做到这一点,首先确保已安装 port,然后创建一个文件用作客户机的虚拟磁盘:

# truncate -s 16G linux.img

使用 grub2-bhyve 启动 Linux 虚拟机是一个两步过程。

  1. 首先必须加载一个内核,然后才能启动客户端。

  2. 使用 sysutils/grub2-bhyve 加载 Linux® 内核。

创建一个 device.map,供 grub 使用,将虚拟设备映射到主机系统上的文件。

(hd0) ./linux.img
(cd0) ./somelinux.iso

使用 sysutils/grub2-bhyve 从 ISO 镜像加载 Linux® 内核:

# grub-bhyve -m device.map -r cd0 -M 1024M linuxguest

这将启动 grub。如果安装 CD 包含 grub.cfg,则会显示菜单。如果没有,则必须手动定位并加载 vmlinuz 和 initrd 文件:

grub> ls
(hd0) (cd0) (cd0,msdos1) (host)
grub> ls (cd0)/isolinux
boot.cat boot.msg grub.conf initrd.img isolinux.bin isolinux.cfg memtest
splash.jpg TRANS.TBL vesamenu.c32 vmlinuz
grub> linux (cd0)/isolinux/vmlinuz
grub> initrd (cd0)/isolinux/initrd.img
grub> boot

现在 Linux® 内核已加载,可以启动虚拟机了:

# bhyve -A -H -P -s 0:0,hostbridge -s 1:0,lpc -s 2:0,virtio-net,tap0 \
    -s 3:0,virtio-blk,./linux.img -s 4:0,ahci-cd,./somelinux.iso \
    -l com1,stdio -c 4 -m 1024M linuxguest

系统将引导并启动安装程序。在虚拟机中安装系统后,重启虚拟机。这将导致 bhyve 退出。必须在可以再次启动之前销毁虚拟机的实例:

# bhyvectl --destroy --vm=linuxguest

现在客户机可以直接从虚拟磁盘启动。加载内核:

# grub-bhyve -m device.map -r hd0,msdos1 -M 1024M linuxguest
grub> ls
(hd0) (hd0,msdos2) (hd0,msdos1) (cd0) (cd0,msdos1) (host)
(lvm/VolGroup-lv_swap) (lvm/VolGroup-lv_root)
grub> ls (hd0,msdos1)/
lost+found/ grub/ efi/ System.map-2.6.32-431.el6.x86_64 config-2.6.32-431.el6.x
86_64 symvers-2.6.32-431.el6.x86_64.gz vmlinuz-2.6.32-431.el6.x86_64
initramfs-2.6.32-431.el6.x86_64.img
grub> linux (hd0,msdos1)/vmlinuz-2.6.32-431.el6.x86_64 root=/dev/mapper/VolGroup-lv_root
grub> initrd (hd0,msdos1)/initramfs-2.6.32-431.el6.x86_64.img
grub> boot

启动虚拟机:

# bhyve -A -H -P -s 0:0,hostbridge -s 1:0,lpc -s 2:0,virtio-net,tap0 \
    -s 3:0,virtio-blk,./linux.img -l com1,stdio -c 4 -m 1024M linuxguest

Linux®现在将在虚拟机中启动,并最终显示登录提示符。登录并使用虚拟机。完成后,重启虚拟机以退出 bhyve。销毁虚拟机实例:

# bhyvectl --destroy --vm=linuxguest

24.6.4. 使用 UEFI 固件引导 bhyve 虚拟机

除了 bhyveload 和 grub-bhyve,bhyve 虚拟机监控程序还可以使用 UEFI 固件引导虚拟机。此选项可能支持其他加载程序不支持的客户操作系统。

要利用 bhyve 中的 UEFI 支持,首先获取 UEFI 固件镜像。这可以通过安装 sysutils/bhyve-firmware port或软件包来完成。

有了固件之后,在 bhyve 命令行中添加标志 -l bootrom,/path/to/firmware。实际的 bhyve 命令可能如下所示:

# bhyve -AHP -s 0:0,hostbridge -s 1:0,lpc \
  	-s 2:0,virtio-net,tap1 -s 3:0,virtio-blk,./disk.img \
	-s 4:0,ahci-cd,./install.iso -c 4 -m 1024M \
	-l bootrom,/usr/local/share/uefi-firmware/BHYVE_UEFI.fd \
	guest

要能让客户端存储 UEFI 变量,可以使用附加到 -l 标志的变量文件。请注意,bhyve 将把客户端修改写入给定的变量文件。因此,请务必首先创建变量模板文件的每个客户端副本:

# cp /usr/local/share/uefi-firmware/BHYVE_UEFI_VARS.fd /path/to/vm-image/BHYVE_UEFI_VARS.fd

然后,将该变量文件添加到你的 bhyve 参数中:

# bhyve -AHP -s 0:0,hostbridge -s 1:0,lpc \
  	-s 2:0,virtio-net,tap1 -s 3:0,virtio-blk,./disk.img \
	-s 4:0,ahci-cd,./install.iso -c 4 -m 1024M \
	-l bootrom,/usr/local/share/uefi-firmware/BHYVE_UEFI.fd,/path/to/vm-image/BHYVE_UEFI_VARS.fd \
	guest

若要查看或修改变量文件内容,请在主机上使用 efivar(8)。

sysutils/bhyve-firmware 还包含一个启用 CSM 的固件,以在传统 BIOS 模式下启动不支持 UEFI 的宿主:

# bhyve -AHP -s 0:0,hostbridge -s 1:0,lpc \
  	-s 2:0,virtio-net,tap1 -s 3:0,virtio-blk,./disk.img \
	-s 4:0,ahci-cd,./install.iso -c 4 -m 1024M \
	-l bootrom,/usr/local/share/uefi-firmware/BHYVE_UEFI_CSM.fd \
	guest

24.6.5. bhyve 宿主的图形 UEFI 帧缓冲

UEFI 固件支持在主要是图形宿主操作系统(如 Microsoft Windows®)中特别有用。

支持 UEFI-GOP 帧缓冲区也可以通过 -s 29,fbuf,tcp=0.0.0.0:5900 标志启用。帧缓冲区分辨率可以通过 w=800 和 h=600 进行配置,并且可以通过添加 wait 指示 bhyve 在引导客户机之前等待 VNC 连接。帧缓冲区可以通过主机或通过 VNC 协议通过网络访问。此外,-s 30,xhci,tablet 可以添加以实现与主机的精确鼠标指针同步。

生成的 bhyve 命令如下所示:

# bhyve -AHP -s 0:0,hostbridge -s 31:0,lpc \
  	-s 2:0,virtio-net,tap1 -s 3:0,virtio-blk,./disk.img \
	-s 4:0,ahci-cd,./install.iso -c 4 -m 1024M \
	-s 29,fbuf,tcp=0.0.0.0:5900,w=800,h=600,wait \
	-s 30,xhci,tablet \
	-l bootrom,/usr/local/share/uefi-firmware/BHYVE_UEFI.fd \
	guest

注意,在 BIOS 仿真模式下,控制权从固件传递到客户操作系统后,帧缓冲区将停止接收更新。

创建 Microsoft Windows® 客户端

为 Windows 10 或更早版本设置客户端可以直接从原始安装媒体进行,这是一个相对简单的过程。除了最低资源要求外,作为客户端运行 Windows 需要

  • 配置虚拟机内存(标记 -w )和

  • 使用 UEFI 引导固件启动。

用 Windows 安装 ISO 启动虚拟机示例:

bhyve \
      -c 2 \
      -s 0,hostbridge \
      -s 3,nvme,windows2016.img \
      -s 4,ahci-cd,install.iso \
      -s 10,virtio-net,tap0 \
      -s 31,lpc \
      -s 30,xhci,tablet \
      -l bootrom,/usr/local/share/uefi-firmware/BHYVE_UEFI.fd \
      -m 8G -H -w \
      windows2016

安装过程中应仅使用一个或两个虚拟 CPU,但可以在安装完 Windows 后增加这个数量。

定制 VirtIO 驱动必须安装才能使用定义的 virtio-net 网络接口。另一种选择是通过将 virtio-net 更改为 e1000 在上述命令行中切换到 E1000 (Intel E82545) 模拟。但性能将受到影响。

24.6.6.1. 创建 Windows 11 客户机

从 Windows 11 开始,Microsoft 引入了对 TPM 2 模块的硬件要求。bhyve 支持将硬件 TPM 传递给客户机。安装媒体可以修改以禁用相关的硬件检查。关于此过程的详细说明可在 FreeBSD Wiki 上找到。

24.6.7. 使用 ZFS 与 bhyve 客户机

如果主机上有 ZFS 可用,则使用 ZFS 卷而不是磁盘映像文件可以为客户机提供显著的性能优势。可以通过以下方式创建 ZFS 卷:

# zfs create -V16G -o volmode=dev zroot/linuxdisk0

当启动虚拟机时,请将 ZFS 卷指定为磁盘驱动器:

# bhyve -A -H -P -s 0:0,hostbridge -s 1:0,lpc -s 2:0,virtio-net,tap0 \
  	-s3:0,virtio-blk,/dev/zvol/zroot/linuxdisk0 \
	-l com1,stdio -c 4 -m 1024M linuxguest

如果你既在主机上使用 ZFS 又在客户机内部使用 ZFS,请谨记两个系统缓存虚拟机内容时存在的内存竞争压力。为减轻这种压力,请考虑设置主机的 ZFS 文件系统仅使用元数据缓存。为此,请在主机上的 ZFS 文件系统上应用以下设置,将 替换为虚拟机特定 zvol 数据集名称的名称。

# zfs set primarycache=metadata <name>

创建虚拟机快照

现代虚拟化程序能让用户创建其状态的“快照”;这样的快照包括客户机的磁盘、CPU 和内存内容。快照通常可以在客户机运行或关闭时独立进行。然后可以将虚拟机重置并返回到快照被拍摄时的精确状态。

24.6.8.1. ZFS 快照

使用 ZFS 卷作为虚拟机的后备存储可以对客户机的磁盘进行快照。例如:

zfs snapshot zroot/path/to/zvol@snapshot_name

虽然在虚拟机运行时可能会对 ZFS 卷进行快照,但请记住,在虚拟机运行时,虚拟磁盘的内容可能处于不一致状态。因此,建议在执行此命令之前先关闭或暂停虚拟机。默认情况下不支持暂停虚拟机,需要先启用(请参阅内存和 CPU 快照)。

当虚拟机正在使用 ZFS zvol 时将其回滚到快照可能会损坏文件系统内容并导致虚拟机崩溃。虚拟机中的所有未保存数据将丢失,并且自上次快照以来的修改可能会被破坏。 如关闭虚拟机,可能需要进行第二次回滚以将文件系统恢复到可用状态。这反过来将最终销毁快照后所做的任何更改。

24.6.8.2. 内存和 CPU 快照(实验性功能)

从 FreeBSD 13 开始,bhyve 具有一个实验性的“快照”功能,用于将客户机的内存和 CPU 状态转储到文件,然后停止虚拟机。以后可以从快照文件内容恢复客户机。

但是,默认情况下未启用此功能,需要重新从源代码构建系统。请参阅有关使用自定义选项编译内核过程的深入说明。

功能尚未准备好用于生产,仅限于特定虚拟机配置的工作。存在多个限制: * nvme 和 virtio-blk 存储后端尚未工作* 仅当客户端使用每种设备的单一种类时才支持快照,即如果连接了多个 ahci-hd 磁盘,则快照创建将失败* 此外,该功能在 Intel 上可能相对稳定,但可能不会在 AMD CPU 上运行。

首先,在/etc/src.conf 中添加以下内容:

WITH_BHYVE_SNAPHOT=yes
BHYVE_SNAPSHOT=1
MK_BHYVE_SNAPSHOT=yes
# cd /usr/src
# make cleanworld

然后继续。

然后按照"从源代码更新 FreeBSD"章节中快速入门部分的步骤来构建和安装世界和内核。

要验证快照功能成功激活,请输入

# bhyvectl --usage

并检查输出是否列出了 --suspend 标志。如果缺少该标志,则该功能未正确激活。

然后,你可以对你选择的运行中的虚拟机进行快照和挂起:

# bhyvectl --vm=vmname --suspend=/path/to/snapshot/filename

如果不提供 --suspend 的绝对路径和文件名,bhyve 将会将快照数据写入 bhyve 启动的目录。 确保将快照数据写入安全目录。生成的输出包含客户机的完整内存转储,因此可能包含敏感数据(例如密码)!

这将创建三个文件:

  • 存储快照 - 命名类似于输入到 --suspend

  • 内核文件 - 与输入类似的名称,带有后缀 .kern

  • 元数据 - 包含关于系统状态的元数据,以 .meta 作为后缀命名

使用 -r 标志与 bhyve 恢复来宾快照。

# bhyve -r /path/to/snapshot/filename

在不同的 CPU 架构上恢复来宾快照将不起作用。一般来说,在与快照创建者不同的系统上尝试恢复将很可能失败。

24.6.9. 在 bhyve 中设置 jail

为了提高安全性并将虚拟机与主机操作系统分离,可以在 jail 中运行 bhyve。查看 Jail 以深入了解 jail 及其安全优势。

24.6.9.1. 为 bhyve 创建 Jail

首先,创建一个 jail 环境。如果使用 UFS 文件系统,只需运行:

# mkdir -p /jails/bhyve

如果使用 ZFS 文件系统,请使用以下命令:

# zfs create zroot/jails
# zfs create zroot/jails/bhyve

然后为虚拟机 bhyvevm0 创建一个 ZFS zvol:

# zfs create zroot/vms
# zfs create -V 20G zroot/vms/bhyvevm0

如果不使用 ZFS,请使用以下命令直接在 jail 目录结构中创建磁盘镜像文件:

# mkdir /jails/bhyve/vms
# truncate -s 20G /jails/bhyve/vms/bhyvevm0

下载一个 FreeBSD 镜像,最好是与主机版本相同或旧一些的版本,并将其提取到jail目录中:

# cd /jails
# fetch -o base.txz http://ftp.freebsd.org/pub/FreeBSD/releases/amd64/13.2-RELEASE/base.txz
# tar -C /jails/bhyve -xvf base.txz

接下来,在/etc/devfs.rules 中添加一个 devfs 规则集:

[devfsrules_jail_bhyve=100]
add include $devfsrules_hide_all
add include $devfsrules_unhide_login
add path 'urandom' unhide
add path 'random' unhide
add path 'crypto' unhide
add path 'shm' unhide
add path 'zero' unhide
add path 'null' unhide
add path 'mem' unhide
add path 'vmm' unhide
add path 'vmm/*' unhide
add path 'vmm.io' unhide
add path 'vmm.io/*' unhide
add path 'nmdmbhyve*' unhide
add path 'zvol' unhide
add path 'zvol/zroot' unhide
add path 'zvol/zroot/vms' unhide
add path 'zvol/zroot/vms/bhyvevm0' unhide
add path 'zvol/zroot/vms/bhyvevm1' unhide
add path 'tap10*' unhide
add path 'zvol' unhide
add path 'zvol/zroot' unhide
add path 'zvol/zroot/vms' unhide
add path 'zvol/zroot/vms/bhyvevm0' unhide
add path 'zvol/zroot/vms/bhyvevm1' unhide

这些规则将导致 bhyve 创建一个名为 {{0}} 和 {{1}} 的带有磁盘卷的虚拟机,

  • 创建一个名为 bhyvevm0 和 bhyvevm1 的带有磁盘卷的虚拟机,

  • 使用以 tap10 为前缀的 tap 网络接口。这意味着有效的接口名称将是 tap10,tap100,tap101,… tap109,tap1000 等等。限制对可能的一组 tap 接口名称的访问,将阻止jail(从而阻止 bhyve)看到主机和其他jail的 tap 接口。

  • 使用以"bhyve"为前缀的 nmdm 设备,即/dev/nmdmbhyve0。

这些规则可以根据需要使用不同的客户机和接口名称进行扩展和变化。

重启 devfs 以加载更改:

# service devfs restart

然后将你的新 jail 的定义添加到 /etc/jail.conf 或 /etc/jail.conf.d 中。将接口号 $if 和 IP 地址替换为你的个性化变量。

使用 NAT 或路由流量与防火墙

bhyve {
        $if = 0;
        exec.prestart = "/sbin/ifconfig epair${if} create up";
        exec.prestart += "/sbin/ifconfig epair${if}a up";
        exec.prestart += "/sbin/ifconfig epair${if}a name ${name}0";
        exec.prestart += "/sbin/ifconfig epair${if}b name jail${if}";
        exec.prestart += "/sbin/ifconfig ${name}0 inet 192.168.168.1/27";
        exec.prestart += "/sbin/sysctl net.inet.ip.forwarding=1";

        exec.clean;

        host.hostname = "your-hostname-here";
        vnet;
        vnet.interface = "em${if}";
        path = "/jails/${name}";
        persist;
        securelevel = 3;
        devfs_ruleset = 100;
        mount.devfs;

        allow.vmm;

        exec.start += "/bin/sh /etc/rc";
        exec.stop = "/bin/sh /etc/rc.shutdown";

        exec.poststop += "/sbin/ifconfig ${name}0 destroy";
}

此示例假设使用类似 pf 或 ipfw 的防火墙来 NAT 你的jail流量。有关实现此操作的可用选项,请参阅防火墙章节。

示例 2. 使用桥接网络连接

bhyve {
        $if = 0;
        exec.prestart = "/sbin/ifconfig epair${if} create up";
        exec.prestart += "/sbin/ifconfig epair${if}a up";
        exec.prestart += "/sbin/ifconfig epair${if}a name ${name}0";
        exec.prestart += "/sbin/ifconfig epair${if}b name jail${if}";
        exec.prestart += "/sbin/ifconfig bridge0 addm ${name}0";
        exec.prestart += "/sbin/sysctl net.inet.ip.forwarding=1";

        exec.clean;

        host.hostname = "your-hostname-here";
        vnet;
        vnet.interface = "em${if}";
        path = "/jails/${name}";
        persist;
        securelevel = 3;
        devfs_ruleset = 100;
        mount.devfs;

        allow.vmm;

        exec.start += "/bin/sh /etc/rc";
        exec.stop = "/bin/sh /etc/rc.shutdown";

        exec.poststop += "/sbin/ifconfig ${name}0 destroy";
}

24.6.9.2. 配置Jail

第一次启动jail并进行一些额外的配置工作,请输入:

# cp /etc/resolv.conf /jails/bhyve/etc
# service jail onestart bhyve
# jexec bhyve
# sysrc ifconfig_jail0="inet 192.168.168.2/27"
# sysrc defaultrouter="192.168.168.1"
# sysrc sendmail_enable=NONE
# sysrc cloned_interfaces="tap100"
# exit

重启并启用jail:

# sysrc jail_enable=YES
# service jail restart bhyve

之后,你可以在jail内创建虚拟机。对于 FreeBSD 客户端,请首先下载安装 ISO:

# jexec bhyve
# cd /vms
# fetch -o freebsd.iso https://download.freebsd.org/releases/ISO-IMAGES/14.0/FreeBSD-14.0-RELEASE-amd64-bootonly.iso

24.6.9.3. 在Jail内创建虚拟机

使用 bhyvectl 创建虚拟机,首先要初始化它:

# jexec bhyve
# bhyvectl --create --vm=bhyvevm0

使用 bhyvectl 创建客户端可能是必需的,当从 jail 启动虚拟机时。跳过此步骤可能会导致启动 bhyve 时出现以下错误消息: vm_open: vm-name could not be opened. No such file or directory

最后,使用你喜欢的方式启动客户端。

例 3。从 vmrun.sh 和 ZFS 开始

在 ZFS 文件系统上使用 vmrun.sh :

# jexec bhyve
# sh /usr/share/examples/bhyve/vmrun.sh -c 1 -m 1024M \
     -t tap100 -d /dev/zvols/zroot/vms/bhyvevm0 -i -I /vms/FreeBSD-14.0-RELEASE-amd64-bootonly.iso bhyvevm0

例 4。从 vmrun.sh 和 UFS 开始

在 UFS 文件系统上使用 vmrun.sh :

# jexec bhyve
# sh /usr/share/examples/bhyve/vmrun.sh -c 1 -m 1024M \
     -t tap100 -d /vms/bhyvevm0 -i -I /vms/FreeBSD-14.0-RELEASE-amd64-bootonly.iso bhyvevm0

示例 5. 使用 ZFS 启动 UEFI 客户机的 bhyve

如果你想要使用 UEFI 客户机,请记得首先在 jail 中安装所需的固件包 sysutils/bhyve-firmware:

# pkg -j bhyve install bhyve-firmware

然后直接使用 bhyve :

# bhyve -A -c 4 -D -H -m 2G \
        -s 0,hostbridge \
        -s 1,lpc \
        -s 2,virtio-net,tap100 \
        -s 3,virtio-blk,/dev/zvol/zroot/vms/bhyvevm0 \
	-s 4,ahci-cd,/vms/FreeBSD-14.0-RELEASE-amd64-bootonly.iso \
        -s 31,fbuf,tcp=127.0.0.1:5900,w=1024,h=800,tablet \
        -l bootrom,/usr/local/share/uefi-firmware/BHYVE_UEFI.fd \
        -l com1,/dev/nmdbbhyve0A \
        bhyvevm0

这将能让你通过 VNC 以及位于/dev/nmdbbhyve0B 的串行控制台连接到你的虚拟机 bhyvevm0。

24.6.10. 虚拟机控制台

It is advantageous to wrap the bhyve console in a session management tool such as sysutils/tmux or sysutils/screen in order to detach and reattach to the console. It is also possible to have the console of bhyve be a null modem device that can be accessed with cu. To do this, load the nmdm kernel module and replace -l com1,stdio with -l com1,/dev/nmdm0A. The /dev/nmdm devices are created automatically as needed, where each is a pair, corresponding to the two ends of the null modem cable (/dev/nmdm0A and /dev/nmdm0B). See nmdm(4) for more information.

# kldload nmdm
# bhyve -A -H -P -s 0:0,hostbridge -s 1:0,lpc -s 2:0,virtio-net,tap0 -s 3:0,virtio-blk,./linux.img \
    -l com1,/dev/nmdm0A -c 4 -m 1024M linuxguest
# cu -l /dev/nmdm0B
Connected

Ubuntu 13.10 handbook ttyS0

handbook login:

To disconnect from a console, enter a newline (i.e. press RETURN) followed by tilde (~), and finally dot (.). Keep in mind that only the connection is dropped while the login session remains active. Another user connecting to the same console could therefore make use of any active sessions without having to first authenticate. For security reasons, it’s therefore recommended to logout before disconnecting.

The number in the nmdm device path must be unique for each virtual machine and must not be used by any other processes before bhyve starts. The number can be chosen arbitrarily and does not need to be taken from a consecutive sequence of numbers. The device node pair (i.e. /dev/nmdm0a and /dev/nmdm0b) are created dynamically when bhyve connects its console and destroyed when it shuts down. Keep this in mind when creating scripts to start your virtual machines: you need to make sure that all virtual machines are assigned unique nmdm devices.

24.6.11. 管理虚拟机

为每个虚拟机在 /dev/vmm 中创建一个设备节点。这使管理员可以轻松查看正在运行的虚拟机列表:

# ls -al /dev/vmm
total 1
dr-xr-xr-x   2 root  wheel    512 Mar 17 12:19 ./
dr-xr-xr-x  14 root  wheel    512 Mar 17 06:38 ../
crw-------   1 root  wheel  0x1a2 Mar 17 12:20 guestname
crw-------   1 root  wheel  0x19f Mar 17 12:19 linuxguest
crw-------   1 root  wheel  0x1a1 Mar 17 12:19 otherguest

可以使用 bhyvectl 销毁指定的虚拟机:

# bhyvectl --destroy --vm=guestname

以这种方式销毁虚拟机意味着立即终止它。任何未保存的数据都将丢失,打开的文件和文件系统可能会损坏。要优雅地关闭虚拟机,请发送 TERM 信号到其 bhyve 进程。这将触发客户机的 ACPI 关机事件:

# ps ax | grep bhyve
17424  -  SC      56:48.27 bhyve: guestvm (bhyve)
# kill 17424

24.6.12. 工具与实用程序

有许多实用程序和应用程序可用于 ports,以帮助简化设置和管理 bhyve 虚拟机:

表 1。bhyve 管理员

名字
执照
软件包
文档

vm-bhyve

BSD-2

CBSD

BSD-2

虚拟管理器

LGPL-3

Bhyve RC 脚本

未知

bmd

未知

VM 状态

BSD-2

24.6.13. 持久配置

为了在启动时配置系统以启动 bhyve 客户机,需要进行一些配置文件更改。

  1. 当使用 tap 接口作为网络后端时,你需要手动设置每个使用的 tap 接口为 UP,或者简单地设置以下 sysctl:

    net.link.tap.up_on_open=1
  2. /etc/rc.conf 要将你的虚拟机的 tap 设备通过桥接连接到网络,你需要将设备设置持久化在 /etc/rc.conf 中。此外,你可以通过 vmm 是用于 bhyve,nmdm 是用于 nmdm 设备的必要内核模块进行加载 kld_list 配置变量。在配置 ifconfig_bridge0 时,请确保将 / 替换为你的物理接口的实际 IP 地址(在此示例中为 igb0),并从物理设备中删除 IP 设置。

    # sysrc cloned_interfaces+="bridge0 tap0"
    # sysrc ifconfig_bridge0="inet <ipaddr>/<netmask> addm igb0 addm tap0"
    # sysrc kld_list+="nmdm vmm"
    # sysrc ifconfig_igb0="up"

示例 6. 设置桥接设备的 IP

对于具有 igb0 接口连接到具有 IP 10.10.10.1 和子网掩码 255.255.255.0 的网络的主机,你将使用以下命令:

# sysrc ifconfig_igb0="up"
# sysrc ifconfig_bridge0="inet 10.10.10.1/24 addm igb0 addm tap0"
# sysrc kld_list+="nmdm vmm"
# sysrc cloned_interfaces+="bridge0 tap0"

最后更新于

FreeBSD 中文社区