Linux 效能分析工具 === ## Perf ### 安裝 & 設定 [安裝方法](https://hackmd.io/c/rJKbX1pFZ/https%3A%2F%2Fhackmd.io%2Fs%2FB11109rdg) 查看目前的 Kernel config 有沒有啟用 Perf: (下面顯示的是已安裝過的) ```shell $cat "/boot/config-`uname -r`" | grep "PERF_EVENT" CONFIG_HAVE_PERF_EVENTS=y CONFIG_PERF_EVENTS=y CONFIG_HAVE_PERF_EVENTS_NMI=y CONFIG_PERF_EVENTS_INTEL_UNCORE=y CONFIG_PERF_EVENTS_INTEL_RAPL=m CONFIG_PERF_EVENTS_INTEL_CSTATE=m # CONFIG_PERF_EVENTS_AMD_POWER is not set CONFIG_SECURITY_PERF_EVENTS_RESTRICT=y ``` 安裝工具: ```shell $sudo apt-get install linux-tools-common ``` 檢查是否安裝成功: ``` $perf top ``` :::warning 有可能因版本不同而沒安裝成功,這時只需照著它顯示缺乏的套件再一次的安裝即可。 ::: 若不是在 root 權限下執行此指令會出現以下錯誤畫面。 ![](https://i.imgur.com/rpdDV6L.png) 指示要我們修改 `/proc/sys/kernel/perf_event_paranoid` 的權限值。 * `2` : 不允許任何量測。但部份用來查看或分析已存在的紀錄的指令仍可使用,如 perf ls、perf report、perf timechart、 perf trace。 * `1` : 不允許 CPU events data。但可以使用 perf stat、perf record 並取得 Kernel profiling data。 * `0` : 不允許 raw tracepoint access。但可以使用 perf stat、perf record 並取得 CPU events data。 * `-1`: 權限全開。 另外,如果要檢測 cache miss event ,需要先取消 kernel pointer 的禁用。 ```shell $sudo sh -c " echo -1 > /proc/sys/kernel/perf_event_paranoid" $sudo sh -c " echo 0 > /proc/sys/kernel/kptr_restrict" ``` ### 效能偵測 針對我們所設計的程式 `example.c` 經由編譯後產生的 object file `example`,若要偵測其效能可輸入以下指令: ```shell $perf stat --repeat 5 \ -e cache-misses,cache-references,instructions,cycles \ ./example ``` * `--repeat <n>`或是`-r <n>` 可以重複執行 n 次該程序,並顯示每個 event 的變化區間。 * `-e` 可以指定要量測的event,若沒有指定的話預設會有10種常用的events,在這我們指定 `cache-misses,cache-references` 和 `instructions,cycles`,而類似這種成對的 event,若同時出現 perf 會很貼心幫你計算比例。 ``` Performance counter stats for './perf_stat_cache_miss' (5 runs): 4,416,226 cache-misses # 3.437 % of all cache refs ( +- 0.27% ) 128,483,262 cache-references ( +- 0.02% ) 2,123,281,496 instructions # 0.65 insns per cycle ( +- 0.02% ) 3,281,498,034 cycles ( +- 0.21% ) 1.299352302 seconds time elapsed ( +- 0.19% ) ``` ## 清除 Cache [手動清除 Linux 記憶體快取](https://medium.com/hungys-blog/clear-linux-memory-cache-manually-90bec95ea003) ### 記憶體使用情況 Linux 提供指令來顯示系統中記憶體的使用情況: ```shell $free total used free shared buff/cache available Mem: 8052900 365692 7327268 64876 359940 7388124 Swap: 11999228 0 11999228 ``` 指令預設是以`KB` 為單位,我們可以發現現在的 cache 使用了將近 360 MB。 ### 清除 Cache 若要評估 cache miss 等問題,要先清空 cache: ```shell $sudo sh -c 'echo 3 > /proc/sys/vm/drop_caches' ``` 有兩種 cache 種類可被清理。 * `2` : 清除 dentries 與 inodes * `1` : 清除 pagecache 清完後再用 `free` 查看清除後的 Cache 只剩差不多 290 MB 的記憶體使用量。 ```shell total used free shared buff/cache available Mem: 8052900 365268 7400464 59528 287168 7394000 Swap: 11999228 0 11999228 ``` :::warning 在清除 Cache 之前最好先執行 [sync](http://man.linuxde.net/sync) 指令,讓存在 buffer 中準備寫回記憶體的資料強制寫回記憶體。 :::