在平時的運維工作中,當一臺伺服器的效能出現問題時,通常會去看當前的CPU使用情況,尤其是看下CPU的負載情況(load average)。對一般的系統來說,根據cpu數量去判斷。比如有2顆cup的機器。如果平均負載始終在1.2以下,那麼基本不會出現cpu不夠用的情況。也就是Load平均要小於Cpu的數量。
對於cpu負載的理解,首先需要搞清楚下面幾個問題: 1)系統load高不一定是效能有問題。 因為Load高也許是因為在進行cpu密集型的計算 2)系統Load高不一定是CPU能力問題或數量不夠。 因為Load高只是代表需要執行的佇列累計過多了。但佇列中的任務實際可能是耗Cpu的,也可能是耗i/0奶子其他因素的。 3)系統長期Load高,解決辦法不是一味地首先增加CPU 因為Load只是表象,不是實質。增加CPU個別情況下會臨時看到Load下降,但治標不治本。 4)在Load average 高的情況下需要鑑別系統瓶頸到底是CPU不足,還是io不夠快造成或是記憶體不足造成的。 =============================================================================================================== 要想獲得伺服器的CPU負載情況,有下面幾種命令: 1)w命令 [root@localhost ~]# w 12:12:41 up 167 days, 20:46, 2 users, load average: 0.00, 0.01, 0.05 USER TTY FROM LOGIN@ IDLE JCPU PCPU WHAT root pts/0 192.168.1.5 10:01 1.00s 0.11s 0.00s w root pts/2 192.168.1.5 10:19 1:47m 0.04s 0.04s -bash 2)uptime命令(一般首先會根據最後那個15分鐘的load負載為準) [root@localhost ~]# uptime 12:12:55 up 167 days, 20:46, 2 users, load average: 0.00, 0.01, 0.05 3)top命令 [root@localhost ~]# top top - 12:13:22 up 167 days, 20:47, 2 users, load average: 0.00, 0.01, 0.05 Tasks: 272 total, 1 running, 271 sleeping, 0 stopped, 0 zombie %Cpu(s): 0.0 us, 0.1 sy, 0.0 ni, 99.9 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st KiB Mem : 65759080 total, 58842616 free, 547908 used, 6368556 buff/cache KiB Swap: 2097148 total, 2097148 free, 0 used. 64264884 avail Mem ................ 對上面第三行的解釋: us(user cpu time):使用者態使用的cpu時間比。該值較高時,說明使用者程式消耗的 CPU 時間比較多,比如,如果該值長期超過 50%,則需要對程式演算法或程式碼等進行優化。 sy(system cpu time):系統態使用的cpu時間比。 ni(user nice cpu time):用做nice加權的程式分配的使用者態cpu時間比 id(idle cpu time):空閒的cpu時間比。如果該值持續為0,同時sy是us的兩倍,則通常說明系統則面臨著 CPU 資源的短缺。 wa(io wait cpu time):cpu等待磁碟寫入完成時間。該值較高時,說明IO等待比較嚴重,這可能磁碟大量作隨機訪問造成的,也可能是磁碟效能出現了瓶頸。 hi(hardware irq):硬中斷消耗時間 si(software irq):軟中斷消耗時間 st(steal time):虛擬機器偷取時間 以上解釋的這些引數的值加起來是100%。 4)vmstat [root@localhost ~]# vmstat procs -----------memory---------------------swap-------io---------system--------cpu----- r b swpd free buff cache si so bi bo in cs us sy id wa st 3 0 0 1639792 724280 4854236 0 0 4 34 4 0 19 45 35 0 0 解釋說明: ----------------------------- procs部分的解釋 r 列表示執行和等待cpu時間片的程式數,如果長期大於1,說明cpu不足,需要增加cpu。 b 列表示在等待資源的程式數,比如正在等待I/O、或者記憶體交換等。 ----------------------------- cpu部分的解釋 us 列顯示了使用者方式下所花費 CPU 時間的百分比。us的值比較高時,說明使用者程式消耗的cpu時間多,但是如果長期大於50%,需要考慮優化使用者的程式。 sy 列顯示了核心程式所花費的cpu時間的百分比。這裡us + sy的參考值為80%,如果us+sy 大於 80%說明可能存在CPU不足。 wa 列顯示了IO等待所佔用的CPU時間的百分比。這裡wa的參考值為30%,如果wa超過30%,說明IO等待嚴重,這可能是磁碟大量隨機訪問造成的,也可能磁碟或者 磁碟訪問控制器的頻寬瓶頸造成的(主要是塊操作)。 id 列顯示了cpu處在空閒狀態的時間百分比 ----------------------------- system部分的解釋 in 列表示在某一時間間隔中觀測到的每秒裝置中斷數。 cs列表示每秒產生的上下文切換次數,如當 cs 比磁碟 I/O 和網路資訊包速率高得多,都應進行進一步調查。 ----------------------------- memory部分的解釋 swpd 切換到記憶體交換區的記憶體數量(k表示)。如果swpd的值不為0,或者比較大,比如超過了100m,只要si、so的值長期為0,系統效能還是正常 free 當前的空閒頁面列表中記憶體數量(k表示) buff 作為buffer cache的記憶體數量,一般對塊裝置的讀寫才需要緩衝。 cache: 作為page cache的記憶體數量,一般作為檔案系統的cache,如果cache較大,說明用到cache的檔案較多,如果此時IO中bi比較小,說明檔案系統效率比較好。 ----------------------------- swap部分的解釋 si 由記憶體進入記憶體交換區數量。 so由記憶體交換區進入記憶體數量。 ----------------------------- IO部分的解釋 bi 從塊裝置讀入資料的總量(讀磁碟)(每秒kb)。 bo 塊裝置寫入資料的總量(寫磁碟)(每秒kb) 5)也可以使用dstat命令檢視cpu資訊 [root@localhost ~]# dstat ----total-cpu-usage---- -dsk/total- -net/total- ---paging-- ---system-- usr sys idl wai hiq siq| read writ| recv send| in out | int csw 19 45 35 0 0 0| 30k 265k| 0 0 | 0 0 |9025 12k 9 18 73 0 0 0| 0 144k|2578k 65k| 0 0 |3956 4343 6)可以使用iostat檢視IO負載 [root@localhost ~]# iostat 1 1 Linux 2.6.32-696.16.1.el6.x86_64 (nc-ftp01.kevin.cn) 2017年12月29日 _x86_64_ (4 CPU) avg-cpu: %user %nice %system %iowait %steal %idle 19.32 0.00 45.44 0.06 0.26 34.93 Device: tps Blk_read/s Blk_wrtn/s Blk_read Blk_wrtn xvda 14.17 29.94 265.17 63120486 558975100 解釋說明: avg-cpu: 總體cpu使用情況統計資訊,對於多核cpu,這裡為所有cpu的平均值 %user: 在使用者級別執行所使用的CPU的百分比. %nice: nice操作所使用的CPU的百分比. %sys: 在系統級別(kernel)執行所使用CPU的百分比. %iowait: CPU等待硬體I/O時,所佔用CPU百分比. %idle: CPU空閒時間的百分比. Device段:各磁碟裝置的IO統計資訊 tps: 每秒鐘傳送到的I/O請求數. Blk_read /s: 每秒讀取的block數. Blk_wrtn/s: 每秒寫入的block數. Blk_read: 讀入的block總數. Blk_wrtn: 寫入的block總數. [root@localhost ~]# iostat -x -k -d 1 Linux 2.6.32-696.el6.x86_64 (centos6-vm02) 01/04/2018 _x86_64_ (4 CPU) Device: rrqm/s wrqm/s r/s w/s rkB/s wkB/s avgrq-sz avgqu-sz await r_await w_await svctm %util scd0 0.00 0.00 0.00 0.00 0.00 0.00 8.00 0.00 0.36 0.36 0.00 0.36 0.00 vda 0.01 0.13 0.04 0.13 0.60 0.89 18.12 0.00 2.78 0.19 3.53 2.55 0.04 dm-0 0.00 0.00 0.04 0.22 0.58 0.88 11.25 0.00 3.27 0.25 3.82 1.61 0.04 dm-1 0.00 0.00 0.00 0.00 0.00 0.00 8.00 0.00 0.13 0.13 0.00 0.04 0.00 dm-2 0.00 0.00 0.00 0.00 0.00 0.00 7.91 0.00 0.19 0.10 5.00 0.16 0.00 解釋說明: rrqm/s: 每秒對該裝置的讀請求被合併次數,檔案系統會對讀取同塊(block)的請求進行合併 wrqm/s: 每秒對該裝置的寫請求被合併次數 r/s: 每秒完成的讀次數 w/s: 每秒完成的寫次數 rkB/s: 每秒讀資料量(kB為單位) wkB/s: 每秒寫資料量(kB為單位) avgrq-sz:平均每次IO操作的資料量(扇區數為單位) avgqu-sz: 平均等待處理的IO請求佇列長度 await: 平均每次IO請求等待時間(包括等待時間和處理時間,毫秒為單位) svctm: 平均每次IO請求的處理時間(毫秒為單位) %util: 採用週期內用於IO操作的時間比率,即IO佇列非空的時間比率 如果 %util 接近 100%,說明產生的I/O請求太多,I/O系統已經滿負荷,該磁碟可能存在瓶頸。 idle小於70% IO壓力就較大了,一般讀取速度有較多的wait。 同時可以結合vmstat 檢視檢視b引數(等待資源的程式數)和wa引數(IO等待所佔用的CPU時間的百分比,高過30%時IO壓力高)
簡單說下CPU負載和CPU利用率的區別
0)load average:系統平均負載是CPU的Load,它所包含的資訊不是CPU的使用率狀況,而是在一段時間內CPU正在處理以及等待CPU處理的程式數之和的統計資訊, 也就是CPU使用佇列的長度的統計資訊,這個數字越小越好。 1)CPU使用率:顯示的是程式在執行期間實時佔用的CPU百分比。 2)CPU負載:顯示的是一段時間內正在使用和等待使用CPU的平均任務數。CPU使用率高,並不意味著負載就一定大。 舉例來說:如果我有一個程式它需要一直使用CPU的運算功能,那麼此時CPU的使用率可能達到100%,但是CPU的工作負載則是趨近於"1",因為CPU僅負責一個工作啊。 如果同時執行這樣的程式兩個呢?CPU的使用率還是100%,但是工作負載則變成2了。所以也就是說,當CPU的工作負載越大,代表CPU必須要在不同的工作之間進行頻繁 的工作切換。 3)CPU利用率高,並不意味著負載就一定大。 舉例來說: 如果有一個程式它需要一直使用CPU的運算功能,那麼此時CPU的使用率可能達到100%,但是CPU的工作負載則是趨近於"1",因為CPU僅負責一個工作! 如果同時執行這樣的程式兩個呢?CPU的使用率還是100%,但是工作負載則變成2了。所以也就是說,當CPU的工作負載越大,代表CPU必須要在不同的工作之間 進行頻繁的工作切換。 ------------------------下面通過一個電話亭打電話的比喻來說明這兩者之間的區別------------------------ 某公用電話亭,有一個人在打電話,四個人在等待,每人限定使用電話一分鐘,若有人一分鐘之內沒有打完電話,只能掛掉電話去排隊,等待下一輪。 電話在這裡就相當於CPU,而正在或等待打電話的人就相當於任務數。 在電話亭使用過程中,肯定會有人打完電話走掉,有人沒有打完電話而選擇重新排隊,更會有新增的人在這兒排隊,這個人數的變化就相當於任務數的增減。 為了統計平均負載情況,我們5分鐘統計一次人數,並在第1、5、15分鐘的時候對統計情況取平均值,從而形成第1、5、15分鐘的平均負載。 有的人拿起電話就打,一直打完1分鐘,而有的人可能前三十秒在找電話號碼,或者在猶豫要不要打,後三十秒才真正在打電話。如果把電話看作CPU,人數看 作任務,我們就說前一個人(任務)的CPU利用率高,後一個人(任務)的CPU利用率低。當然, CPU並不會在前三十秒工作,後三十秒歇著,只是說,有的程 序涉及到大量的計算,所以CPU利用率就高,而有的程式牽涉到計算的部分很少,CPU利用率自然就低。但無論CPU的利用率是高是低,跟後面有多少任務在排隊 沒有必然關係。
=========正確理解%iowait和CPU使用率=========
1)%steal 一般是在虛擬機器中才能看到數值,比如CPU overcommitment很嚴重的VPS,而%guest和%nice一般都很低,所以也可以 根據/proc/stat或者top可得,user + nice + system + idle + iowait + irq + softirq + steal = 100 2)Linux程式狀態 執行狀態(TASK_RUNNING): 是執行態和就緒態的合併,表示程式正在執行或準備執行,Linux 中使用TASK_RUNNING 巨集表示此狀態 可中斷睡眠狀態(淺度睡眠)(TASK_INTERRUPTIBLE): 程式正在睡眠(被阻塞),等待資源到來是喚醒,也可以通過其他程式訊號或時鐘中斷喚醒,進入執行佇列。Linux 使用TASK_INTERRUPTIBLE 巨集表示此狀態。 不可中斷睡眠狀態(深度睡眠狀態)(TASK_UNINTERRUPTIBLE): 其和淺度睡眠基本類似,但有一點就是不可被其他程式訊號或時鐘中斷喚醒。Linux 使用TASK_UNINTERRUPTIBLE 巨集表示此狀態。 暫停狀態(TASK_STOPPED): 程式暫停執行接受某種處理。如正在接受除錯的程式處於這種狀態,Linux 使用TASK_STOPPED 巨集表示此狀態。 僵死狀態(TASK_ZOMBIE): 程式已經結束但未釋放PCB,Linux 使用TASK_ZOMBIE 巨集表示此狀態。 3)%iowait 的正確認知 %iowait 表示在一個取樣週期內有百分之幾的時間屬於以下情況:CPU空閒、並且有仍未完成的I/O請求。 對 %iowait 常見的誤解有兩個: 一是誤以為 %iowait 表示CPU不能工作的時間, 二是誤以為 %iowait 表示I/O有瓶頸。 首先 %iowait 升高並不能證明等待I/O的程式數量增多了,也不能證明等待I/O的總時間增加了。 例如: 在CPU繁忙期間發生的I/O,無論IO是多還是少,%iowait都不會變; 當CPU繁忙程度下降時,有一部分IO落入CPU空閒時間段內,導致%iowait升高。 再比如:IO的併發度低,%iowait就高;IO的併發度高,%iowait可能就比較低。 可見%iowait是一個非常模糊的指標,如果看到 %iowait 升高,還需檢查I/O量有沒有明顯增加, avserv/avwait/avque等指標有沒有明顯增大,應用有沒有感覺變慢,如果都沒有,就沒什麼好擔心的。 4)檢視CPU使用率,推薦如下Linux命令: # top # sar -u 1 5 # vmstat -n 1 5 # mpstat -P ALL 1 5 檢視Load的值,推薦如下Linux命令: # top # uptime # sar -q 1 5
load average相關梳理(一分鐘,五分鐘,十五分鐘的平均CPU負載,最重要的指標是最後一個數字,即前15分鐘的平均CPU負載,這個數字越小越好。所謂CPU負載指的是一段時間內任務佇列的長度,通俗的講,就是一段時間內一共有多少任務在使用或等待使用CPU。(當前的"負載值除以cpu核數"就是cpu的利用率))
load average表示的是系統的平均負荷,即CPU的Load。 它所包含的資訊不是CPU的使用率狀況,而是在一段時間內CPU正在處理以及等待CPU處理的程式數之和的統計資訊,也就是CPU使用佇列的長度的統計資訊。 它包括3個數字,分別表示系統在1、5、15分鐘內程式佇列中的平均程式數量(即處理的程式情況), 原則上來說這3個數字越小越好,數字越小表示伺服器的工作量越小,系統負荷比較輕 當CPU完全空閒的時候,平均負荷為0(即load average的值為0);當CPU工作量飽和的時候,平均負荷為1。 這裡需要注意的是: load average這個輸出值,這三個值的大小一般不能大於系統邏輯CPU的個數 比如一臺伺服器有4個邏輯CPU,如果load average的三個值長期大於4時,說明CPU很繁忙,負載很高,可能會影響系統效能; 但是偶爾大於4時,倒不用擔心,一般不會影響系統效能。 相反,如果load average的輸出值小於CPU的個數,則表示CPU還有空閒,比如本例中的輸出,CPU是比較空閒的。 -------------load average舉例理解--------------- 判斷系統負荷是否過重,必須理解load average的真正含義。假設當前我的一臺伺服器只有一個CPU,所有的運算都必須由這個CPU來完成。 不妨把這個CPU想象成一座大橋,橋上只有一根車道,所有車輛都必須從這根車道上通過(很顯然,這座橋只能單向通行)。 1)系統負荷為0,意味著大橋上一輛車也沒有。 2)系統負荷為0.5,意味著大橋一半的路段有車。 3)系統負荷為1.0,意味著大橋的所有路段都有車,也就是說大橋已經"滿"了。但是必須注意的是,直到此時大橋還是能順暢通行的。 4)系統負荷為1.7,意味著車輛太多了,大橋已經被佔滿了(100%),後面等著上橋的車輛為橋面車輛的70%。 以此類推,系統負荷2.0,意味著等待上橋的車輛與橋面的車輛一樣多; 系統負荷3.0,意味著等待上橋的車輛是橋面車輛的2倍。 總之,當系統負荷大於1,後面的車輛就必須等待了;系統負荷越大,過橋就必須等得越久。 CPU的系統負荷,基本上等同於上面的類比。大橋的通行能力,就是CPU的最大工作量;橋樑上的車輛,就是一個個等待CPU處理的程式(process)。 如果CPU每分鐘最多處理100個程式,那麼: 系統負荷0.2,意味著CPU在這1分鐘裡只處理20個程式; 系統負荷1.0,意味著CPU在這1分鐘 里正好處理100個程式; 系統負荷1.7,意味著除了CPU正在處理的100個程式以外,還有70個程式正排隊等著CPU處理。 為了伺服器順暢執行,系統負荷最好不要超過1.0,這樣就沒有程式需要等待了,所有程式都能第一時間得到處理。 很顯然,1.0是一個關鍵值,超過這個值,系統就不在最佳狀態了,就需要動手干預了。 --------1.0是系統負荷的理想值嗎?----------- 不一定,系統管理員往往會留一點餘地,當這個值達到0.7,就應當引起注意了。 以往經驗是這樣的: 當系統負荷持續大於0.7,必須開始調查了,問題出在哪裡,防止情況惡化。 當系統負荷持續大於1.0,必須動手尋找解決辦法,把這個值降下來。 當系統負荷達到5.0,就表明系統有很嚴重的問題,長時間沒有響應,或者接近當機了。覺不能讓系統達到這個值。 上面,假設我的這臺伺服器只有1個CPU。如果它裝了2個CPU,就意味著伺服器的處理能力翻了一倍,能夠同時處理的程式數量也翻了一倍。 還是用大橋來類比,兩個CPU就意味著大橋有兩根車道了,通車能力翻倍了。 所以,2個CPU表明系統負荷可以達到2.0,此時每個CPU都達到100%的工作量。推廣開來,n個CPU的伺服器,可接受的系統負荷最大為n.0。 ---------至於load average是多少才算理想,這個有爭議,各有各的說法--------- 個人比較贊同CPU負載小於等於"核心數乘以0.5-0.7"算是一種理想狀態。 比如4核CPU的伺服器,理想負載是小於等於2,最好不要超過2.8,否則效能多少會受影響。 不管某個CPU的效能有多好,1秒鐘能處理多少任務,可以認為它無關緊要,雖然事實並非如此。 在評估CPU負載時,只以5分鐘為單位做統計任務佇列長度。如果每隔5分鐘統計的時候,發現任務佇列長度都是1,那麼CPU負載就為1。 假如現在某臺伺服器只有一個單核的CPU,負載一直為1,意味著沒有任務在排隊,還不錯。 但是這臺伺服器是雙核CPU,等於是有4個核心,每個核心的負載為1的話,總負載為4。這就是說,如果這臺伺服器的CPU負載長期保持在4左右,還可以接受。 但是每個核心的負載為1,並不能算是一種理想狀態!這意味著伺服器的CPU一直很忙,不得清閒。 -----------load average返回三個平均值應該參考哪個值?------------ 如果只有1分鐘的系統負荷大於1.0,其他兩個時間段都小於1.0,這表明只是暫時現象,問題不大。 如果15分鐘內,平均系統負荷大於1.0(調整CPU核心數之後),表明問題持續存在,不是暫時現象。 所以應該主要觀察"15分鐘系統負荷",將它作為伺服器正常執行的指標。 ----------如何來降低伺服器的CPU負載?-------------- 最簡單辦法的是更換效能更好的伺服器,不要想著僅僅提高CPU的效能,那沒有用,CPU要發揮出它最好的效能還需要其它軟硬體的配合。 在伺服器其它方面配置合理的情況下,CPU數量和CPU核心數(即核心數)都會影響到CPU負載,因為任務最終是要分配到CPU核心去處理的。兩塊CPU要比一塊 CPU好,雙核要比單核好。因此,需要記住的是:除去CPU效能上的差異,CPU負載是基於核心數來計算的。有一個說法是"有多少核心,即有多少負載"。