OpenStack NUMA 配置

NUMA 體系架構

  • SMP 體系架構
  • NUMA 體系架構
  • NUMA 結構基本概念
  • Openstack flavor NUMA 策略
  • Nova 實現 NUMA 流程

 1. SMP 體系架構

CPU 計算平臺體系架構分爲 SMP 體系架構和 NUMA 體系架構等,下圖爲 SMP 體系架構:node

SMP(Sysmmetric Multi-Processor System,對稱多處理器系統),它由多個具備對稱關係的處理器組成。所謂對稱,即處理器之間是水平的鏡像關係,沒有主從之分。SMP 架構使得一臺計算機再也不由單個 CPU 組成。數據庫

SMP 的結構特徵是多處理器共享一個集中式存儲器,每一個處理器訪問存儲器的時間片一致,使工做負載可以均勻的分配到全部可用處理器上,極大地提升了整個系統的數據處理能力。可是,若是多個處理器同時請求訪問共享資源時,就會引起資源競爭,須要軟硬件實現加鎖機制來解決這個問題。因此,SMP 又稱爲 UMA(Uniform Memory Access,一致性存儲器訪問),其中,一致性指的是在任意時刻,多個處理器只能爲內存的每一個數據保存或共享一個惟一的數值。api

所以,這樣的架構設計沒法擁有良好的處理器數量擴展性,由於共享內存的資源競態老是存在的,處理器利用率最好的狀況只能停留在 2 到 4 顆。緩存

 

2. NUMA 體系架構

計算機系統中,處理器的處理速度要遠快於內存的讀寫速度,因此限制計算機計算性能的瓶頸在存儲器帶寬上。SMP 架構由於限制了處理器訪問存儲器的頻次,因此處理器可能會時刻對數據訪問感到飢餓。架構

NUMA(Non-Uniform Memory Access,非一致性存儲器訪問)架構優化了 SMP 架構擴展性差以及存儲器帶寬窄的問題。socket

從上圖能夠看出,NUMA 和 SMP 架構是相似的,一樣只會保存一份操做系統和數據庫的副本,表示 NUMA 架構中的處理器依舊可以訪問到整個存儲器。兩種主要的區別在於 NUMA 架構採用了分佈式存儲器,將處理器和存儲器劃分爲不一樣的節點(NUMA Node),每一個節點都包含了若干的處理器與內存資源。多節點的設計有效提升了存儲器的帶寬和處理器的擴展性。假設系統含有 4 個 NUMA 節點,那麼在理想狀況下系統的存儲器帶寬將會是 SMP 架構的 4 倍。分佈式

另外一方面,NUMA 節點的處理器能夠訪問到總體存儲器。按照節點內外,內存被分爲節點內部的本地內存以及節點外部的遠程內存。當處理器訪問本地內存時,走的是內部總線,當處理器訪問遠程內存時,走的是主板上的 QPI 互聯模塊。訪問前者的速度要遠快於後者,NUMA(非一致性存儲器訪問)所以而得名。

性能

3. NUMA 結構基本概念

  • Socket:表示一顆物理 CPU 的封裝(物理 CPU 插槽),簡稱插槽。爲了不將邏輯處理器和物理處理器混淆,Intel 將物理處理器稱爲插槽。
  • Core: 物理 CPU 封裝內的獨立的一組程序執行的硬件單元,好比寄存器,計算單元等。
  • Thread: 使用超線程技術虛擬出來的邏輯 Core,須要 CPU 支持。爲了便於區分,邏輯 Core 通常被寫做 Processor。在具備 Intel 超線程技術的處理器上,每一個內核能夠具備兩個邏輯處理器,這兩個邏輯處理器共享大多數內核資源(如內存緩存和功能單元)。此類邏輯處理器一般稱爲 Thread 。優化

  • Node: 包含有若干個物理 CPU 的組。

上圖的  NUMA Topology 有 2 個 NUMA node,每一個 node 有 1 個 socket,即 pCPU, 每一個 pCPU 有 6 個 core,1 個 core 有 2 個 Processor,則共有邏輯 cpu processor 24 個。ui

在 LIUNX 命令行中執行 lscpu 便可看到機器的 NUMA 拓撲結構:

如上圖所示,機器有 2 個 node 分配到 2 個 socket 上,每一個 socket 有 14 個 core,每一個 core 有 2 個 processor, 則共有 56 個 cpu processor。同時,從上圖也可看出 NUMA node 0 上的 cpu 分佈爲 0-13,28-41,而 node 1 上的分佈爲 14-27, 42-55。

由上節分析知,NUMA node 處理器訪問本地內存的速度要快於訪問遠端內存的速度。訪問速度與 node 的距離有關係,node 間的距離稱爲 node distance,使用  numactl --hardware  能夠 show 出該距離:

node0 的本地內存大小爲 32209MB,Node1 的本地內存大小爲 32316MB。Node0 到本地內存的 distance 爲 10,到 node1 的內存 distance 距離爲 20。node1 到本地內存的 distance 爲10,到 node0 的內存distance距離爲20。

進一步對上面的 NUMA Topology 圖進行介紹。

Liunx 上使用 cat /proc/cpuinfo 命令 show 出 cpu 信息:

其中 physical  id 表示 socket 號。當前的 cpu core 是第 14 個 ,siblings 爲 28 表示此 cpu14 在 core14 裏面的兄弟邏輯 cpu 爲 cpu28。CPU 14 和 CPU 28 共享 L1 Data cache、L1 instruction 和 L2 Cache 。

[***@controller-0 ~]$ cat /sys/devices/system/cpu/cpu14/cache/index0/type
Data
[***@controller-0 ~]$ cat /sys/devices/system/cpu/cpu14/cache/index1/type
Instruction
[***@controller-0 ~]$ cat /sys/devices/system/cpu/cpu14/cache/index2/type
Unified
[***@controller-0 ~]$ cat /sys/devices/system/cpu/cpu14/cache/index0/size
32K
[***@controller-0 ~]$ cat /sys/devices/system/cpu/cpu14/cache/index1/size
32K
[***@controller-0 ~]$ cat /sys/devices/system/cpu/cpu14/cache/index2/size
256K

 

4. Openstack flavor NUMA 策略

cpu 綁核策略

 對 Libvirt 驅動而言,虛擬機的 vCPU 能夠綁定到主機的物理 CPU 上(pCPU)。這些配置能夠改善虛擬機實例的精確度與性能。

 openstack flavor set FLAVOR-NAME \
    --property hw:cpu_policy=CPU-POLICY \
    --property hw:cpu_thread_policy=CPU-THREAD-POLICY

有效的CPU-POLICY值爲:

  • shared (默認值) : 虛擬機的 vCPU 容許在主機 pCPU 上自由浮動,儘管可能受到 NUMA 策略的限制。
  • dedicated: 虛擬機 vCPU 被嚴格綁定到一組主機 pCPU 上。

有效的 CPU-THREAD-POLICY 值爲:

  • prefer (默認值) : 主機多是也可能不是 SMT 架構,若是應用 SMT 架構時,優選兄弟線程。
  • isolate: 應用在主機可能不是 SMT 架構,或者必須模擬非 SMT 架構。當主機不是 SMT 架構時,每一個 vCPU 至關於一個核。若是主機應用 SMT 架構,也就是說一個物理核有多個兄弟線程,每一個 vCPU 也至關於一個物理核。其餘虛擬機的 vCPU 不會放在同一個核上。選中的核上只有一個兄弟線程可用。
  • require: 主機必要使用 SMT 架構。每一個 vCPU 被分配在兄弟線程上。若是主機沒有 SMT 架構,那就不使用此主機。若是主機使用 SMT 架構,卻沒有足夠空閒線程的核,那麼 nova 調度失敗。
有一點要注意的是 cpu_thread_policy 只在 hw:cpu_policy 設置爲 dedicated 時纔有效。

NUMA拓撲

Libvirt 驅動程序能夠爲虛擬機 vCPU 定義放置的 NUMA 節點,或者定義虛擬機從哪一個 NUMA 節點分配 vCPU 與內存。

$ openstack flavor set FLAVOR-NAME \
    --property hw:numa_nodes=FLAVOR-NODES \
    --property hw:numa_cpus.N=FLAVOR-CORES \
    --property hw:numa_mem.N=FLAVOR-MEMORY
  • FLAVOR-NODES: 限制虛擬機 vCPU 線程運行的可選 NUMA 節點數量。若是不指定,則 vCPU 線程能夠運行在任意可用的 NUMA 節點上。
  • N:  應用 CPU 或內存配置的虛擬機 NUMA 節點,值的範圍從 0 到 FLAVOR-NODES - 1。好比爲 0,則運行在NUMA節點 0,爲 1,則運行在 NUMA 節點1。
  • FLAVOR-CORES: 映射到虛擬機NUMA節點N上的虛擬機vCPU列表。若是不指定,vCPU 在可用的 NUMA 節點之間平均分配。
  • FLAVOR-MEMORY: 映射到虛擬機 NUMA 節點 N 上的虛擬機內存大小。若是不指定,則內存平均分配到可用 NUMA 節點。

舉例以下:

$ openstack flavor set aze-FLAVOR \
    --property hw:numa_nodes=2 \
    --property hw:numa_cpus.0=0,1 \ 
    --property hw:numa_cpus.1=2,3 \
    --property hw:numa_mem.0=2048 \
    --property hw:numa_mem.1=2048 \
Flavor 定義虛擬機有 4 個 vCPU,4096MB 內存,它們分佈在 2 個 NUMA 節點上。虛擬機的 0 號與 1 號 vCPU 在 NUMA 0 上,2 號與 3 號 vCPU 在 NUMA 1 上。虛擬機的 2048MB 內存在 NUMA 0 上,另外的 2048MB 內存分配到在 NUMA 1上。
注意:hw:numa_cpus.N 與 hw:numa_mem.N 只在設置 hw:numa_nodes 時有效。N 是虛擬機 NUMA 節點的索引,並不必定對應主機 NUMA 節點。例如,在兩個 NUMA 節點的平臺,根據 hw:numa_mem.0,調度會選擇虛擬機 NUMA 節點 0,可是倒是在主機 NUMA 節點 1 上,反之亦然。相似的,FLAVOR-CORES 也是虛擬機 vCPU 的編號,並不對應與主機 CPU。所以,這個特性不能用來約束虛擬機所處的主機 CPU 與 NUMA 節點。

大頁內存分配

$ openstack flavor set FLAVOR-NAME \
    --property hw:mem_page_size=PAGE_SIZE

有效的 PAGE_SIZE 值爲:

  • small (默認值): 使用最小的內存頁面,例如 x86 平臺的 4KB。
  • large: 虛擬機 RAM 使用大頁內存。例如 x86 平臺的 2MB 或 1G。
  • any: 取決於計算驅動程序。此狀況下,Libvirt 驅動可能會嘗試尋找內存大頁,但最終回落到小頁。其餘的驅動則可能選擇可用策略。

注意:大頁內存能夠分配給虛擬機內存,而不考慮 Guest OS 是否使用。若是 Guest OS 不使用大頁內存,則它值會識別小頁。反過來,若是 Guest OS 計劃使用大頁內存,則必定要給虛擬機分配大頁內存。不然虛擬機的性能將不及預期。 

 

5. Nova 實現 NUMA 流程

Nova 實現 NUMA 流程以下所示:

1. nova-api 對 flavor metadata 或 image property 中的 NUMA 配置信息進行解析,生成 Guest NUMA topology,保存爲 instance[‘numa_topology’]。

2. nova-scheduler 經過 NUMATopologyFilter 判斷 Host NUMA topology 是否可以知足 Guest NUMA topology,進行 ComputeNode 調度。

3. nova-compute 再次經過 instance_claim 檢查 Host NUMA 資源是否知足創建 Guest NUMA。

4. nova-compute 創建 Guest NUMA node 和 Host NUMA node 的映射關係,並根據映射關係調用 libvirt driver 生成 XML 文件。

5.  Resource Tracker 會刷新 Host NUMA 資源的使用狀況。

相關文章
相關標籤/搜索