1. 程式人生 > >10G(82599EB) 網絡卡測試優化(中斷處理)

10G(82599EB) 網絡卡測試優化(中斷處理)

這裡主要涉及的是 core 的繫結問題,有時候不是簡單的算幾個 bitmask,寫幾個數字到 smp_affinity/smf_affinity_list 裡面就完事了。

在做 affinity 的時候,有下面幾點需要注意:
1. 千萬千萬在不要在做 affinity 的時候開啟 irqbalance,否則你剛把 irq 給人肉指定好,他就自動給你給恢復成他那套了
2. 使用 iperf 或者其他的工具做 benchmark 時,需要開啟多執行緒(-P),以滿足多個 stream 的要求,否則不管你怎麼分佈,都只能壓在某一個 core 上,造成 affinity 無效的幻覺
3. 能不用 HT 儘量別用,尤其對於 affinity 來說,效果並不明顯,比較好的做法是以物理 core 的數量為參照,比如單路 6-core(開啟 HT 則 12 core),設定 queue 的數量為 6 而非 12 比較好,具體的還是需要測試

目前,要對 NIC 做 affinity,最好的方式還是 NIC 支援 RSS(Receive Side Scaling) 也就是 multiqueue RX,這樣可以很方便的將 irq(RSS) 對映到 core 上。基本上主流的千兆 NIC(bnx2, igb) 都支援,10G 的更是預設配置了,這個上篇已經說過。 各個 bitmask 的問題,不在這裡說了。

在 interrupts 檔案裡面,能看到不少的諸如 IO-APIC-level, IO-APIC-edge, PCI-MSI-X 等術語,這些其實是跟各個裝置支援的特性相關的,要看他們之間的演變過程,可以看這裡

關於 IO-APIC-level 跟 PCI-MSI-X  的

區別,是兩個完全不同的產生中斷的方式,前者(1,2)  是使用硬體實現,比如 8259A,後者則是往某個特定的 address 裡面進行寫操作實現中斷。
因此,要判斷一個裝置使用使用了 MSI/MSI-X 很簡單,只要檢視 interrputs 檔案就可以了,IO-APIC-level 非 MSI,PCI-MSI 表示試用了 MSI,這個不僅僅限於 NIC。

而 IO-APIC-fasteoi 跟 IO-APIC-edge 的區別,很好解釋。interrupts 觸發的方式不同而已,一個是邊緣(edge)觸發,一個是條件(level)觸發。

理解了上面了,可以發現,可能的中斷方式基本是下面兩種:
1. 將某個 irq 繫結到所有的 core 上
2. 將某個 irq 繫結到某幾個 core 上,第一個只是第二個的一個特例
3. 將某個 irq 繫結到指定的某個 core 上

先來看前兩種情況。其實就是 RR(round-robin) 的方式,或許能解決一些 bottleneck,但是更嚴重的問題來了,尤其對於網絡卡這種中斷很頻繁的裝置來說,會造成 cpu cache missed,造成影響是直接訪問記憶體比訪問 cache 裡面的內容慢 30x;並且對於流媒體來說,還可能造成 congestion collapse。另外,由於 APIC 的問題,可能無法實現上面的要求,比如,我想將 irq 60 繫結到 core 0 以及  core 1 上,或者想把 irq 67 分佈到所有的 core 中,將 3 寫入到 60 的 smp_affinity 不就可以了嗎?實事是做不到的,並且上面已經說明了這樣做沒有意義的原因。將 CONFIG_HITPLUG_CPU 由原先的 yes 設定成 no 可能會解決問題,不過我並沒有試過,尤其明白了上面將 irq 分佈到多個 core 的不合理之處之後更沒有必要這樣做了。

明白了上面了問題,第三點說的將 irq 繫結到一個特定的 core 上的意義就很明顯了。