virtio-scsi和virtio-blk的理解
virtio-scsi和virtio-blk都是c盘的半虚拟化驱动,virtio-scsi解决了virtio-blk的一些限制,来瞧瞧官网的介绍:
译文:
virtioscsihba代替virtioblk,这是一种简单的高性能准虚拟化储存设备。但是,virtioblk的设计固有的局限性如下:
virtioscsi是一种新的准虚拟化的scsi控制器设备。它提供了与virtioblk相同的性能,并降低了以下直接用处:
virtio-blk简介
virtio-blk是虚拟化KVM平台下虚拟c盘的一种实现方法,也是储存虚拟化所研究的主要对象之一。在KVM平台下,qemu程序负责模拟一台PC的整个工作过程,是虚拟化技术的真谛所在。你们晓得,在化学PC中,c盘是必不可少的设备,系统、应用程序的安装和数据的储存都离不开c盘。在虚拟化场景下,qemu自然也须要提供对c盘的模拟。那qemu究竟是怎样模拟c盘的?virtio-blk又是一种哪些样的虚拟c盘呢?
qemu对设备的模拟可以分成两类:全模拟和半模拟。全模拟即完全模拟化学设备的工作过程,致使运行在虚拟机上的软件完全感知不到自身运行环境的差别。诸如qemu中实现了对IDEc盘、LSI控制器(其上可接SCSIc盘)等化学储存设备的模拟,原本运行在化学机上的IDE驱动、LSI驱动或应用程序不做任何改动即可运行在虚拟机中。因而,全模拟的优点比较显著,即不用提供专门针对虚拟化场景的设备驱动,完全可以复用化学环境下的驱动程序。这么全模拟有何缺点呢?全模拟时linux系统安装教程,虚拟机内部驱动会频繁访问虚拟机IO端口,KVM平台下会造成大量的深陷和陷出操作;另外虚拟机内外数据传输时只能通过以字节为单位的拷贝方法进行,难以直接采用共享显存的形式,因而存在较大的访问性能问题。
为解决全虚拟化在性能上的问题,半模拟技术应运而生。它构造了一种虚拟化环境所独有的储存设备,因而半虚拟化须要在虚拟机内部安装特定的驱动程序能够正常驱使该设备进行工作。一般我们称虚拟机内部的驱动为后端驱动,称负责实现其功能模拟的程序(KVM平台下即为qemu程序)为前端程序,半模拟技术也经常被称作前后端技术。采用半摸拟技术后,配合后端驱动,虚拟化设备完全可以采用全新的风波通知和数据传递机制从而急剧提高性能,比如在virtio-blkc盘中,采用io_event_fd进行后端到前端通知,采用中断注入形式实现前端到后端的通知linux 查看scsi设备,并通过IO环(vring)进行数据的共享。至此,主要说明了virtio-blk形成的背景及其价值。附上qemu所模拟的PC(基于inteli440440fx显卡构架)的组成结布光,以作为后续深入剖析的基础。
qemu模拟实现的virtio-blk设备的组成结构如右图所示:
从图中可见,virtio-blk设备“内嵌”在一块PCI设备板(即virtio-blk-pci设备)上,其内部通过一条virtio总线联接PCI插口和virtio-blk设备。为什么要将virtio-blk设备设计成这样呢?
qemu模拟的所有设备都通过总线相连,总线下可挂接若干设备,桥接设备又可生成子总线;整个PC只有一条总线(即MainSystemBus,对应后端总线FSB)。因而,qemu内模拟的所有设备构成一棵总线与设备交替衍生的树。virito-blk是一种哪些样的设备?又该联接在哪些总线上呢?其实virtio-blk仅在虚拟化环境下存在,但若果完全陡然创造一种新的设备类型linux 查看scsi设备,那后端驱动开发将是一个很大的挑战。PCI设备是PC中最为常见的一种设备类别,且有较为健全的规范说明,因而可将virtio-blk设备模拟成一种PCI设备,这样可复用虚拟机内部已有的PCI驱动。
virtio-blk设备从功能上来看linux服务器系统,核心功能就是实现虚拟机内外的风波通知和数据传递:虚拟机内部的后端驱动打算好待处理的IO恳求和数据储存空间并通知前端;虚拟机外部的前端程序获取待处理的恳求并交给真正的IO子系统处理,完成后将处理结果通知后端。实际上,不仅虚拟c盘,虚拟网卡也完全可以复用这套机制,因而实现半模拟的网路前后端(virtio-net)。假如将virtio-blk或virtio-net设计成不同类型的PCI设备,这么后端驱动中会存在大量关于风波通知和数据传递的重复代码。
综上剖析,virtio-blk首先是PCI设备;其次为了复用半模拟中通用的风波通知和数据传递机制,具象出一类virtio-pci设备,其内部通过virtio总线联接不同的virtio设备。这样virtio-blk设备就通过virtio总线联接到virtio-blk-pci设备的PCI插口上,virtio-net也通过virtio总线联接到virtio-net-pci设备的PCI插口上。可能有的人会问,为什么通过设备的具象才能复用后端驱动的代码?在virtio-blk-pci或virtio-net-pci后端驱动加载时,最初辨识到的都是virtio-pci设备,这样都可调用virtio-pci驱动进行风波通知和数据传递的初始化,后续也可使用virtio-pci中相关函数进行风波通知和数据传递。
因而virtio-blk完全是基于通用的virtio框架实现的c盘前后端,virtio框架中最为核心的就是风波通知和数据传递机制。
使用VIRTIO_BLK(半虚拟化c盘)
virtio_blk驱动使用VirtioAPI为顾客机的提供了一个高效访问块设备I/O的方式。在QEMU/KVM对块设备使用virtio,须要两方面的配置:顾客机中的后端驱动模块virtio_blk和宿主机中的QEMU提供前端处理程序。目前比较流行的Linux发行版通常都将virtio_blk编译为内核模块了,可以作为顾客机直接使用virtio_blk,而windows中virtio驱动的安装方式已在5.1.2节中做了介绍。而且较新的qemu-kvm都是支持virtioblock设备的前端处理程序的。
启动一个使用virtio_blk作为c盘驱动的顾客机,其qemu-kvm命令行如下。
[root@jay-linuxkvm_demo]#qemu-system-x86_64-smp2-m1024-netnic-nettap–drivefile=rhel6u3.img,if=virtio
VNCserverrunningon`::1:5900'
在顾客机中,查看virtio_blk生效的情况如下所示。
[root@kvm-guest~]#grepVIRTIO_BLK/boot/config-2.6.32-279.el6.x86_64
CONFIG_VIRTIO_BLK=m
root@virtio-scsi-nodiscard-ceph-sas:~#lsmod|grepvirtio
virtio_balloon163840
virtio_console245761
virtio_scsi204802
virtio_net286720
virtio_pci245760
virtio_ring245765virtio_net,virtio_scsi,virtio_balloon,virtio_console,virtio_pci
virtio163845virtio_net,virtio_scsi,virtio_balloon,virtio_console,virtio_pci
scsi_mod2252806sd_mod,virtio_scsi,libata,scsi_transport_spi,sg,sym53c8xx
[root@kvm-guest~]#lspci|grep-iblock
00:04.0SCSIstoragecontroller:RedHat,IncVirtioblockdevice
[root@kvm-guest~]#lspci-vv-s00:04.0
00:04.0SCSIstoragecontroller:RedHat,IncVirtioblockdevice
Subsystem:RedHat,IncDevice0002
PhysicalSlot:4
Control:I/O+Mem+BusMaster-SpecCycle-MemWINV-VGASnoop-ParErr-Stepping-SERR-FastB2B-DisINTx+
Status:Cap+66MHz-UDF-FastB2B-ParErr-DEVSEL=fast>TAbort-SERR-
Interrupt:pinAroutedtoIRQ11
Region0:I/Oportsatc100[size=64]
Region1:Memoryatfebf2000(32-bit,non-prefetchable)[size=4K]
Capabilities:[40]MSI-X:Enable+Count=2Masked-
Vectortable:BAR=1offset=00000000
PBA:BAR=1offset=00000800
Kerneldriverinuse:virtio-pci
Kernelmodules:virtio_pci
[root@kvm-guest~]#fdisk-l
Disk/dev/vda:8589MB,8589934592bytes
16heads,63sectors/track,16644cylinders
Units=cylindersof1008*512=516096bytes
Sectorsize(logical/physical):512bytes/512bytes
I/Osize(minimum/optimal):512bytes/512bytes
Diskidentifier:0x000726b0
DeviceBootStartEndBlocksIdSystem
/dev/vda1*314826747110483Linux
/dev/vda2148261664591648082Linuxswap/Solaris
可知顾客机中早已加载virtio_blk等驱动,SCSIc盘设备是使用virtio_blk驱动(前面查询结果中显示为virtio_pci,由于它是作为任意virtio的PCI设备的一个基础、必备的驱动)。使用virtio_blk驱动的c盘显示为“/dev/vda”,使用virtio_scsi驱动的c盘显示为“/dev/sda”,这不同于IDE硬碟的“/dev/hda”或者SATA硬碟的“/dev/sda”这样的显示标示。
而“/dev/vd*”这样的c盘设备名称可能会造成从前分配在c盘上的swap分区失效,由于有些顾客机系统中记录文件系统信息的“/etc/fstab”文件中有类似如下的对swap分区的写法。
/dev/sda2swapswapdefaults00
或/dev/hda2swapswapdefaults00
缘由就是换为“/dev/vda2”这样的c盘分区名称未被正确辨识,解决这个问题的方式就很简单了,只须要更改它为如下的方式并保存“/etc/fstab”文件,之后重启顾客机系统即可。
/dev/vda2swapswapdefaults00
假如启动的是已安装virtio驱动的Windows顾客机,则在顾客机的“设备管理器”中的“存储控制器”中见到的是正在使用“RedHatVirtIOSCSIController”设备作为c盘。
RelatedPosts:(KVM连载)5.1.3使用virtio_balloon(KVM中的Ballooning)(下)怎样挂载qcow2格式的镜像文件(howtomountaqcow2image)(KVM连载)5.1.4使用virtio_net(半虚拟化网卡)virtio-blk-data-plane的配置使用
参考:
(KVM连载)5.1.5使用VIRTIO_BLK(半虚拟化c盘)
virtio-blk的影响virtioscsi相比较virtioblk的强的地方
virtio-scsi功能是一种新的半虚拟化SCSI控制器设备。它是取代virtio-blk并改进其功能的KVMVirtualization储存堆栈的取代储存实现的基础。它提供与virtio-blk相同的性能,并降低了以下直接用处:
virtio-SCSI的优势在于它还能处理数百个设备,而virtio-blk只能处理大概30个设备并用尽PCI插孔。virtio-scsi致力代替virtio-blk,保留了virtio-blk的性能优势,同时提升了储存可扩充性,容许通过单个控制器访问多个储存设备,并支持重用顾客操作系统的SCSI堆栈。
virtioscsi的c盘的命名为/dev/sda,通常的命名为/dev/vda
virtioscsi的配置:对centos这个镜像执行以下操作:
#glanceimage-update--propertyhw_disk_bus=scsicentos
#glanceimage-update--propertyhw_scsi_model=virtio-scsicentos
创建好的虚机使用命令lsblk查看
root@virtio-blk-test:~#lsblk
NAMEMAJ:MINRMSIZEROTYPEMOUNTPOINT
vda254:0020G0disk
└─vda1254:1020G0part/
vdb254:16064M1disk
vdc254:320200G0disk/home/cloud-disk
root@virtio-scsi-nodiscard-ceph-sas:~#lsblk
NAMEMAJ:MINRMSIZEROTYPEMOUNTPOINT
sda8:0020G0disk
└─sda18:1020G0part/
sdb8:160200G0disk/home/cloud-disk
sdc8:32064M1disk
参考硬碟的插口形式:硬碟基础知识(HDD、SSD、IDE、PATA、SATA、SCSI、SAS)
配置virtio-scsi:
配置SCSI:virtio是一套半虚拟化驱动,包括网路、磁盘等。virtio-scsi和virtio-blk都是c盘的半虚拟化驱动,virtio-scsi解决了virtio-blk的一些限制
查看内核是否支持配置SCSI
(my_new_env)likailiang@pubbeta1-nova10:~$grep"VIRTIO"/boot/config-3.2.0-4-amd64
CONFIG_NET_9P_VIRTIO=m
CONFIG_VIRTIO_BLK=m
CONFIG_SCSI_VIRTIO=m
CONFIG_VIRTIO_NET=m
CONFIG_VIRTIO_CONSOLE=m
CONFIG_HW_RANDOM_VIRTIO=m
CONFIG_VIRTIO=m
CONFIG_VIRTIO_RING=m
CONFIG_VIRTIO_PCI=m
CONFIG_VIRTIO_BALLOON=m
#CONFIG_VIRTIO_MMIOisnotset
(my_new_env)likailiang@pubbeta1-nova10:~$grep"VIRTIO"/boot/config-3.10.45-openstack-amd64
CONFIG_NET_9P_VIRTIO=m
CONFIG_VIRTIO_BLK=m
CONFIG_SCSI_VIRTIO=m
CONFIG_VIRTIO_NET=m
CONFIG_VIRTIO_CONSOLE=m
CONFIG_HW_RANDOM_VIRTIO=m
CONFIG_VIRTIO=m
CONFIG_VIRTIO_PCI=m
CONFIG_VIRTIO_BALLOON=m
#CONFIG_VIRTIO_MMIOisnotset
Centos6下Virtio-SCSI(multi-queues)/Virtio-SCSI/Virtio-blk性能对比: