Linux之《荒島餘生》(二)CPU篇
溫馨提示,動圖已壓縮,流量黨放心檢視。CPU方面內容不多,我們順便學點命令。本篇是《荒島餘生》系列第二篇,垂直觀測CPU。其餘參見:
如何做一個CPU
cpu是晶片的一種,我們以漢芯為例,看一下製作七步曲。
- 提純精度11個9的矽片(99.999999999%)
- 生成晶圓
- 使用光刻機加工晶圓
- 使用刻蝕機溝槽
- 完成P型半導體制作
- 使用200號的粗砂紙抹掉原標誌
- 塗上新標誌 bingo,完工!
雖然CPU很小,但生產它的裝置可不簡單。如下圖,就是一臺重十幾噸,佔地上百平米,全世界都當寶貝的光刻機!
你我就這樣飽受科技的恩澤,有時間探討在中央處理器上發生的故事了。找到佔用CPU最高的執行緒
接下來看一個實際的例子。公司有點窮,所以機器上混合部署了多個java應用,突然有一天,CPU炸了,我們要找到是誰引起的。這個誰不是程序,而是執行緒,離真相最近的那個。
傳統做法
通常的做法是:
- 在命令列輸入
top
,然後shift+p
檢視佔用CPU最高的程序,記下程序號 - 在命令列輸入
top -Hp 程序號
,檢視佔用CPU最高的執行緒 - 使用
printf 0x%x 執行緒號
,得到其16進位制執行緒號 - 使用
jstack 程序號
得到java執行棧,然後grep
16進位制找到相應的資訊 錄個屏先
拔蘿蔔帶泥
但我想通過另外一種方式來實現這個功能(最多樣化),順便學幾個其他常用的命令。
ps -eo %cpu,pid |sort -n -k1 -r | head -n 1 | awk '{print $2}' |xargs top -b -n1 -Hp | grep COMMAND -A1 | tail -n 1 | awk '{print $1}' | xargs printf 0x%x
複製程式碼
這一行Shell的意思是,找到使用CPU最高的程序之使用CPU最高的執行緒的16進位制號。 這麼長的命令,是不是暈了?別怕,我們一點點來。通常情況下,練習熟練了命令中出現的這幾個,就能夠應對50%的常用工作了。Come on,上圖。 15423589014500.jpg
接下來,試著寫一下指令碼吧。有哪些檢視CPU的命令
top
其實從上面命令就可以瞧出來,top和ps的命令是互通的,只不過表現形式不同,我們直接拿top來說。按數字1就可以顯示每核CPU的使用情況。基本上都是些單詞的縮寫,看幾遍就忘不掉了。比如 :
us ==> user CPU time
複製程式碼
先記住這些判斷準則,我們在示例中再聊:
- 如果load超過了cpu核數,則負載過高
- 如果wa過高,可初步判斷I/O有問題
- sy,si,hi,st,任何一個超過5%,都有問題
- 程序狀態長時處於D、Z、T狀態,提高注意度
- cpu不均衡,判斷親和性和優先順序問題
vmstat
vmstat 以另一種形式來展示一些資訊。如圖:
除了關注類似top的一些指標,還有:b
置於等待佇列(等待資源、等待輸入/輸出)的核心執行緒數目。數字過大則cpu太忙。cs
如果頻繁的進行上下文切換,則考慮是否是執行緒數開的過多si
/so
顯示了交換分割槽的現狀,有時候會造成cpu問題,一併關注
sar
是目前Linux上最為全面的系統性能分析工具之一,但可能沒有預裝。在centos上使用以下命令即可安裝。
yum install sysstat -y
複製程式碼
sar主要的好處是可以看到歷史,顯示友好,可以對結果進行二次處理。sar還有圖形化工具,執行sar -A
即可獲得所有資料。
https://github.com/vlsi/ksar
複製程式碼
針對於CPU方面,我們關注:
- sar -u 預設
- sar -P ALL 每顆cpu的使用狀態資訊
- sar -q cpu佇列的長度,runq-sz>cpu count就表明有瓶頸了
- sar -w 每秒上下文交換 可以瞧見,關注的也就那幾個點而已。
##mpstat 還有
pidstat
,包括彩色的dstat
,功能都差不多, 用熟一個就ok了。
資料從何而來
那麼資料從何而來? /proc
目錄是一個虛擬目錄,儲存的是當前核心的一系列特殊檔案,你不僅能檢視一些狀態,甚至能修改一些值來改變系統的行為。
比如top的load (使用uptime命令得到同樣的結果)。讀取的就是 /proc/loadavg
檔案 而每核cpu的資訊,讀取 /proc/stat
檔案
這些命令,是對/proc目錄中一系列資訊的解析和友好的展示,這些值,Linux核心都算好了躺在那呢。
(圖片來源網路) 建立這個目錄的人真是天才!幾個例子
此文歸屬微信公眾號「小姐姐味道」,轉載註明出處。CPU過高是表象。除了系統確實負載已經到了極限,其他的,都是由其他原因引起的,比如I/O;比如裝置。這些我們放在其他章節進行討論。
GC引起的CPU過高
接著我們最開始的例子來。通過檢視jstack找到相應的16進位制程序,結果發現是GC執行緒。
"VM Thread" prio=10 tid=0x00007f06d8089000 nid=0x58c7 runnable
"GC task thread#0 (ParallelGC)" prio=10 tid=0x00007f06d801b800 nid=0x58d7 runnable
複製程式碼
這種情況,一般都是JVM記憶體不夠用了,瘋狂GC,可能是socket/執行緒忘了關閉了,也可能是大物件沒有回收。這種情況只能通過重啟來解決了,記得重啟之前,使用jmap dump一下堆疊哦。當然,你可能會得到jdk版本的問題。
st%佔比過高
st過高一般是物理CPU資源不足所致,也就是隻發生在虛擬機器上。 如果你買的虛擬機器st一直很高,那你的服務提供商可能在超賣,擠佔你的資源。不信雙11的時候看下你的虛擬機器?
網絡卡導致單cpu過高
業務方几臺kafka,cpu使用處於正常水平,才10%左右,但有一核cpu,負載特別的高,si奇高。
mpstat -I SUM -P ALL 檢視cpu使用情況,cpu0的中斷確實比較多。
20:15:18 CPU intr/s
20:15:23 all 34234.20
20:15:23 0 9566.20
20:15:23 1 0.00
複製程式碼
網絡卡需要cpu服務時,都會丟擲一箇中斷,中斷告訴cpu發生了什麼事情,cpu就要停止目前的工作來處理這個中斷。其實,預設所有的中斷處理都集中在cpu0 上,導致伺服器負載過高。cpu0 成了瓶頸,而其他cpu卻還閒著。 ➊ 解決方式1:使用CPU親和性功能,kafka略過網絡卡所使用的CPU ➋ 解決方式2: 更換網絡卡 ➌ 通常修改的方式還是有些複雜了,比如,修改/proc/irq/{seq}/smp_affinity 我們可以直接安裝irqbalance
,然後執行就可以了。
yum install irqbalance -y
service irqbalance start
複製程式碼
cpu使用率低,但負載高
cpu id%高,也就是空閒,比如90%。但 load average非常高,比如4核達到10。
分析:load average高,說明其任務已經排隊,許多工正在等待。出現此種情況,可能存在大量不可中斷的程序。
使用top或者ps可以看到程序相應的狀態。
ps aux
複製程式碼
一種情況就是有大量程序處於D的狀態,也就是不可中斷的睡眠狀態,所以很可能是硬體問題。 詳見
《Linux程序狀態(ps stat)之R、S、D、T、Z、X》
高頻問題:load
load代表的是啥
說句白話,load代表的就是你目前系統程序的排隊情況。
如圖,以單核為例,將CPU資源抽象成一條單行馬路。則會發生三種情況:- 馬路上的車只有4輛,車輛暢通無阻,load大約是0.5
- 馬路上的車有8輛,正好能首尾相接安全通過,此時load大約為1
- 馬路上的車有12輛,除了在馬路上的8輛車,還有4輛交集的等在外面,也就是超出容量了,需要排隊。此時load大約為1.5
load為1代表的是啥
針對這個問題,誤解還是比較多的。很多同學認為,load達到1,系統就到了瓶頸,這不完全正確。 load的值和cpu核數息息相關:
- 單核的cpu達到100%,load約1
- 雙核的cpu都達到100%,load約2
- 四核的cpu都達到100%,load約為4
所以,對於一個load到了10,卻是16核的機器,你的系統還遠沒有達到負載極限。
結尾
本篇實際的排查過程較少,因為cpu問題一般都伴隨著其他問題。但文中出現的這些命令可不簡單,尤其是它們豐富的引數。這些引數,執行一下man,就可以一睹芳容了。比如:
man top
複製程式碼
當然,也可以這樣~
no woman、 no love,果然是一個只有男人的世界!