目录

概述

I/O设备半虚拟化驱动(virtio)

Guest of Windows

Guest of Linux

Virtio in Openstack

virtio_blk和virtio-scsi

virtio-blk:

virtio-scsi:


概述

IDE       - Slow Write in the Guest System
SCSI     - Faster Write(as IDE) in Guest System
VIRTIO - Fastest Write (more that SCSI and IDE) in the Guest System, but only with extra Drivers (In Guest)

磁盘驱动

类型

兼容性

性能

磁盘命名

虚拟机支持最大磁盘数量

热插拔

备注

IDE

全虚拟化

最好

/dev/hdX

依赖IDE协议限制(测试值3)

不支持

虚机无需更改,使用方便

SATA

全虚拟化

virtio-blk/

virtio

半虚拟化

较好

/dev/vdX

受限虚机PCI槽数限制

理论:30(测试值14)

支持,可以在线添加硬盘

为了改善全虚拟化性能,部分系统需要安装virtio驱动

virtio-scsi/

scsi

半虚拟化

与virtio-blk持平

/dev/sdX

受限于内核限制:18278

支持

为了解决virtio的诸多限制,用以替代virtio

注释:CentOS6.x只支持IDE、virtio;CentOS7.x增加支持SATA、scsi。

整体上来看这三者的最大不同还是挂载磁盘的数量。
一台win7的虚拟机,最多可以创建3个ide硬盘,当再次创建新的ide硬盘时候,会提示无法创建。
同时,实验中最多创建了14块virtio硬盘,虽然界面允许创建更多virtio硬盘,但是超过14块,虚拟机是无法启动的。
virtio-scsi可以创建足够多的硬盘,以至于协议自身并不是限制因素,而内核的限制反而成了硬盘数目的极限。

KVM是必须使用硬件虚拟化辅助技术(如Intel VT-x、AMD-V)的hypervisor。

在CPU运行效率方面有硬件支持,其效率是比较高的;

在I/O虚拟化方面,传统的方式是使用QEMU纯软件的方式来模拟I/O设备。但可以在客户机中使用半虚拟化驱动(Paravirtualized Drivers,PV Drivers)来提高客户机的性能(特别是I/O性能):

  • 全虚拟化时GuestOS不知道自己是虚拟机,于是像发送普通的IO一样发送数据,被Hypervisor拦截,并经由QEMU转发给真正的硬件。
  • 在半虚拟时GuestOS知道自己是虚拟机(我理解应该驱动是经过修改的),即GuestOS安装的是半虚拟化驱动,所以数据直接发送给半虚拟化设备,经过特殊处理,发送给真正的硬件。因此性能要好于全虚拟化。

I/O设备半虚拟化驱动(virtio)

包括:磁盘I/O、网络I/O

目前,KVM中实现半虚拟化驱动的方式是采用了virtio这个Linux上的设备驱动标准框架。Virtio半虚拟化驱动的方式,可以获得很好的I/O性能,其性能几乎可以达到和native(即:非虚拟化环境中的原生系统)差不多的I/O性能。

所以,在使用KVM之时,如果宿主机内核和客户机都支持virtio的情况下,一般推荐使用virtio达到更好的性能。

当然,virtio也是有缺点的,它必须要客户机安装特定的Virtio驱动使其知道是运行在虚拟化环境中,且按照Virtio的规定格式进行数据传输,不过客户机中可能有一些老的Linux系统不支持virtio主流的Windows系统需要安装特定的驱动才支持Virtio。不过,较新的一些Linux发行版(如RHEL 6.3、Fedora 17等)默认都将virtio相关驱动编译为模块,可直接作为客户机使用virtio,而且对于主流Windows系统都有对应的virtio驱动程序可供下载使用。

Guest of Windows

主流Windows virtio驱动下载地址:

https://docs.fedoraproject.org/en-US/quick-docs/creating-windows-virtual-machines-using-virtio-drivers/index.html

创建Windows镜像:https://docs.openstack.org/image-guide/windows-image.html 

Guest of Linux

Linux下查看内核是否支持virtio:

# grep "VIRTIO" /boot/config-3.10.0-1062.9.1.el7.x86_64
……
CONFIG_VIRTIO_BLK=m
CONFIG_SCSI_VIRTIO=m
CONFIG_VIRTIO_NET=m
……

Virtio in Openstack

openstack对virtio支持,是通过Image实现的。

首先Image需要像上面Linux一样内核支持,否则需要提前安装virtio驱动。openstack默认使用virtio-blk创建虚机,如果要使用scsi,需要设置Image的property。

https://docs.openstack.org/glance/latest/admin/useful-image-properties.html

$ openstack image set --property hw_disk_bus=scsi centos7-mini
$ openstack image set --property hw_scsi_model=virtio-scsi centos7-mini


$ openstack image show centos7-mini |grep properties
| properties       | hw_disk_bus='scsi', hw_scsi_model='virtio-scsi'      |

$ openstack image show win10-scsi |grep properties
| properties       | hw_disk_bus='scsi', hw_scsi_model='virtio-scsi'      |

如果使用IDE,则会报:INACCESSIBLE BOOT DEVICE蓝屏。

                          

virtio_blk和virtio-scsi

确认硬盘是否为半虚拟化设备(Linux$ lsblk

使用virtio_blk驱动的硬盘显示为/dev/vda
使用IDE硬盘显示为/dev/hda
使用SATA硬盘显示/dev/sda。

确认网络设备是否为半虚拟化设备

使用ethtool -i 设备名 查看,当driver为virtio_net时说明为半虚拟化的。

virtio-blk

虚拟机启动参数:

-device virtio-blk-pci,scsi=off,bus=pci.0,addr=0x7,drive=drive-virtio-disk0,id=virtio-disk0,bootindex=1
-drive file=/home/images/win10-virtio.qcow2,format=qcow2,if=none,id=drive-virtio-disk0 

对应Libvirt XML描述文件:

<disk type='file' device='disk'>
      <driver name='qemu' type='qcow2' cache='none'/>
      <source file='/var/lib/libvirt/images/win10-virtio.qcow2'/>
      <target dev='vda' bus='virtio'/>
      <address type='pci' domain='0x0000' bus='0x00' slot='0x04' function='0x0'/>
</disk>

虚拟机内部:

$ lspci
……
00:05.0 SCSI storage controller: Red Hat, Inc Virtio block device

$ lsblk
vda
……

virtio-scsi

虚拟机启动参数:

-device virtio-scsi-pci,id=scsi0,bus=pci.0,addr=0x6
-drive file=/home/images/win10-scsi.qcow2,format=qcow2,if=none,id=drive-scsi0-0-0-0
-device scsi-hd,bus=scsi0.0,channel=0,scsi-id=0,lun=0,drive=drive-scsi0-0-0-0,id=scsi0-0-0-0,bootindex=1

对应的Libvirt XML描述如下:

 <controller type='scsi' index='0' model='virtio-scsi'/>
 <disk type='file' device='disk'>
      <driver name='qemu' type='qcow2'/>
      <source file='/home/images/win10-scsi.qcow2'/>
      <target dev='sda' bus='scsi'/>
      <address type='drive' controller='0' bus='0' target='0' unit='0'/>
 </disk>

虚拟机内部:

$ lspci
……
00:04.0 SCSI storage controller: Red Hat, Inc Virtio SCSI

或

$ lsscsi
[2:0:0:0]    disk    QEMU     QEMU HARDDISK    2.5+  /dev/sda

$ lsblk
sda
……
Logo

开放原子开发者工作坊旨在鼓励更多人参与开源活动,与志同道合的开发者们相互交流开发经验、分享开发心得、获取前沿技术趋势。工作坊有多种形式的开发者活动,如meetup、训练营等,主打技术交流,干货满满,真诚地邀请各位开发者共同参与!

更多推荐