NUMA技术是解决多CPU共同工作的技术方案,多CPU共同工作主要有3中架构:SMP:Symmetric Multi-Processor),非统一存储访问结构(NUMA:Non-Uniform Memory Access),以及海量并行处理结构(MPP:Massive Parallel Processing;
访问存储器可以分为两种:统一存储器访问(UMA)和非统一存储器访问(NUMA)。
1.SMP技术:
SMP多个CPU通过一个总线访问存储器,SMP系统有事也被称为一致内存访问(UMA)结构体系;在SMP系统上,所有的cpu对共享内存控制器拥有相同的访问权限。cpu之间的访问这个共享资源的请求会导致拥塞。这个单独的内存控制器能够管理的内存大小也是有限的;
2.MPP模式:
MPP提供了另外一种进行系统扩展的方式,它由多个SMP服务器通过一定的节点互联网络进行连接,协同工作,完成相同的任务,从用户的角度来看是一个服务器系统。其基本特征是由多个SMP服务器通过节点互联网络连接而成,每个节点只访问自己的本地资源(内存、存储等),是一种完全无共享(Share Nothing)结构,因而扩展能力最好,理论上其扩展无限制,目前的技术可实现512个节点互联,数千个CPU。目前业界对节点互联网络暂无标准,如 NCR的Bynet,IBM的SPSwitch,它们都采用了不同的内部实现机制。但节点互联网仅供MPP服务器内部使用,对用户而言是透明的。
3.NUMA技术
NUMA模式是每个处理器有自己的存储器,每个处理也可以访问别的处理器的存储器;与UMA相比,UMA提供了一个集中的内存池(因此在一定数量的处理器之后无法扩展),NUMA架构将内存划分为相对于微处理器的本地和远程内存。
4.KVM虚拟机NUMA调优
NUMA架构每个处理器都可以访问自己的存储器和其他处理器的存储器,访问自己的存储器要比访问其他的存储器快的多,速度相差10-100倍,所以NUMA调优的目的就是让处理器尽量访问自己的存储器,以提高访问速度。
#安装 numactl
[root@node3 ~] yum install numactl
#安装后出现以下三个命令
#numactl 用于控制 进程与共享存储的 NUMA 技术机制
#numademo
#numastat 提供了一个监测NUMA架构的工具
[root@node3 ~] # numactl --hardware #共有2个node,各领取16个CPU和128G内存
available: 2 nodes (0-1)
node 0 cpus: 0 1 2 3 4 5 6 7 16 17 18 19 20 21 22 23
node 0 size: 131037 MB
node 0 free: 3019 MB
node 1 cpus: 8 9 10 11 12 13 14 15 24 25 26 27 28 29 30 31
node 1 size: 131071 MB
node 1 free: 9799 MB
node distances:
node 0 1
0: 10 20
1: 20 10
[root@node3 ~] # numactl --cpubind=0 --membind=0 python param #python在node0中执行
[root@node3 ~] # numactl --cpubind=1 --membind=1 java param #java在node1中执行
[root@node3 ~] # numactl --interleave=all mongod -f /etc/mongod.conf #分配所有的node供mongodb使用
[root@node3 ~]# numastat #通过numastat命令可以查看numa状态
node0 node1
numa_hit 1775216830 6808979012 #使用本节点内存次数
numa_miss 4091495 494235148 #计划使用本节点内存而被调度到其他节点次数
numa_foreign 494235148 4091495 #计划使用其他节点内存而使用本地内存次数
interleave_hit 52909 53004 #交叉分配使用的内存中使用本节点的内存次数
local_node 1775205816 6808927908 #在本节点运行的程序使用本节点内存次数
other_node 4102509 494286252 #在其他节点运行的程序使用本节点内存次数
[root@node3 ~]# virsh list --all
Id Name State
----------------------------------------------------
17 centos7.0 running
20 centos7.2 running
[root@node3 ~]# virsh numatune 20 #命令可以查看或者修改虚拟机的NUMA配置
numa_mode : strict
numa_nodeset :
[root@node3 ~]# virsh vcpuinfo centos7.2 #查看虚拟机的VCPU调度信息
VCPU: 0
CPU: 1 #vcpu 0 被调用到cpu1上
State: running #使用状态
CPU time: 17.6s #使用时间
CPU Affinity: yyyy 可以使用的物理CPU内部的逻辑核
[root@node3 ~]# virsh emulatorpin centos7.2 #查看虚拟机调用那些CPU
emulator: CPU Affinity
----------------------------------
*: 0-7
[root@node3 ~]# virsh numatune centos7.2 #设置虚拟机CPU在部分物理CPU之间调度
numa_mode : strict
numa_nodeset :
[root@node3 ~]# virsh emulatorpin centos7.2 4-7 --live
[root@node3 ~]# virsh emulatorpin centos7.2
emulator: CPU Affinity
----------------------------------
*: 4-7
[root@node3 ~]# virsh dumpxml 2 |grep vcpu -C2 #查看配置看VCPU调度信息
<memory unit='KiB'>4188160</memory>
<currentMemory unit='KiB'>2097152</currentMemory>
<vcpu placement='static' current='2'>4</vcpu>
<cputune>
<emulatorpin cpuset='4-7'/>
CPU绑定技术和原理:
CPU绑定实际是通过Libvirt通过CGroup来实现的,CGroup直接去绑定KVM虚拟机进程也可以。CGroup不仅可以绑定CPU,也可以绑定虚拟机磁盘,网络的资源控制;
#强制VCPU和物理CPU一对一的绑定
[root@node3 ~]# virsh vcpupin centos7.2 0 4 #绑定VCPU 0和物理CPU 4
[root@node3 ~]# virsh vcpupin centos7.2 1 5
[root@node3 ~]# virsh vcpuinfo centos7.2
VCPU: 0
CPU: 4
State: running
CPU time: 17.9s
CPU Affinity: ----y---
VCPU: 1
CPU: 5
State: running
CPU time: 10.6s
CPU Affinity: -----y--
[root@node3 ~]# virsh dumpxml 2 |grep vcpu -C2 #查看配置文件信息
<memory unit='KiB'>4188160</memory>
<currentMemory unit='KiB'>2097152</currentMemory>
<vcpu placement='static' current='2'>4</vcpu>
<cputune>
<vcpupin vcpu='0' cpuset='4'/>
<vcpupin vcpu='1' cpuset='5'/>
<vcpupin vcpu='2' cpuset='6'/>
<emulatorpin cpuset='4-7'/>
</cputune>
参考:
https://access.redhat.com/documentation/en-us/red_hat_enterprise_linux/6/html/virtualization_tuning_and_optimization_guide/chap-virtualization_tuning_optimization_guide-numa
http://docs.redhat.com
https://docs.openstack.org/queens/
http://cloud.centos.org
https://www.centos.org/