ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

服务器虚拟化挂载外置存储:直通与存储池选型及KVM实战

服务器虚拟化挂载外置存储:直通与存储池选型及KVM实战 简介在数据爆炸式增长的背景下存储管理已成为虚拟化落地的重要环节。面向虚拟化技术学习与运维实践的PPT课件系统讲解如何通过IP SAN挂载外置存储设备帮助读者理解iSCSI协议封装原理并掌握从存储端到虚拟化平台的完整配置流程。内容涵盖IP SAN定义、无需专用HBA卡和光纤交换机的成本效益、基于IP标准的标准化接入、良好的可维护性、带宽扩展及传输距离等优势重点拆解创建硬盘域、存储池、LUN、LUN组以及在vCenter中添加网络、存储适配器与主机等关键操作。PPT按步骤组织配有实战案例对照从存储管理界面端口查看、命名硬盘域、选择RAID与容量到LUN属性定义、LUN组分配、虚拟化平台网络配置再到主机添加与操作系统类型选择完整还原挂载外置存储的实操链路。适合虚拟化课程学员、系统管理员及备考相关认证的技术人员对照学习。资源包内为1个pptx演示文件大小约1.97MB结构清晰便于课堂讲解、演示或自学复盘。目前已有80人浏览学习对想快速上手虚拟化存储挂载操作的读者具有较好的参考价值。1. 服务器虚拟化技术下的挂载外置存储按下开机键之前先把“直通”还是“收编”想清楚加一块外置盘给虚拟机直觉上是把 USB 硬盘盒插进宿主机再在虚拟机里开个磁盘就完事。实际做过的都知道服务器虚拟化技术里做“挂载外置存储”一半以上的翻车都发生在动手之前没想明白的一个选型问题上这块盘到底要“直通”给某台虚拟机独占还是“收编”进宿主机当共享存储池。方向选错轻则虚拟机迁移后起不来重则外置阵列重启一次盘符漂移VM 直接进 recovery mode。这个标题对应的日常工作就是把外置 SATA 盘、USB 硬盘柜、NVMe 盒子或小型磁盘阵列稳定地变成虚拟机的一块数据盘。最适合的读者是刚把物理机切成虚拟化、正在考虑扩容的运维以及要给开发环境挂测试盘的前端后端起服务的人。先确定路径再谈命令顺序反了就是要返工。2. 直通和存储池两条路线怎么选这决定了后面所有命令的走向2.1 直通路线USB 直通、PCIe 直通与 RDM分别适合什么样的虚拟机直通Passthrough的本质是把“物理设备”的访问权整块交给虚拟机宿主机不再参与这块盘的协议层管理。常见的实现有三种USB 直通、PCIe 直通、以及 VMware 体系里的 RDMRaw Device Mapping裸设备映射。USB 直通最轻量适合外置 USB 硬盘盒、U 盾、加密狗这类设备。libvirt 里用 hostdev 节点把 USB 设备的 vendor/product ID 绑定到虚拟机虚拟机直接走自己的 USB 控制器访问它。代价是性能一般USB 转发路径上多一层虚拟 USB 控制器4K 随机读通常只有原生性能的六到七成。我在一线常用的判断是只要这块盘不是压测对象、不跑数据库USB 直通完全够用要是虚拟机里跑 MySQL 或 PostgreSQL这条路就别走。PCIe 直通VT-d / IOMMU性能最接近原生适合 NVMe 外置盒、阵列 HBA 卡这类走 PCIe 总线的设备。做法是把设备从宿主机的默认驱动摘下来绑定到 vfio-pci再整卡或整设备塞进虚拟机。这里的代价比较隐蔽设备一旦直通宿主机上就再也看不到它想同时在宿主机上备份这份数据是做不到的。而且如果是直通一张 USB 扩展卡卡上插着的键鼠、U 盾会一起被带进虚拟机——这属于最常见的翻车现场后面避坑章节我单独展开。RDM 是 VMware 生态里的老方案把外置 LUN 通过一个映射文件挂给虚拟机。命令是 vmkfstools -r /vmfs/devices/disks/naa.xxxx /vmfs/volumes/datastore1/vm/vm.vmdk。它和 PCIe 直通最大的差别是虚拟机拿到的是裸设备映射但 vSphere 还能帮你管理这个映射文件做快照、做克隆都比整卡直通灵活。RDM 适合 Windows 虚拟机里要跑厂商级存储工具、要读 S.M.A.R.T. 和磁盘阵列日志的场景。Linux 下的等价做法是直接把 /dev/sdb 这样的块设备作为 qemu 的 raw 磁盘后端命令上没那么多仪式感但概念是一致的。2.2 存储池路线把外置盘收编成 VMFS 或 EXT4 资源池换取快照和迁移另一条路是放弃“这块盘被某台虚拟机独占”的想法把它格式化成宿主机认识的文件系统再切成 N 个镜像文件分给多台虚拟机。这就是存储池Storage Pool的思路。VMware 里叫 VMFS 数据存储建好数据存储后虚拟机文件、ISO、模板都往里放。KVM/QEMU 里更直接外置盘做成 EXT4/XFS挂载到宿主机某个目录再用 libvirt 把这个目录定义成 fs 类型的存储池。虚拟机看到的 vdb、vdc实际是池里一个个 qcow2 文件。这么做的核心收益是三个快照qcow2 天然支持、克隆、以及迁移。虚拟机迁移时目标宿主机只要挂到同一块外置盘、看到同一个目录镜像文件路径一致就能迁走不需要关心设备直通到哪台物理机。损失也很明确外置盘本身的硬件信息在虚拟机里是透明的虚拟机不认盘认的是镜像文件。想做品牌阵列自带的快照、做磁盘健康度告警就没了。另外多一层文件系统多一分写放大外置盘本身 IOPS 就不高的前提下这一层的损耗大约 5% 到 10%。我的习惯是抓一条分界线生产数据库、需要健康监测、要整盘加密的盘走直通或 RDM普通的临时盘、备份盘、开发环境系统盘一律走存储池。这个分界线省掉了大量后期维护的麻烦事。2.3 决策表用一张表锁死你的选型场景推荐路线理由虚拟机要读外置阵列的 S.M.A.R.T. / 品牌工具PCIe 直通 / RDM虚拟机直接看到物理盘厂商工具才能工作Windows 虚拟机做 BitLocker 整盘加密RDM 或块设备直通加密要有原始扇区访问能力qcow2 不行多台虚拟机共享一块外置大容量盘存储池qcow2 文件级隔离互不干扰外置 NVMe 盒子跑数据库PCIe 直通不做池绕开文件系统层降延迟备份盘、ISO 库、模板镜像存储池迁移和快照优先性能次要USB 硬盘盒放日志或临时数据USB 直通图省事/ 存储池性能都不行选管理方便的选型定下来之后再碰键盘这就是我处理一切挂载外置存储需求的第一步。3. KVM/QEMU 实操从识别外置盘到完成直通绑定的完整命令3.1 识别外置盘lsblk / blkid / udevadm 三条指令先看清真实身份拿到一块外置盘第一步不是急着挂载而是把它的物理身份搞清楚。宿主机上的 /dev/sdb 这个节点是会变的真正不变的是磁盘的序列号和 WWN。用 lsblk 看传输类型和型号lsblk -o NAME,SIZE,TYPE,TRAN,MODEL,SERIAL /dev/sdb输出里 TYPE 是 disk 还是 partTRAN 是 usb 还是 sata 或 nvmeSERIAL 是磁盘的序列号。这些信息决定了后续用哪种方式绑定。很多新手栽在只看 /dev/sdb 这个节点名上节点名在重启或插拔后会漂移所以我还习惯再用 blkid 确认 UUID 和文件系统类型blkid /dev/sdb /dev/sdb1如果输出为空说明盘上没有可识别的文件系统这是一块裸盘如果显示 PTUUID 和 PARTUUID说明盘上有分区表。接着查设备的稳定标识符udevadm info --queryproperty --name/dev/sdb | grep -E ID_SERIAL|ID_WWN|ID_PATH这一步拿到的 ID_SERIAL 和 ID_WWN 是给直通用的“身份 ID”后面绑定设备时不用 /dev/sdb而是用 /dev/disk/by-id/ 下的稳定路径。我一般会把这三条命令的输出截图或记到变更单里避免后面排查时还得重新插拔确认。3.2 直通绑定USB 直通用 vendor/productPCIe 直通用 vfio-pci确定走直通路线后先处理 USB 设备。用 usb-devices 或 lsusb 找到设备的 vendor 和 product IDlsusb | grep -i external正常会输出类似 Bus 002 Device 004: ID 0bc2:2322 Seagate 这样的行0bc2 是 vendor ID2322 是 product ID。然后写一个 libvirt hostdev XMLhostdev modesubsystem typeusb source vendor id0x0bc2/ product id0x2322/ /source /hostdev把这 XML 保存为 usb-disk.xml执行:virsh attach-device your-vm usb-disk.xml --live --config这里 --live 表示热插拔立即生效--config 表示写入虚拟机配置、下次开机也保留。参数说明vendor/product 是 USB 设备的固有标识不是盘符所以换一个 USB 口插上去依然能识别。但要注意如果宿主机上有多个同型号 USB 硬盘盒它们的 vendor/product 完全一样libvirt 会随机挑一个给虚拟机。规避办法是用 hostdev 里的 serial 属性精确匹配或者干脆给每个盒子贴标签管理实际操作中我更推荐用后者。PCIe 直通路径更重。先确认宿主机开了 IOMMU内核参数里有 intel_iommuon 或 amd_iommuon然后查看设备所属的 PCI 地址lspci -nn | grep -i nvme会输出类似 01:00.0 Non-Volatile memory controller [0108]: Device [144d:a80c] 这样的结果。把 01:00.0 绑定到 vfio-pcimodprobe vfio-pci driverctl set-override 0000:01:00.0 vfio-pcidriverctl 的作用是让设备在下次驱动加载时直接走 vfio-pci而不是原来的 nvme 驱动。执行完后写 PCI hostdev XMLhostdev modesubsystem typepci source address domain0x0000 bus0x01 slot0x00 function0x0/ /source /hostdev再 attach 一次。这里有三个关键点第一domain/bus/slot/function 必须和 lspci 输出严格对应多个 NVMe 盒子时最容易在这里搞混第二绑定之后宿主机 lsblk 会立刻丢失这块盘属于正常现象别慌第三如果设备在 IOMMU 分组里和其他设备绑在一起必须把整组都直通否则设备启动时会直接失败。3.3 存储池挂载外置盘做 EXT4 后用 virsh 池定义一次搞定走存储池路线时先把外置盘分区并格式化成 EXT4或 XFS。盘上如果没有重要数据用 parted 重新分区parted /dev/sdb --script -- mklabel gpt parted /dev/sdb --script mkpart primary ext4 1MiB 100% mkfs.ext4 /dev/sdb1GPT 分区表是为了支持超过 2TB 的盘MBR 在 2TB 边界上的坑我已经踩过不止一次。格式化完成后查看分区 UUIDblkid /dev/sdb1然后在 /etc/fstab 里用 UUID 挂载防止重启后盘符漂移echo UUID7c5f3bd0-9e2b-4e7a-9f5f-123456789abc /mnt/extdisk ext4 defaults,noatime,nofail 0 0 /etc/fstab mount -a挂载点建议不要用 /mnt 而是用 /srv/vm-images 这类语义清晰的路径。接着定义 libvirt 存储池virsh pool-define-as --type fs --name extpool \ --source-dev /dev/disk/by-uuid/7c5f3bd0-9e2b-4e7a-9f5f-123456789abc \ --source-format ext4 --target /srv/vm-images virsh pool-start extpool virsh pool-autostart extpool参数拆解--source-dev 这里用的是 by-uuid 稳定路径不用 /dev/sdb1--source-format ext4 告诉 libvirt 用 fs 类型探测--target /srv/vm-images 是宿主机上的挂载点。pool-autostart 很关键宿主机重启后 libvirt 会先挂这个池再启动虚拟机否则会出现虚拟机在存储池尚未就绪时就启动的竞态错误。池建好后创建 qcow2 镜像并挂给虚拟机qemu-img create -f qcow2 /srv/vm-images/data.qcow2 100G virsh attach-disk your-vm /srv/vm-images/data.qcow2 vdb \ --cache none --subdriver qcow2 --persistentattach-disk 的 --cache none 是给外置盘用的默认值这里先记住这个参数下一章讲性能问题时会展开。--persistent 表示长期有效。挂完在虚拟机里执行 lsblk看到 vdb 就是成功了。4. 参数与性能缓存策略、队列深度和 fio 压测这几个参数决定外置盘好不好用4.1 缓存策略的取舍外置盘上 writeback 是性能陷阱QEMU 的 disk cache 参数有 none、writethrough、writeback、directsync、unsafe 五种挂载外置存储时真正需要决策的是前三个。cachenone 表示 QEMU 不从宿主机层做缓存虚拟机的写请求直落磁盘cachewritethrough 是写请求同时写入磁盘并报告完成安全但慢cachewriteback 是 QEMU 先收进自己内存异步刷盘性能最好。问题出在 writeback 和断电的组合上。外置 USB 盘、外置阵列一旦意外断开或宿主机断电writeback 里未落盘的数据直接丢失虚拟机文件系统报错都算轻的重的直接起不来。我见过有人给外置 USB 盘配了 writeback结果运维误拔盘虚拟机里的 EXT4 直接进入只读状态最后靠 fsck 救回来一半数据。所以我的习惯是直通盘不设 cache或设 none存储池里的 qcow2 文件如果宿主机没有 UPS一律 cachenone有 UPS 且盘是走 SATA 直连的可以试 writeback但必须接受风险。对应到 libvirt XML 里就是disk typefile devicedisk driver nameqemu typeqcow2 cachenone/ source file/srv/vm-images/data.qcow2/ target devvdb busvirtio/ /disk注意 driver 节点的 cache 属性修改后需要完全关机再启动虚拟机才生效热重启不保证加载新参数。这是经常让人误以为“改了没用”的原地踩坑点。4.2 队列深度与 io_uring让外置 NVMe 盒子的延迟降下来同一块 NVMe 外置盘直通和存储池的性能差异不止来自文件系统层还来自 QEMU 的 IO 引擎和后端队列配置。老版本的 QEMU 用 libaio新版本推荐 io_uring。io_uring 对 NVMe 和高速外置盘更友好省掉不少系统调用开销。设置 io_uring 要在 XML 里加 iothread 和 io 参数domain iothreads2/iothreads devices disk typeblock devicedisk driver nameqemu typeraw cachenone ioio_uring ioeventfdon queue-size1024/ source dev/dev/disk/by-id/nvme-eui.xxxx/ target devvdb busvirtio/ iothread1/iothread /disk /devices /domain参数说明ioio_uring 让 QEMU 使用新一代异步 IOioeventfdon 允许虚拟机通知与数据拷贝并发queue-size1024 增大 virtio 队列深度让 NVMe 盘上的高队列深度请求不至于在虚拟化层排队。直通 NVMe 盒子时queue-size 从 1024 起调压测掉队列就降不掉的反而说明 IO 引擎或磁盘本身是瓶颈。这里有个血泪经验不要一上来就把 queue-size 调到 2048有的外置 NVMe 盒子固件会直接丢命令表现为虚拟机里整个盘消失一两秒比 1024 更难看。4.3 fio 压测先测盘再上生产延迟和 IOPS 都有数参数改完不能直接上生产我习惯用 fio 做一轮压测既验证参数生效也确认这块外置盘的性能上限。fio --namerandwrite-test \ --filename/dev/vdb \ --rwrandwrite \ --bs4k \ --size1G \ --iodepth32 \ --numjobs4 \ --ioenginelibaio \ --direct1 \ --runtime60 \ --time_based参数含义rwrandwrite 是随机写和数据库日志盘场景最接近iodepth32 是每个队列的并发深度超过队列深度后数据没意义numjobs4 模拟四路并发direct1 绕过虚拟机内页缓存压测的是真正的写路径runtime60 控制跑一分钟。压测外置机械盘时bs4k 的结果会很难看IOPS 三位数甚至两位数是正常的别拿到结果就去调参——那说明选型时就该直接走绕开文件系统的直通。测完看两列数据latency 的 p99 以及 iops 总和。同样条件做一轮 randread 对比如果写比读慢五倍以上说明外置存储的写缓存策略或盘的硬件特性有问题这时再回去检查 cache 参数和盘本身的写策略。5. 挂载外置存储的五个坑现象、原因、解决一条条说清楚5.1 坑一USB 设备直通后虚拟机里完全看不到盘现象virsh attach-device 执行成功没报错但虚拟机里 lsusb 和 lsblk 都找不到设备。原因链宿主机上这个 USB 设备被某个进程占用或 libvirt 没有足够的权限去重定向该设备。最常见的是宿主机桌面环境或系统服务抢先抓取了设备比如某些发行版的 udisks2 会自动挂载外置盘。解决先在宿主机上卸载和停用自动挂载服务udisksctl unmount -b /dev/sdb1 systemctl stop udisks2.service然后重新 attach。如果还不行检查 /var/log/libvirt/qemu/ 下的日志看有没有 Permission denied 的字样有的话给 USB 设备所在 cgroup 加访问权限。另一个隐蔽原因有的 USB 硬盘盒内部有休眠逻辑虚拟机里点一下磁盘图标才能唤醒。这是我遇到过的最玄学的一次最后是让对端虚拟机执行 echo 1 /sys/block/sdb/device/delete 再重新扫描解决的。5.2 坑二宿主机重启后外置盘盘符漂移导致虚拟机起不来现象宿主机因断电或维护重启虚拟机启动失败错误里提示找不到磁盘文件或 vdb 设备不存在。原因当初给虚拟机或存储池配的路径是 /dev/sdb1重启后外置盘变成了 /dev/sdc1。Linux 的 /dev/sdX 节点按发现顺序命名USB 设备的枚举顺序不稳定这是物理规律不是配置失误。解决把存储池定义里的 --source-dev 改成 /dev/disk/by-uuid/xxxx 这样的稳定路径虚拟机磁盘段则改成 /dev/disk/by-id/ 或 /dev/mapper/ 路径。改完执行 virsh pool-destroy 再 pool-start 验证一遍。virsh pool-edit extpool把 source-dev 改成 by-id 路径后重启存储池同一块盘就会有固定的身份标识。这里要提醒的是by-id 路径里如果包含分区号比如 nvme-eui.xxxx-part1分区表变更后这个后缀会变所以更稳妥的做法是整盘用 by-id分区用 blkid 的 UUID。5.3 坑三PCIe 直通 USB 控制器把宿主机键鼠一起带走现象给虚拟机直通了一张 PCIe 转 USB 卡虚拟机启动后宿主机鼠标键盘全部失灵直接“黑匣子”状态。原因PCIe 直通的最小单位是 IOMMU 分组不是设备。那张 USB 卡和卡上插的所有设备键鼠、U 盾在同一个 IOMMU 分组里一起被丢给虚拟机了。解决直通前执行 lspci -s 03:00.0 -vvv 查看 IOMMU group确保设备独立分组如果分组里有不想直通的东西物理上把键鼠换到宿主机板载 USB 口。更稳的做法是绕开 PCIe用 USB 设备级直通替代控制器直通只把目标盘重定向进去。这类问题排查时先切到 SSH 登录宿主机不要坐在那台机器前按键盘——所有按键都会进虚拟机越按越乱。这也是我做任何 PCIe 直通前必做 SSH 保底的原因。5.4 坑四外置盘文件在宿主机目录虚拟机却报 Cannot access storage file现象virt-manager 里给虚拟机加盘时路径填了 /mnt/extdisk/data.qcow2点击完成却报错无法访问。原因SELinux 或 AppArmor 拦截。libvirt 默认只信任 /var/lib/libvirt/images 目录外部目录的文件没有 virt_image_t 上下文qemu 进程无权读取。解决给目录和文件打上上下文标签。chcon -t virt_image_t /mnt/extdisk /mnt/extdisk/data.qcow2如果是目录里以后还会新增文件用 semanage 做持久规则semanage fcontext -a -t virt_image_t /mnt/extdisk(/.*)? restorecon -Rv /mnt/extdisk之后 /var/log/audit/audit.log 里不再出现 denied 记录。AppArmor 系统则需要在 /etc/apparmor.d/libvirt-qemu 里添加可读路径并 reload。查这种问题最快的命令是 ausearch -m avc -ts recent看的时候不要只看最后几行要在日志里搜 qemu 或 virt 关键词。5.5 坑五虚拟机迁移后找不到外置盘目标宿主上路径全错现象用 virsh migrate 把虚拟机迁到另一台宿主机目标机上虚拟机起不来报磁盘找不到。原因外置盘只挂在源宿主机上库里的存储池没在目标机定义或者目标机上挂载点名称不同。虚拟机迁移时只迁移了 XML 配置不会迁移物理盘。解决迁移前在目标宿主机重复一遍 3.3 的步骤先挂载外置盘UUID 挂载再 pool-define-as 同名存储池确保 XML 里 source file 的绝对路径和源机一致。路径不相同的话迁移完成后用 virsh edit 修改虚拟机磁盘路径再启动。值得留意的是如果外置盘由多路径软件管理源机和目标机看到的 multipath 别名必须一致否则会出现“盘在但路径识别不了”的怪象这个我放在最后一章讲。6. 跑通之后再做一件事用 multipath 和 by-id 给外置盘做永不漂移的身份外置盘真正跑稳不是看开机时能不能挂上而是看宿主机重启三次、盘拔插两次之后它还是不是那个它。我处理完一批外置存储后固定会做一遍“身份固化”。先看盘的 WWID。单盘用 udev 的 by-id 路径就够了但如果是双控制器磁盘阵列或支持多路径的设备系统里会出现多个 /dev/sdX 指向同一块盘直接挂载会造成数据错乱。这种场景用 device-mapper-multipath 合并路径配置写在 /etc/multipath.confmultipath -r multipath -ll能看到 WWID 和当前映射名。然后在配置里给盘起个别名blacklist { device { vendor ATA } } multipaths { multipath { wwid 36xxxxxxxxxxxxxxxx alias extbackup } }注意黑名单那段很重要本地 SATA 盘也会被 multipath 扫描到不加黑名单会把系统盘也卷进 multipath 管理。改完执行 multipath -r 重载路径会变成 /dev/mapper/extbackup这个设备节点在所有机器上一模一样。之后 fstab 和 libvirt 存储池都改用这个路径或它的 UUID不再看 /dev/sdX。验证方法很简单连续重启宿主机两三次每次重启后跑 multipath -ll确认 /dev/mapper/extbackup 一直在再拔掉外置盘重新插上确认节点恢复。通过这个验证后虚拟机迁移、盘符漂移就都成了过去式。我有一次深夜处理机柜断电重启二十多台虚拟机里只有没做 by-id 固化的两台起不来从那以后所有外置盘一律先固化身份再上业务。这套流程会多花半小时但省下的是半夜三点被叫起来的痛苦。希望帮到你。本文还有配套的精品资源点击获取
返回列表