显卡用默认配置的话是没有这种现象的。这个问题出现在使用 SPICE 显卡模拟功能的情况下。
虚拟机有个配置项为 tablet: <boolean> (default = 1)
,它用来启用 / 禁用被模拟出的,使用绝对坐标的 USB 指针设备。通常只有启用了该设备才能在 VNC 中使用鼠标的绝对坐标,从而使得 host 和 guest 的鼠标设备同步。
QEMU-KVM 文档 https://qemu-project.gitlab.io/qemu/system/devices/usb.html 里这么描述 usb-tablet 设备:
Pointer device that uses absolute coordinates (like a touchscreen). This means QEMU is able to report the mouse position without having to grab the mouse. Also overrides the PS/2 mouse emulation when activated.
tablet: 0 是使用 spice 终端的默认配置 (即 qm set <vmid> --vga qxl
),所以出现了 Host 的鼠标和 VNC 终端内的鼠标位置不同步的现象。
如果一台主机上运行了多台通过 VNC 终端访问的虚拟机,可以考虑在全局配置里禁用该参数,以节省不必要的上下文切换。
要在尽可能少地改动配置、尽量减少影响范围的情况下,解决鼠标同步问题,需要连接到 PVE 主机,使用 sudo vim /etc/pve/qemu-server/<vm_id>.conf
对单台虚拟机配置进行修改。加入以下语句:
...
tablet: 1
# tablet: yes 也行,随后会自动地被 PVE 改写成 tablet: 1
...
最后重启 windows 虚拟机即可解决问题。
这是因为 Windows 7 默认没有原生的 VM Generation ID (PVE 的一个特性) 支持。只能手动安装补丁包到系统中。
下载 Hyper-V integration components update (All supported x64-based versions of Windows 7) 然后传输到虚拟机中,并安装: Dism /online /Add-Package /PackagePath:C:\<package>.cab
。
virtio-win 官方兼容 win7 的最后一个版本是 virtio-win-0.1.173-4。但是这个版本还有一些问题。
在使用 virtio-win-gt-x64.msi 装驱动时,Spice Agent 相关的驱动有些问题,会导致 rdservice 不能启动,进而导致安装失败。
必须在 Custom Setup 阶段将 Spice Agent 组件设为 Feature will be installed when required 以跳过安装 Spice Agent 组件才能继续后面的安装过程。
但是要注意,如果 virtio-win-0.1.173-4 用在 Windows Server 2008R2 上,那么 virtio-win-gt-x64.msi 除了 Spice Agent 之外什么都装不上,而且唯一要装的 Spice Agent 还有问题,所以跑完什么都没装上。所有驱动必须自己手动装上去。
可能是 openwrt 系统里缺 QEMU Guest Agent 这个包。
ssh 进 openwrt,安装 qemu-ga 即可:
opkg update
opkg install qemu-ga
如果使用的固件没有 opkg 一类的包管理器,那么只能在重新编译的时候把 qemu-ga 一起编译进去。
第一步,获取硬盘信息。SSH 连接到 PVE 物理机执行 ls /dev/disk/by-id/
得到硬盘 ID 的第一列大概长这样:
# 这是一块硬盘的 ID
ata-HGST_HUS728T8TALE6L4_VDGW2G2D
# 这是上面 ID 对应硬盘的一个分区
ata-HGST_HUS728T8TALE6L4_VDGW2G2D-part1
# 这是上面 ID 对应硬盘的另一个分区
ata-HGST_HUS728T8TALE6L4_VDGW2G2D-part2
ata-HGST_HUS728T8TALE6L4_VGGP235G
ata-HGST_HUS728T8TALE6L4_VGGP235G-part1
ata-HGST_HUS728T8TALE6L4_VGGP235G-part2
ata-INTEL_SSDSC2BA400G3_BTTV501203BG400HGN
ata-MK0800GCTZB_BTTV5295004K800JGN
ata-MK0800GCTZB_BTTV5295004K800JGN-part1
ata-WDC_WD5000AAKX-08U6AA0_WD-WCC2EMU56607
ata-WDC_WD5000AAKX-08U6AA0_WD-WCC2EMU56607-part1
dm-name-Intel400GS3700-vm--130--disk--0
dm-name-pve-root
第二步,映射硬盘,命令为 qm set <vm_id> -<controller_type><controller_id> /dev/disk/by-id/<disk_id>
。 <vm_id>
是虚拟机的真实 id, <controller_type>
是对应的控制器类型, <controller_id>
是该类型未被占用的通道,PVE 支持 sata[0-5] 以及 scsi[0-13] 。
比如执行这样的命令:
qm set 130 -scsi1 /dev/disk/by-id/ata-MK0800GCTZB_BTTV5295004K800JGN
得到的输出是这样的:
update VM 130: -scsi1 /dev/disk/by-id/ata-MK0800GCTZB_BTTV5295004K800JGN
在这条命令执行后,物理机上的磁盘 (不论是 SATA 还是 SAS 接口) 被默认的 VirtIO SCSI 控制器模拟成普通的 scsi 磁盘,在系统中显示为 /dev/sd[a-z] 。这个控制器在老版本的 PVE 需要特别指定,即在命令后加 -scsihw virtio-scsi-pci (至少 PVE 6 不用手动写这个参数)。
常用的控制器类型有 SATA, VirtIO (也叫 VirtIO blk), VirtIO SCSI 和 VirtIO SCSI single 。
当 <controller_type>
填 virtio (这种控制器通常被称为 VirtIO 或 VirtIO blk),虚拟硬盘在系统中显示为 /dev/vd[a-z] 。这是一种较老的半虚拟化控制器,就功能而言,它已被 VirtIO SCSI 控制器取代。
如果在 WebUI 里编辑 SCSI 控制器,可以在选项中看到 VirtIO SCSI 和 VirtIO SCSI single:
注: 在 PVE 7.3 之前,VirtIO SCSI 是默认的控制器;之后,VirtIO SCSI single 是默认的控制器。
不论主板上插了 SATA 接口的盘还是 SAS 接口的盘,CPU 核心多主频低的时候用 VirtIO SCSI single 控制器,CPU 核心少主频高的时候用 VirtIO SCSI 控制器。
如果 guest 太老,不支持 VirtIO SCSI 控制器,则可以把 -scsi[0-13] 换成 -sata[0-5] 来使用 SATA 控制器。
PVE 虚拟机备份在默认情况下只存储一份,如果设定了定时备份任务,那么旧的备份会被删除。
修改方法: Web UI -> 数据中心 -> 存储 -> 双击备份所在位置的 ID -> Backup Retention -> 自定义备份文件存储逻辑。
这里的设置要参考 PVE 文档,或者直接去搜 Proxmox Backup Server - Prune Simulator 这是 PVE 官方做的备份模拟器。
SSH 登录到 PVE 物理机,执行 qm rescan --vmid <vm_id>
后,未使用的磁盘会出现在 Web UI 上,此时可以删除。
如果还不能删,重启 PVE 物理机再从 Web UI 上删除。
也可以用命令 pvesm free <volume_id>
或 pvesm free <storage_id>:<disk_id>
(比如 pvesm free local-lvm:vm-105-disk-1
或 pvesm free local-lvm:vm-105-disk-1
) 删除虚拟磁盘。
第一步,生成备份文件。选中虚拟机 -> 备份 -> 立即备份 -> 选定备份参数 -> 备份 。
第二步,找到备份文件。如果使用 PVE local 存储,那么在 /var/lib/vz/dump 内有 .vma.gz 压缩文件和 .log 日志文件。
最后下载这两个文件自行备份。
第一步,正常创建一个虚拟机,过程中:
第二步,删除默认创建的硬盘: 选中虚拟机 -> 硬件 -> 选中硬盘 (比如 scsi0) -> 分离 -> 选中未使用的磁盘 -> 删除 。
第三步,把 img 文件传入 PVE 宿主机。
第四步,添加磁盘。用 SSH 连接到宿主机,执行命令导入硬盘,格式为:
qm importdisk <vm_id> /<img_file_path>/<img_file> <disk_id>
比如: qm importdisk 150 ./openwrt.img local-lvm
第五步,添加导入的磁盘: 选中虚拟机 -> 硬件 -> 选中未使用的磁盘 -> 编辑 -> 添加 。
第六步,调整启动顺序: 选中虚拟机 -> 选项 -> 引导顺序 -> 编辑 -> 选中硬盘,拖到第一位。
虚拟机可以在 Web UI 里转成模板。
模板转虚拟机,删除 /etc/pve/qemu-server/<vm_id>.conf
文件里的 template: 1 行。
此时,虚拟机已可以正常启动。
虚拟机转模板后,虚拟机磁盘的名称也会由 vm-<vm_id>-disk-<disk_id>
变成 base-<vm_id>-disk-<disk_id>
,比如 vm-3000-disk-0 变成 base-3000-disk-0。
视需要更新虚拟磁盘的名称。但在更新虚拟磁盘名称后也要更新 /etc/pve/qemu-server/<vm_id>.conf
中 scsi0: <storage_id>:<vm_id>/<disk_name>.<disk_format>,size=<size>,ssd=1
的磁盘信息。
比如,scsi0: Intel400S3710:3000/base-3000-disk-0.qcow2,size=32G,ssd=1 更新为 scsi0: Intel400S3710:3000/base-3000-disk-0.qcow2,size=32G,ssd=1。
如果文件系统为 ext 系列,使用 zerofree 这个包能做到只对非 0 块写 0,减少非必要的写入,延长硬盘寿命。具体操作方法为:
如果文件系统为 xfs 或者其他,那么只能用最基础的方法:
# 创建一个全 0 的大文件,对于所有的块写 0
dd if=/dev/zero of=/null.dat
# 删除这个文件
rm -f /null.dat
在 windows 虚拟机上,下载微软 SysinternalsSuite 套件,执行里面的 sdelete.exe: =.\sdelete.exe -z c:=
raw 格式虚拟磁盘文件导出到 qcow2:
# --sparse=always 稀疏拷贝,忽略全 0 数据
cp --sparse=always vm500G.raw vm500G-new.raw
qemu-img convert -c -f raw -O qcow2 vm500G.raw vm500G.qcow2
# 删除第一条命令产生的 raw 文件
rm vm500G.raw
qcow2 格式的虚拟磁盘文件精简导出:
qemu-img convert -c -O qcow2 vm500G.qcow2 vm500G-mini.qcow2