BPF 編譯器集合 (BCC)
BCC 是一個用於創建高效的核心追蹤和操作程序的工具包,包括幾個有用的工具和範例。它利用了擴展的 BPF(伯克利資料包過濾器),正式名稱為 eBPF,這是 Linux 3.15 中首次添加的新功能。 BCC 使用的大部分內容都需要 Linux 4.1 及更高版本。
Ingo Molnár 將 eBPF 描述為:
此週期中更有趣的功能之一是將 eBPF 程式(由核心執行的使用者定義的沙箱字節碼)附加到 kprobes 的能力。這允許在即時核心映像上進行使用者定義的檢測,而永遠不會崩潰、掛起或對核心產生負面影響。
BCC 使 BPF 程式更易於編寫,具有 C 語言的核心檢測(並包括圍繞 LLVM 的 C 包裝器)以及 Python 和 lua 的前端。它適用於許多任務,包括效能分析和網路流量控制。
螢幕截圖
此範例追蹤磁碟 I/O 核心函數,並填入 I/O 大小的核心內 2 次冪直方圖。為了提高效率,僅將直方圖摘要傳回給使用者層級。
# ./bitehist.py
Tracing... Hit Ctrl-C to end.
^C
kbytes : count distribution
0 - > 1 : 3 | |
2 - > 3 : 0 | |
4 - > 7 : 211 | ********** |
8 - > 15 : 0 | |
16 - > 31 : 0 | |
32 - > 63 : 0 | |
64 - > 127 : 1 | |
128 - > 255 : 800 | ************************************** |
上面的輸出顯示了雙峰分佈,其中 800 I/O 的最大模式大小在 128 到 255 KB 之間。
請參閱來源:bitehist.py。其追蹤的內容、儲存的內容以及資料的呈現方式都可以完全自訂。這僅顯示了許多可能的功能中的某些功能。
安裝中
請參閱 INSTALL.md 以了解您平台上的安裝步驟。
常問問題
請參閱 FAQ.txt 以了解最常見的故障排除問題。
參考指南
有關 bcc 和 bcc/BPF API 的參考指南,請參閱 docs/reference_guide.md。
內容
其中一些是包含 C 和 Python 的單一文件,其他有一對 .c 和 .py 文件,還有一些是文件目錄。
追蹤
範例
- example/tracing/bitehist.py:區塊 I/O 大小直方圖。例子。
- example/tracing/disksnoop.py:追蹤區塊裝置 I/O 延遲。例子。
- example/hello_world.py:印出“Hello, World!”對於新流程。
- example/tracing/mysqld_query.py:使用 USDT 探針追蹤 MySQL 伺服器查詢。例子。
- example/tracing/nodejs_http_server.py:使用 USDT 探針追蹤 Node.js HTTP 伺服器請求。例子。
- example/tracing/stacksnoop:追蹤核心函數並列印所有核心堆疊追蹤。例子。
- tools/statsnoop:追蹤 stat() 系統呼叫。例子。
- example/tracing/task_switch.py:使用起始和終止 PID 來計算任務切換。
- example/tracing/tcpv4connect.py:追蹤 TCP IPv4 活動連線。例子。
- example/tracing/trace_fields.py:列印追蹤事件欄位的簡單範例。
- example/tracing/undump.py:轉儲 UNIX 套接字封包。範例
- example/tracing/urandomread.py:核心追蹤點範例,追蹤 random:urandom_read。例子。
- example/tracing/vfsreadlat.py Examples/tracing/vfsreadlat.c:VFS 讀取延遲分佈。例子。
- example/tracing/kvm_hypercall.py:KVM 進入、退出和超級呼叫範例的條件靜態核心追蹤點。
工具
- tools/argdist:將函數參數值顯示為直方圖或頻率計數。例子。
- tools/bashreadline:在系統範圍內列印輸入的 bash 指令。例子。
- tools/bpflist:顯示具有活動 BPF 程式和對應的進程。例子。
- 工具/能力:追蹤安全能力檢查。例子。
- tools/compactsnoop:使用 PID 和延遲追蹤緊湊區域事件。例子。
- Tools/Criticalstat:追蹤並報告內核中的長原子關鍵部分。範例
- 工具/死鎖:偵測正在運作的進程上潛在的死鎖。例子。
- tools/drsnoop:使用 PID 和延遲追蹤直接回收事件。例子。
- tools/funccount:計算核心函數呼叫次數。例子。
- 工具/注入:使用呼叫鍊和謂詞範例進行有針對性的錯誤注入。
- tools/klockstat:追蹤核心互斥鎖定事件並顯示鎖定統計資料。例子。
- tools/opensnoop:追蹤 open() 系統呼叫。例子。
- tools/readahead:顯示預讀快取範例的效能。
- tools/reset-trace:重置追蹤狀態。僅維護工具。例子。
- tools/stackcount:計算核心函數呼叫及其堆疊追蹤。例子。
- 工具/syncsnoop:追蹤sync()系統呼叫。例子。
- tools/threadsnoop:列出新線程創建。例子。
- tools/tplist:顯示核心追蹤點或 USDT 探針及其格式。例子。
- 工具/追蹤:使用篩選器追蹤任意函數。例子。
- tools/ttysnoop:觀看 tty 或 pts 設備的即時輸出。例子。
- tools/ucalls:總結高階語言中的方法呼叫或 Linux 系統呼叫。例子。
- tools/uflow:用高階語言列印方法流程圖。例子。
- tools/ugc:追蹤高階語言中的垃圾收集事件。例子。
- tools/uobjnew:按物件類型和分配的位元組數匯總物件分配事件。例子。
- tools/ustat:以高階語言收集事件,例如 GC、執行緒建立、物件分配、異常等。例子。
- tools/uthreads:追蹤 Java 和原始 pthread 中的執行緒建立事件。例子。
記憶體和處理工具
- tools/execsnoop:透過 exec() 系統呼叫追蹤新進程。例子。
- tools/exitsnoop:追蹤進程終止(退出和致命訊號)。例子。
- tools/killsnoop:由kill()系統呼叫發出的追蹤訊號。例子。
- tools/kvmexit:顯示每個虛擬機器退出的 exit_reason 及其統計資料。例子。
- tools/memleak:顯示未完成的記憶體分配以查找記憶體洩漏。例子。
- tools/oomkill:追蹤記憶體不足 (OOM) 殺手。例子。
- tools/pidpersec:計算新進程(透過 fork)。例子。
- tools/rdmaucma:追蹤 RDMA 使用者空間連線管理員存取事件。例子。
- tools/shmsnoop:追蹤 System V 共享記憶體系統呼叫。例子。
- tools/slabratetop:內核SLAB/SLUB記憶體快取分配率top。例子。
性能和時間工具
- tools/dbslower:追蹤慢於閾值的 MySQL/PostgreSQL 查詢。例子。
- tools/dbstat:將 MySQL/PostgreSQL 查詢延遲總結為直方圖。例子。
- tools/funcinterval:作為直方圖的同一函數之間的時間間隔。例子。
- 工具/功能:時間函數並顯示其延遲分佈。例子。
- tools/funcslower:追蹤緩慢的核心或使用者函數呼叫。例子。
- tools/hardirqs:測量硬體 IRQ(硬中斷)事件時間。例子。
- tools/mysqld_qslower:追蹤慢於閾值的 MySQL 伺服器查詢。例子。
- tools/ppchcalls:總結 ppc hcall 計數和延遲。例子。
- 工具/軟中斷:測量軟IRQ(軟中斷)事件時間。例子。
- tools/syscount:總結系統呼叫計數和延遲。例子。
CPU 和調度程序工具
- tools/cpudist:將每個任務的 CPU 開啟和關閉時間總結為直方圖。範例
- tools/cpuunclaimed:CPU 運行佇列樣本並計算無人認領的空閒 CPU。範例
- tools/llcstat:依行程匯總 CPU 快取引用和未命中情況。例子。
- tools/offcputime:透過核心堆疊追蹤總結 CPU 外時間。例子。
- tools/offwaketime:依核心脫離 CPU 堆疊和喚醒堆疊匯總阻塞時間。例子。
- 工具/設定檔:透過按時間間隔採樣堆疊追蹤來分析 CPU 使用情況。例子。
- tools/runqlat:以直方圖形式運行佇列(調度程序)延遲。例子。
- tools/runqlen:以直方圖形式運行佇列長度。例子。
- tools/runqslower:追蹤長進程調度延遲。例子。
- tools/wakeuptime:透過喚醒器核心堆疊總結睡眠到喚醒時間。例子。
- tools/wqlat:總結工作隊列上的工作等待延遲。例子。
網路和套接字工具
- tools/gethostlatency:顯示 getaddrinfo/gethostbyname[2] 呼叫的延遲。例子。
- tools/bindsnoop:追蹤 IPv4 和 IPv6 bind() 系統呼叫 (bind())。例子。
- tools/netqtoptools/netqtop.c:追蹤並顯示 NIC 佇列上的資料包分佈。例子。
- tools/sofdsnoop:追蹤透過 unix 套接字傳遞的 FD。例子。
- tools/solisten:追蹤 TCP 套接字偵聽。例子。
- tools/sslsniff:嗅探 OpenSSL 寫入和讀取的資料。例子。
- tools/tcpaccept:追蹤 TCP 被動連線 (accept())。例子。
- tools/tcpconnect:追蹤 TCP 活動連線 (connect())。例子。
- tools/tcpconnlat:追蹤 TCP 活動連線延遲 (connect())。例子。
- tools/tcpdrop:追蹤基於核心的 TCP 封包遺失的詳細資訊。例子。
- tools/tcplife:追蹤 TCP 會話並總結生命週期。例子。
- tools/tcpretrans:追蹤 TCP 重傳和 TLP。例子。
- tools/tcprtt:追蹤 TCP 往返時間。例子。
- tools/tcpstates:追蹤 TCP 會話狀態隨持續時間的變化。例子。
- tools/tcpsubnet:匯總並聚合按子網路發送的 TCP。例子。
- tools/tcpsynbl:顯示 TCP SYN 積壓。例子。
- tools/tcptop:按主機匯總 TCP 傳送/接收吞吐量。 TCP 的頂部。例子。
- 工具/tcptracer:追蹤 TCP 建立的連線(connect()、accept()、close())。例子。
- tools/tcpcong:追蹤 TCP 套接字擁塞控制狀態持續時間。例子。
儲存和檔案系統工具
- tools/bitesize:顯示每個進程 I/O 大小直方圖。例子。
- tools/cachestat:追蹤頁面快取命中/未命中率。例子。
- tools/cachetop:按進程追蹤頁面快取命中/未命中率。例子。
- tools/dcsnoop:追蹤目錄條目快取 (dcache) 查找。例子。
- tools/dcstat:目錄條目快取 (dcache) 統計資料。例子。
- 工具/生物延遲:將區塊裝置 I/O 延遲總結為直方圖。例子。
- tools/biotop:磁碟頂部:按進程匯總區塊設備 I/O。例子。
- 工具/生物模式:辨識隨機/順序磁碟存取模式。例子。
- tools/biosnoop:使用 PID 和延遲追蹤區塊設備 I/O。例子。
- tools/dirtop:依目錄進行檔案讀寫。目錄頂部。例子。
- tools/filelife:追蹤短期文件的生命週期。例子。
- 工具/檔案消失:追蹤檔案消失的原因(刪除或重新命名)。例子。
- tools/fileslower:追蹤緩慢的同步檔案讀取和寫入。例子。
- tools/filetop:依檔案名稱和進程讀取和寫入檔案。頂部為文件。例子。
- tools/mdflush:追蹤 md 刷新事件。例子。
- tools/mountsnoop:追蹤系統範圍內的掛載和卸載系統呼叫。例子。
- tools/virtiostat:顯示 VIRTIO 設備 IO 統計資料。例子。
檔案系統工具
- tools/btrfsdist:將 btrfs 操作延遲分佈總結為直方圖。例子。
- tools/btrfsslower:追蹤緩慢的 btrfs 操作。例子。
- tools/ext4dist:將 ext4 操作延遲分佈總結為直方圖。例子。
- tools/ext4slower:追蹤緩慢的 ext4 操作。例子。
- tools/nfsslower:追蹤緩慢的 NFS 操作。例子。
- tools/nfsdist:將 NFS 操作延遲分佈總結為直方圖。例子。
- tools/vfscount:統計 VFS 呼叫。例子。
- tools/vfsstat:統計一些 VFS 調用,並帶有列輸出。例子。
- tools/xfsdist:將 XFS 操作延遲分佈總結為直方圖。例子。
- tools/xfsslower:追蹤緩慢的 XFS 操作。例子。
- tools/zfsdist:將 ZFS 操作延遲分佈總結為直方圖。例子。
- tools/zfsslower:追蹤緩慢的 ZFS 操作。例子。
聯網
範例:
- example/networking/distributed_bridge/:分散式網橋範例。
- example/networking/http_filter/:簡單的 HTTP 過濾器範例。
- example/networking/simple_tc.py:簡單的流量控制範例。
- example/networking/simulation.py:模擬助手。
- example/networking/neighbor_sharing/tc_neighbor_sharing.py Examples/networking/neighbor_sharing/tc_neighbor_sharing.c:每 IP 分類和速率限制。
- example/networking/tunnel_monitor/:有效監控流量。
- example/networking/vlan_learning/vlan_learning.py Examples/vlan_learning.c:將乙太網路流量解複用到工作執行緒 veth+ 命名空間。
BPF自省
有助於內省 BPF 程序的工具。
- introspection/bps.c:列出載入到核心中的所有 BPF 程式。 'ps' 用於 BPF 程式。例子。
動機
BPF 保證載入到核心中的程式不會崩潰,也不會永遠運行,但 BPF 的通用性足以執行許多任意類型的計算。目前,可以用 C 編寫一個程序,將其編譯為有效的 BPF 程序,但編寫一個將編譯為無效 BPF 的 C 程序要容易得多(C 就是這樣)。用戶直到嘗試運行程式才知道它是否有效。
對於 BPF 特定的前端,人們應該能夠用一種語言編寫並從編譯器接收有關 BPF 後端有效性的回饋。該工具包旨在提供一個只能創建有效的 BPF 程式的前端,同時仍充分利用其靈活性。
此外,目前與 BPF 的整合工作流程混亂,有時涉及直接在 Linux 核心原始碼樹中進行編譯。該工具鏈旨在最大限度地減少開發人員編譯 BPF 所花費的時間,並將重點放在可以編寫的應用程式以及可以使用 BPF 解決的問題上。
該工具包的功能包括:
- 共用程式庫中的端對端 BPF 工作流程
- 用於 BPF 後端的改進的 C 語言
- 與 llvm-bpf 後端整合以實現 JIT
- JIT 程式的動態(卸載)載入
- 支援 BPF 核心掛鉤:套接字過濾器、tc 分類器、tc 操作和 kprobes
- Python 的綁定
- 套接字過濾器、tc 分類器和 kprobes 的範例
- 用於追蹤正在運行的系統的獨立工具
將來,可能會支援 python 之外的更多綁定。請隨意添加對您選擇的語言的支援並發送拉取請求!
教學
- docs/tutorial.md:使用 bcc 工具解決效能、故障排除和網路問題。
- docs/tutorial_bcc_python_developer.md:使用 Python 介面開發新的 bcc 程式。
聯網
在 2015 年紅帽高峰會上,BCC 作為 BPF 會議的一部分進行了介紹。模擬多主機vxlan環境,並使用BPF程式監控其中一個實體介面。 BPF 程式對經過介面的內部和外部 IP 位址進行統計,使用者空間元件將這些統計資料轉換成顯示多粒徑流量分佈的圖表。請參閱此處的代碼。
貢獻
已經準備好提交一些程式碼了嗎?這裡有一些資源可供您加入 IOVisor 社群的討論並了解您想要做什麼。
- 電子郵件清單: https://lists.iovisor.org/mailman/listinfo/iovisor-dev
- IRC: #iovisor,位於 irc.oftc.net
- BCC 問題追蹤器: Github 問題
- 貢獻腳本指南: CONTRIBUTING-SCRIPTS.md
外部連結
想要了解更多關於 BCC 及其使用方式的資訊?您可以在 LINKS.md 中找到網路上其他 BCC 內容的連結。