化 Intel? Xeon? 上的 PyTorch CPU 推理性能)
示例工程【免費下載鏈接】tutorialsPyTorch tutorials.項目地址https://gitcode.com/gh_mirrors/tuto/tutorials點擊查看免費下載本篇指南基于 PyTorch tutorials 倉庫中的 recipes_source/xeon_run_cpu.rst 編寫系統(tǒng)講解 Intel? Xeon? 可擴展處理器上影響 PyTorch 推理性能的關(guān)鍵配置并深入介紹倉庫提供的torch.backends.xeon.run_cpu啟動腳本它通過線程親和性、Intel? OpenMP 預(yù)加載、NUMA 綁定與 TCMalloc/JeMalloc 內(nèi)存分配器預(yù)加載等機制幫助用戶在單實例與多實例場景下獲得接近峰值的 CPU 推理性能。讀完本文你將掌握lscpu/numactl/taskset的用法、OpenMP 與內(nèi)存分配器的選型安裝以及run_cpu腳本全部參數(shù)的含義與典型命令行組合。優(yōu)化概覽為什么需要 run_cpu 腳本在 Intel? Xeon? 可擴展處理器上執(zhí)行 PyTorch 推理時有多項配置會影響最終性能其中最主要的是兩類線程管理配置線程親和性thread affinity并預(yù)加載 Intel? OpenMP 運行時庫libiomp內(nèi)存管理配置 NUMA 綁定NUMA binding并預(yù)加載優(yōu)化內(nèi)存分配庫TCMalloc、JeMalloc。torch.backends.xeon.run_cpu腳本將上述兩類優(yōu)化封裝為統(tǒng)一入口同時還提供計算資源分配的調(diào)優(yōu)參數(shù)覆蓋單實例與多實例兩種場景幫助用戶針對具體負載試出資源利用的最優(yōu)組合。該腳本的用法通過python -m torch.backends.xeon.run_cpu調(diào)用屬于 PyTorch 標準安裝自帶的torch.backends后端工具。理解 NUMA多插槽服務(wù)器的內(nèi)存訪問模型隨著單插槽內(nèi) CPU 核數(shù)不斷增加多個核心共享內(nèi)存控制器會導(dǎo)致內(nèi)存訪問競爭程序可能因內(nèi)存總線繁忙而停滯。為此引入了非一致性內(nèi)存訪問Non-Uniform Memory AccessNUMA與一致性內(nèi)存訪問UMA所有內(nèi)存對所有核心訪問速度相同不同NUMA 將內(nèi)存劃分為多個組每組內(nèi)存直接掛接在某個插槽的集成內(nèi)存控制器上成為該插槽的本地內(nèi)存核心訪問本地內(nèi)存遠快于訪問遠端內(nèi)存因此避免跨插槽計算、將內(nèi)存訪問盡量限定在本地是提升多路服務(wù)器性能的關(guān)鍵。在 Linux 上可通過lscpu命令查看機器上的核心數(shù)、插槽數(shù)以及 NUMA 分布。以下是在一臺搭載 Intel? Xeon? CPU Max 9480 的機器上執(zhí)行l(wèi)scpu的輸出示例$ lscpu ... CPU(s): 224 On-line CPU(s) list: 0-223 Vendor ID: GenuineIntel Model name: Intel (R) Xeon (R) CPU Max 9480 CPU family: 6 Model: 143 Thread(s) per core: 2 Core(s) per socket: 56 Socket(s): 2 ... NUMA: NUMA node(s): 2 NUMA node0 CPU(s): 0-55,112-167 NUMA node1 CPU(s): 56-111,168-223 ...對照該輸出可以得出三條關(guān)鍵結(jié)論機器檢測到 2 個插槽每個插槽含 56 個物理核開啟超線程Hyper-Threading后每個物理核可處理 2 個線程即每個插槽有 56 個邏輯核整機共 224 個 CPU 核心物理核通常排在邏輯核之前核心 0-55 是第一個 NUMA 節(jié)點的物理核核心 56-111 是第二個 NUMA 節(jié)點的物理核邏輯核隨后編號核心 112-167 對應(yīng)第一個 NUMA 節(jié)點的邏輯核核心 168-223 對應(yīng)第二個 NUMA 節(jié)點的邏輯核。實踐建議運行計算密集的 PyTorch 程序時通常應(yīng)避免使用邏輯核超線程核以獲得更好的性能。使用 numactl 控制 NUMA 策略Linux 提供numactl工具允許用戶為進程或共享內(nèi)存設(shè)置 NUMA 策略即以指定的 NUMA 調(diào)度或內(nèi)存放置策略運行進程。同一插槽內(nèi)的核心共享高速緩存因此避免跨插槽計算、將內(nèi)存訪問限定在本地是性能優(yōu)化的基本原則。numactl在較新的 Linux 發(fā)行版中通常已預(yù)裝若缺失可手動安裝Ubuntu$ apt-get install numactlCentOS$ yum install numactl使用 taskset 設(shè)置 CPU 親和性Linux 的taskset是另一款實用工具可設(shè)置或查詢運行中進程的 CPU 親和性。大多數(shù) Linux 發(fā)行版已預(yù)裝若缺失Ubuntu$ apt-get install util-linuxCentOS$ yum install util-linux使用 Intel? OpenMP 運行時庫OpenMP 是一種多線程并行實現(xiàn)主線程一系列連續(xù)執(zhí)行的指令派生指定數(shù)量的子線程系統(tǒng)將任務(wù)劃分給這些線程并發(fā)執(zhí)行運行時環(huán)境負責(zé)把線程分配到不同處理器。用戶可通過環(huán)境變量控制 OpenMP 行為以適應(yīng)具體負載這些設(shè)置由 OMP 庫讀取并執(zhí)行。默認情況下PyTorch 使用 GNU OpenMP 庫GNU libgomp進行并行計算。在 Intel? 平臺上Intel? OpenMP 運行時庫libiomp提供 OpenMP API 規(guī)范支持相比 libgomp 通常能帶來更多性能收益。安裝方式$ pip install intel-openmp或$ conda install mkl選擇優(yōu)化的內(nèi)存分配器內(nèi)存分配器同樣顯著影響性能更高效的內(nèi)存使用能減少不必要的分配/銷毀開銷從而加快執(zhí)行。實踐經(jīng)驗表明對于深度學(xué)習(xí)負載TCMalloc或JeMalloc通過盡可能復(fù)用內(nèi)存通常比默認的malloc操作獲得更好的性能。安裝 TCMallocUbuntu$ apt-get install google-perftoolsCentOS$ yum install gperftoolsconda 環(huán)境$ conda install conda-forge::gperftools安裝 JeMallocUbuntu$ apt-get install libjemalloc2CentOS$ yum install jemallocconda 環(huán)境$ conda install conda-forge::jemallocQuick Startrun_cpu 腳本的典型用法以下四組命令覆蓋最常見的啟動場景程序參數(shù)通過program.py [program_args]透傳1. 單實例、單核推理僅使用 Core #0$ python -m torch.backends.xeon.run_cpu --ninstances 1 --ncores-per-instance 1 program.py [program_args]2. 單實例、綁定單個 CPU 節(jié)點NUMA socket$ python -m torch.backends.xeon.run_cpu --node-id 0 program.py [program_args]3. 多實例推理在 112 核 CPU 上運行 8 個實例每個實例 14 核$ python -m torch.backends.xeon.run_cpu --ninstances 8 --ncores-per-instance 14 program.py [program_args]4. 吞吐模式每個 CPU 節(jié)點上的全部核心組成一個實例$ python -m torch.backends.xeon.run_cpu --throughput-mode program.py [program_args]關(guān)于“實例”的說明此處的 “instance” 并非指云主機實例。該腳本以單個進程運行進程內(nèi)部基于多個線程派生出多個 “instances”在此語境下 “instance” 相當于一組線程的集合。run_cpu 腳本參數(shù)詳解可通過如下命令查看完整參數(shù)列表與用法說明$ python -m torch.backends.xeon.run_cpu –h usage: run_cpu.py [-h] [--multi-instance] [-m] [--no-python] [--enable-tcmalloc] [--enable-jemalloc] [--use-default-allocator] [--disable-iomp] [--ncores-per-instance] [--ninstances] [--skip-cross-node-cores] [--rank] [--latency-mode] [--throughput-mode] [--node-id] [--use-logical-core] [--disable-numactl] [--disable-taskset] [--core-list] [--log-path] [--log-file-prefix] program [program_args]位置參數(shù)positional argumentsknob說明program待啟動程序/腳本的完整路徑program_args傳遞給待啟動程序/腳本的輸入?yún)?shù)通用選項knob類型默認值說明-h,--help--顯示幫助信息并退出-m,--module--將每個進程解釋為以 “python -m” 方式執(zhí)行的 Python 模塊--no-pythonboolFalse不在程序前拼接 “python”直接執(zhí)行適用于非 Python 腳本--log-pathstr指定日志文件目錄默認空串表示不寫日志文件--log-file-prefixstrrun日志文件名的前綴啟用或禁用優(yōu)化的選項knob類型默認值說明--enable-tcmallocboolFalse啟用TCMalloc內(nèi)存分配器--enable-jemallocboolFalse啟用JeMalloc內(nèi)存分配器--use-default-allocatorboolFalse使用默認內(nèi)存分配器既不使用TCMalloc也不使用JeMalloc--disable-iompboolFalse默認在已安裝的情況下使用 Intel? OpenMP 庫設(shè)置該標志則禁用內(nèi)存分配器的自動選擇邏輯內(nèi)存分配器會影響性能。若用戶未顯式指定期望的分配器run_cpu腳本會按TCMalloc JeMalloc PyTorch 默認分配器的順序探測系統(tǒng)中已安裝的分配器并采用第一個匹配到的。用戶可在安裝環(huán)節(jié)按此優(yōu)先級規(guī)劃或直接通過--enable-tcmalloc/--enable-jemalloc/--use-default-allocator顯式指定。實例數(shù)量與計算資源分配的選項knob類型默認值說明--ninstancesint0實例數(shù)量--ncores-per-instanceint0每個實例使用的核心數(shù)--node-idint-1多實例時使用的節(jié)點 ID默認使用全部節(jié)點--core-liststr指定核心列表格式為core_id, core_id, ....或核心范圍core_id-core_id默認使用全部核心--use-logical-coreboolFalse默認只使用物理核設(shè)置該標志啟用邏輯核--skip-cross-node-coresboolFalse防止工作負載運行在跨 NUMA 節(jié)點的核心上--rankint-1指定實例索引為該 rank 分配ncores_per_instance否則按順序依次分配給各實例--multi-instanceboolFalse在多插槽 CPU 服務(wù)器上快速啟動多實例負載的快捷開關(guān)--latency-modeboolFalse延遲模式快捷開關(guān)使用全部物理核每個實例 4 核--throughput-modeboolFalse吞吐模式快捷開關(guān)使用全部物理核每個實例綁定 1 個 NUMA 節(jié)點--disable-numactlboolFalse默認使用numactl命令控制 NUMA 訪問設(shè)置該標志則禁用--disable-tasksetboolFalse禁用taskset命令的使用腳本設(shè)置的環(huán)境變量run_cpu腳本會為被啟動的進程設(shè)置以下環(huán)境變量環(huán)境變量取值LD_PRELOAD依據(jù)設(shè)置的選項可能將lib/libiomp5.so、lib/libjemalloc.so、lib/libtcmalloc.so追加到LD_PRELOADKMP_AFFINITY若預(yù)加載了 libiomp5.soKMP_AFFINITY會被設(shè)置為granularityfine,compact,1,0KMP_BLOCKTIME若預(yù)加載了 libiomp5.soKMP_BLOCKTIME被設(shè)置為1OMP_NUM_THREADS取值為ncores_per_instanceMALLOC_CONF若預(yù)加載了 libjemalloc.soMALLOC_CONF被設(shè)置為oversize_threshold:1,background_thread:true,metadata_thp:auto環(huán)境變量優(yōu)先級腳本會尊重用戶預(yù)先設(shè)置的環(huán)境變量。例如如果在運行腳本前已設(shè)置了上述環(huán)境變量腳本不會覆蓋這些值。因此可通過預(yù)先 export 自定義KMP_AFFINITY、OMP_NUM_THREADS等變量來覆蓋腳本默認行為。結(jié)合倉庫的縱深理解參數(shù)與底層工具的對應(yīng)關(guān)系run_cpu腳本對numactl與taskset的啟用/禁用開關(guān)直接對應(yīng)倉庫中 recipes_source/xeon_run_cpu.rst 所介紹的 NUMA 綁定與線程親和性原理--disable-numactl關(guān)閉 NUMA 策略控制相當于不再執(zhí)行numactl --cpunodebind/--membind類綁定--disable-taskset則關(guān)閉 CPU 親和性設(shè)置。腳本通過LD_PRELOAD機制注入libiomp5.so、libjemalloc.so、libtcmalloc.so與 recipes_source/recipes/tuning_guide.py 中 “CPU specific optimizations” 一節(jié)描述的手工優(yōu)化手段export LD_PRELOADpath/libiomp5.so:$LD_PRELOAD、KMP_AFFINITYgranularityfine,compact,1,0、KMP_BLOCKTIME1等完全一致——腳本的價值在于把這一系列手工設(shè)置自動化、參數(shù)化避免用戶逐一 export。與手動優(yōu)化命令的對照如果你不想使用腳本倉庫的調(diào)優(yōu)指南還給出了等價的底層命令可作為理解腳本行為的參考NUMA 綁定將腳本綁定到第 N 個 NUMA 節(jié)點避免跨插槽內(nèi)存訪問$ numactl --cpunodebindN --membindN python pytorch_scriptIntel OpenMP 庫預(yù)加載$ export LD_PRELOADpath/libiomp5.so:$LD_PRELOAD $ export KMP_AFFINITYgranularityfine,compact,1,0 $ export KMP_BLOCKTIME1內(nèi)存分配器預(yù)加載$ export LD_PRELOADjemalloc.so/tcmalloc.so:$LD_PRELOADOMP_NUM_THREADS決定 OpenMP 計算使用的線程數(shù)是影響并行計算性能最直接的開關(guān)KMP_AFFINITY將 OpenMP 線程綁定到物理處理單元KMP_BLOCKTIME則設(shè)置線程在完成并行區(qū)域后、進入休眠前等待的毫秒數(shù)設(shè)置為 1 或 0 通常能獲得良好性能。這些語義同樣被run_cpu腳本繼承并通過--ncores-per-instance、--use-logical-core等參數(shù)以更易用的方式暴露。在項目中的定位該教程在倉庫的 recipes_index.rst 中被歸類為 “Performance”Model-Optimization 標簽條目卡片描述為 “How to use run_cpu script for optimal runtime configurations on Intel? Xeon CPUs”與同類的 Performance Tuning Guide 共同構(gòu)成 CPU 性能優(yōu)化主題。建議將本文與 tuning guide 的 CPU 章節(jié)NUMA 控制、OpenMP 利用、內(nèi)存分配器切換配合閱讀前者提供自動化腳本后者提供底層原理與手工替代方案。結(jié)論本文圍繞 Intel? Xeon? 可擴展處理器上的 PyTorch 推理優(yōu)化系統(tǒng)梳理了三類關(guān)鍵技術(shù)NUMA 訪問控制通過numactl/taskset將計算與內(nèi)存訪問限定在本地節(jié)點避免跨插槽開銷Intel? OpenMP 運行時庫以libiomp5.so替代默認 GNU libgomp配合KMP_AFFINITY、KMP_BLOCKTIME獲得更好的多線程并行效果優(yōu)化內(nèi)存分配器TCMalloc/JeMalloc通過內(nèi)存復(fù)用減少分配開銷。torch.backends.xeon.run_cpu腳本將上述優(yōu)化自動化自動配置線程親和性、預(yù)加載 Intel OpenMP、綁定 NUMA、按優(yōu)先級探測內(nèi)存分配器并以--ninstances、--ncores-per-instance、--node-id、--core-list、--latency-mode、--throughput-mode等參數(shù)覆蓋單實例與多實例場景幫助用戶針對具體負載快速嘗試最優(yōu)的資源分配組合。掌握該腳本的參數(shù)語義與底層機制后即可在 Intel? Xeon? 平臺上顯著提升 PyTorch 應(yīng)用的推理效率。贊分享示例工程【免費下載鏈接】tutorialsPyTorch tutorials.項目地址https://gitcode.com/gh_mirrors/tuto/tutorials點擊查看免費下載相關(guān)推薦Intel? Extension for PyTorch* v2.6.0cpu為英特爾?至強?6平臺帶來全面AI優(yōu)化Intel? Extension for PyTorch v2.6.0cpu為英特爾?至強?6平臺帶來全面AI優(yōu)化 Intel? Extension forIntel? Deep Learning Streamer (Intel? DL Streamer) 使用教程Intel? Deep Learning Streamer Intel? DL Streamer 使用教程 1. 項目介紹 Intel? Deep Learni音視頻計算機視覺深度學(xué)習(xí)【親測免費】 Intel? Performance Counter Monitor (Intel? PCM) 使用教程Intel? Performance Counter Monitor Intel? PCM 使用教程 1. 項目介紹 Intel? Performance Co運維上一篇OPA 錯誤排查指南Rego 解析、編譯與求值三階段錯誤分類與修復(fù)實戰(zhàn)下一篇明日方舟自動化工具完整指南讓 arknights-mower 承包你的長草日常創(chuàng)作聲明:本文部分內(nèi)容由AI輔助生成(AIGC),僅供參考