为了账号安全,请及时绑定邮箱和手机立即绑定

KVM半虚拟化设备virtio及性能调优最佳实践

标签:
C#

为了提高硬盘,网络的性能,需要支持半虚拟化

在全虚拟化状态下,Guest OS不知道自己是虚拟机,于是像发送普通的IO一样发送数据,被Hypervisor拦截,转发给真正的硬件

在半虚拟化状态下,Guest需要安装半虚拟化驱动,Guest OS知道自己是虚拟机,所以数据直接发送给半虚拟化设备,经过特殊处理,发送给真正的硬件

半虚拟化驱动的例子:virtio, Vmware Tools

然而要虚拟的设备多种多样,要支持的硬件多种多样,需要统一的接口,这就是virtio的使命

不同的虚拟设备和不同的虚拟机可以有不同的前端驱动

不同的硬件设备可以有不同的后端驱动

两者之间的交互遵循virtio的标准

virtio层是虚拟队列接口,virtio-net网络驱动程序使用两个虚拟队列(一个用于接收,另一个用于发送),而virtio-blk块驱动程序仅使用一个虚拟队列。

Transport(virtio-ring)实现了环形缓冲区(ring buffer),用于保存前端驱动和后端处理程序执行的信息,并且它可以一次性保存前端驱动的多次I/O请求,并且交由后端去动去批量处理。

我们首先来看硬盘虚拟化virtio_blk

qemu-system-x86_64 -enable-kvm -name ubuntutest -m 2048 -balloon virtio -drive file=ubuntutest.qcow2,if=virtio -vnc :19 -net nic,model=virtio -net tap,ifname=tap0,script=no,downscript=n -monitor stdio

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

virtio-blk-data-plane:进一步提高性能,每个device单独的线程,仅支持raw disk,不支持storage migration

我们再来看网络设备虚拟化virtio_net

ethtool -i eth0

TSO是通过网络设备进行TCP段的分割,从而来提高网络性能的一种技术

GSO(Generic Segmentation Offload) 应用于其他的传输层协议,如TCPv6,UDP

应用层可以使用ethtool -K eth0 tso off|on命令对支持TSO特性的网络设备进行TSO功能的关闭和启用

使用virtio_net性能低,可尝试关闭这两个选项

使用Virtio的性能比较如下:

有了virtio性能会好很多。

所以性能优化的第一个最佳实践是:使用半虚拟化驱动virtio,对于block storage,使用virtio_blk,对于network,使用virtio_net

**在CPU方面
**

每个Guest相当于一个进程,Guest中的每个vcpu相当于一个线程

Host CPU支持进程间切换,SMP可以并行执行多个进程,从而可以进行CPU超配

CPU的超配增加了进程上下文切换,从而可能带来富贵论坛
性能问题

为了保证Guest进行能够得到足够的时间片,常常使用cgroup的cpu.cfs_period_us和cpu.cfs_quota_us来控制

Cfs全称Completely Fair Scheduler是Linux Kernel的调度策略

cfs_period_us的意思是cgroup对CPU的调度的干预周期,cfs_quota_us是指则一个周期内这个进程得到的时间片长度。比如cfs_period_us=100000说明100毫秒cgroup进行一次干预,cfs_quota_us=25000表示在100毫秒里面,这个进程能够得到25毫秒的时间片,如果对cgroup进行的修改,则要等到下个100毫秒才起作用

Processor Pin: 可以讲vCPU pin到一个或者一组共享cache的物理CPU上,由于cache共享,则很多命令和数据都被缓存,从而提高性能。缺点是即便其他物理CPU空闲,由于绑定到了这个CPU,也得不到运行

CPU和Cache拓扑模型/sys/devices/system/cpu

virsh vcpupin guest# vproc# pproc#,pproc#

**在内存方面
**

KSM全称Kernel Same Page Merging

Qemu向KSM注册内存,KSM对内存进行扫描,将相同的内存区域设为共享,并且copy on write

cat /boot/config-3.13.0-27-generic | grep KSM CONFIG_KSM=y

共享内存节约内存空间,但是内存扫描同时影响性能

使用virtio_balloon

尽量不要使用swap,/proc/sys/vm/swappiness设为0

多核的两种方式:SMP和NUMA

SMP的问题主要在CPU和内存之间的通信延迟较大、通信带宽受限于系统总线带宽,同时总线带宽会成为整个系统的瓶颈

NUMA(Non-Uniform Memory Access):每个处理器有其可以直接访问其自身的“本地”内存池,使CPU和这块儿内存之间拥有更小的延迟和更大的带宽。而且整个内存仍然可做为一个整体,可以接受来自任何CPU的访问。

禁止zone_reclaim_mode:/proc/sys/vm/zone_reclaim_mode

当操作系统分配内存时,发现CPU本节点的内存已满,如果reclaim=true,则将会回收一部分本地内存,否则将分配其他节点的内存

使用KSM和Huge Page都会造成reclaim

建议开启大页Huge pages,从而提高地址转换的效率

普通页:PDPT -> PD -> Page Table -> In Page Offset

Translation Lookaside Buffer (TLB)是一个从虚拟地址到物理地址转换的一个Cache

Huge Page不但使得每次地址转换比较快,而且使得TLB每个记录较小,相同的内存的情况下,保存的记录较多,Cache命中率较高

大页:PDPT -> PD -> In Page Offset

**在网络方面
**

使用tap作为网卡配置

使用virtio_net

使用PCI passthough可以提高性能,但是影响虚拟机迁移

可以使用DPDK或者SR-IOV

在存储方面

尽量使用block device,性能更好,无需管理HOST文件系统,无需管理稀疏文件,I/O Cache以4K为边界。

如果不能使用block device,则只好使用Image File。易管理,易移动,但需要HOST文件系统,需要管理稀疏文件

Partition问题:标准分区软件分区是以512byte一个Cylinder为边界的,Linux系统的I/O Cache是以4K为边界的,所以Linux下的标准文件系统将分区format的时候,会将文件以4k为边界进行存储,从而每次缓存正好缓存整个page(大小4k)

Image File作为一个文件,在Host文件系统中一定是以4k为边界的,然而一个Image File对于Guest来讲是整块硬盘,对其分区的时候往往不是以4K为边界的,从而Guest上读取文件的时候,本来是读取缓存的4K一个page,映射到Host文件系统上,变成了两个Page。写入也要更新两个页。

Host使用ext3文件系统,因为ext4的barrier会影响性能

使用raw image,比qcow2性能要好

选择正确的cache策略:

Page Cache: Host和Guest在FS和Block层都有自己的Page Cache,我们无法控制Guest里面的设置,但是可以配置Host Page Cache

Disk Write Cache在Hypervisor层

Cache Mode有以下四种,推荐使用none

I/O Scheduler推荐使用Deadline I/O scheduler

点击查看更多内容
1人点赞

若觉得本文不错,就分享一下吧!

评论

作者其他优质文章

正在加载中
感谢您的支持,我会继续努力的~
扫码打赏,你说多少就多少
赞赏金额会直接到老师账户
支付方式
打开微信扫一扫,即可进行扫码打赏哦
今天注册有机会得

100积分直接送

付费专栏免费学

大额优惠券免费领

立即参与 放弃机会
意见反馈 帮助中心 APP下载
官方微信

举报

0/150
提交
取消