天天看點

如何迅速分析出系統I/O的瓶頸在哪裡?

一、性能名額

描述I/O的性能名額有哪些呢?可以回想下檔案系統和磁盤I/O的原理,結合下面這張Linux系統的I/O棧圖複習下。

如何迅速分析出系統I/O的瓶頸在哪裡?

二、檔案系統I/O性能名額

我們先來看檔案系統的情況。

首先,最容易想到的是存儲空間的使用情況,包括容量、使用量以及剩餘空間等。我們通常也稱這些為磁盤空間的使用量,因為檔案系統的資料最終還是存儲在磁盤上。

不過要注意,這些隻是檔案系統向外展示的空間使用,而非在磁盤空間的真實用量,因為檔案系統的中繼資料也會占用磁盤空間。

而且,如果你配置了 RAID,從檔案系統看到的使用量跟實際磁盤的占用空間,也會因為 RAID 級别的不同而不一樣。比方說,配置 RAID10 後,你從檔案系統最多也隻能看到所有磁盤容量的一半。

除了資料本身的存儲空間,還有一個容易忽略的是索引節點的使用情況,它也包括容量、使用量以及剩餘量等三個名額。如果檔案系統中存儲過多的小檔案,就可能碰到索引節點容量已滿的問題。

其次,你應該想到的是緩存使用情況,包括頁緩存、目錄項緩存、索引節點緩存以及各個具體檔案系統(如 ext4、XFS 等)的緩存。這些緩存會使用速度更快的記憶體,用來臨時存儲檔案資料或者檔案系統的中繼資料,進而可以減少通路慢速磁盤的次數。

除了以上這兩點,檔案 I/O 也是很重要的性能名額,包括 IOPS(包括 r/s 和 w/s)、響應時間(延遲)以及吞吐量(B/s)等。在考察這類名額時,通常還要考慮實際檔案的讀寫情況。比如,結合檔案大小、檔案數量、I/O 類型等,綜合分析檔案 I/O 的性能。

這些性能名額非常重要,但Linux檔案系統并沒有提供,直接檢視這些名額的方法。隻能通過系統調用、動态跟蹤或者基準測試等方法,間接進行觀察、評估。

​不過,實際上,這些名額在我們考察磁盤性能時更容易見到,因為 Linux 為磁盤性能提供了更詳細的資料。

二、磁盤I/O性能名額

衡量磁盤I/O性能的四個核心名額:

  • 使用率,是指磁盤忙處理 I/O 請求的百分比。過高的使用率(比如超過 60%)通常意味着磁盤 I/O 存在性能瓶頸。
  • IOPS(Input/Output Per Second),是指每秒的 I/O 請求數。
  • 吞吐量,是指每秒的 I/O 請求大小。
  • 響應時間,是指從發出 I/O 請求到收到響應的間隔時間。

考察這些名額時,一定要注意綜合 I/O 的具體場景來分析,比如讀寫類型(順序還是随機)、讀寫比例、讀寫大小、存儲類型(有無 RAID 以及 RAID 級别、本地存儲還是網絡存儲)等。

注意:切忌把不同場景的I/O性能名額,直接進行分析對比。

除了這些名額,緩沖區(Buffer)也是要重點名額,它經常出現在記憶體和磁盤問題的分析中。

檔案系統和磁盤 I/O 的這些名額都很有用,需要熟練掌握。

如何迅速分析出系統I/O的瓶頸在哪裡?

三、性能工具

掌握檔案系統和磁盤 I/O 的性能名額後,還要知道,怎樣去擷取這些名額,也就是搞明白工具的使用問題。

第一,​​在檔案系統的原理中​​,檢視檔案系統容量的工具 df。它既可以檢視檔案系統資料的空間容量,也可以檢視索引節點的容量。至于檔案系統緩存,通過 ​

/proc/meminfo

​、​

/proc/slabinfo

​ 以及 ​

slabtop

​ 等各種來源,觀察頁緩存、目錄項緩存、索引節點緩存以及具體檔案系統的緩存情況。

第二,​​在磁盤 I/O 的原理中​​,分别用 iostat 和 pidstat 觀察了磁盤和程序的 I/O 情況。它們都是最常用的 I/O 性能分析工具。通過 iostat ,可以得到磁盤的 I/O 使用率、吞吐量、響應時間以及 IOPS 等性能名額;而通過 pidstat ,則可以觀察到程序的 I/O 吞吐量以及塊裝置 I/O 的延遲等。

第三,​​在狂打日志的案例中​​,先用 top 檢視系統的 CPU 使用情況,發現 iowait 比較高;然後,又用 iostat 發現了磁盤的 I/O 使用率瓶頸,并用 pidstat 找出了大量 I/O 的程序;最後,通過 strace 和 lsof,找出了問題程序正在讀寫的檔案,并最終鎖定性能問題的來源——原來是程序在狂打日志。

第四,​​在磁盤 I/O 延遲的單詞熱度案例中​​,同樣先用 top、iostat ,發現磁盤有 I/O 瓶頸,并用 pidstat 找出了大量 I/O 的程序。可接下來,想要照搬上次操作的我們失敗了。在随後的 strace 指令中,居然沒看到 write 系統調用。于是,換了一個思路,用新工具 filetop 和 opensnoop ,從核心中跟蹤系統調用,最終找出瓶頸的來源。

最後,​​在 MySQL 和 Redis 的案例中​​,同樣的思路,先用 top、iostat 以及 pidstat ,确定并找出 I/O 性能問題的瓶頸來源,它們正是 mysqld 和 redis-server。随後,又用 strace+lsof 找出了它們正在讀寫的檔案。

關于 MySQL 案例,根據 mysqld 正在讀寫的檔案路徑,再結合 MySQL 資料庫引擎的原理,不僅找出了資料庫和資料表的名稱,還進一步發現了慢查詢的問題,最終通過優化索引解決了性能瓶頸。

至于 Redis 案例,根據 redis-server 讀寫的檔案,以及正在進行網絡通信的 TCP Socket,再結合 Redis 的工作原理,我們發現 Redis 持久化選項配置有問題;從 TCP Socket 通信的資料中,還發現了用戶端的不合理行為。于是,修改 Redis 配置選項,并優化了用戶端使用 Redis 的方式,進而減少網絡通信次數,解決性能問題。

四、性能名額和工具的聯系

從名額和工具兩個不同次元出發,整理記憶。

  • 從 I/O 名額出發,可以更容易把性能工具同系統工作原理關聯起來,對性能問題有宏觀的認識和把握。
  • 而從性能工具出發,可以更快上手使用工具,迅速找出想觀察的性能名額。特别是在工具有限的情況下,更要充分利用好手頭的每一個工具,少量工具也要盡力挖掘出大量資訊。

第一個次元,從檔案系統和磁盤 I/O 的性能名額出發。當你想檢視某個性能名額時,要清楚知道,哪些工具可以做到。

根據不同的性能名額,對提供名額的性能工具進行分類和了解。這樣,在實際排查性能問題時,你就可以清楚知道,什麼工具可以提供你想要的名額,而不是毫無根據地挨個嘗試,撞運氣。

如何迅速分析出系統I/O的瓶頸在哪裡?

第二個次元,從工具出發。也就是當你已經安裝了某個工具後,要知道這個工具能提供哪些名額。

​這在實際環境中,特别是生産環境中也是非常重要的。因為很多情況下,你并沒有權限安裝新的工具包,隻能最大化地利用好系統已有的工具,而這就需要你對它們有足夠的了解。

​具體到每個工具的使用方法,一般都支援豐富的配置選項。這些配置選項并不用背下來。隻要知道有哪些工具,以及這些工具的基本功能是什麼就夠了。真正要用到的時候, 通過 man 指令,查它們的使用手冊就可以了。

如何迅速分析出系統I/O的瓶頸在哪裡?

五、如何迅速分析I/O的性能瓶頸

那有沒有什麼方法,可以又快又準地找出系統的 I/O 瓶頸呢?答案是肯定的。

多種性能名額間都有一定的關聯性,不要完全孤立的看待他們。想弄清楚性能名額的關聯性,就要通曉每種性能名額的工作原理。

從前面的案例梳理分析思路基本類似:

  1. 先用 iostat 發現磁盤 I/O 性能瓶頸;
  2. 再借助 pidstat ,定位出導緻瓶頸的程序;
  3. 随後分析程序的 I/O 行為;
  4. 最後,結合應用程式的原理,分析這些 I/O 的來源。

為了縮小排查範圍,通常先運作那幾個支援名額較多的工具。如:iostat、vmstat、pidstat等。然後再根據觀察到的現象,結合系統和應用程式的原理,尋找下一步的分析方向。

如何迅速分析出系統I/O的瓶頸在哪裡?

圖中列出了最常用的幾個檔案系統和磁盤 I/O 性能分析工具,以及相應的分析流程,箭頭則表示分析方向。這其中,iostat、vmstat、pidstat 是最核心的幾個性能工具,它們也提供了最重要的 I/O 性能名額。

例如,在MySQL 和 Redis 案例中,就是通過 iostat 确認磁盤出現 I/O 性能瓶頸,然後用 pidstat 找出 I/O 最大的程序,接着借助 strace 找出該程序正在讀寫的檔案,最後結合應用程式的原理,找出大量 I/O 的原因。

再如,當你用 iostat 發現磁盤有 I/O 性能瓶頸後,再用 pidstat 和 vmstat 檢查,可能會發現 I/O 來自核心線程,如 Swap 使用大量升高。這種情況下,你就得進行記憶體分析了,先找出占用大量記憶體的程序,再設法減少記憶體的使用。

繼續閱讀