我們對(duì)系統(tǒng)性能進(jìn)行優(yōu)化時(shí),一般會(huì)使用top命令來(lái)查看系統(tǒng)負(fù)載和系統(tǒng)中各個(gè)進(jìn)程的運(yùn)行情況,從而找出影響系統(tǒng)性能的因素。如下圖所示:

top
top命令會(huì)輸出很多系統(tǒng)相關(guān)的信息,如:系統(tǒng)負(fù)載、系統(tǒng)中的進(jìn)程數(shù)、CPU使用率和內(nèi)存使用率等,這些信息對(duì)排查系統(tǒng)性能問(wèn)題起著至關(guān)重要的作用。
本文主要介紹top命令中的iowait指標(biāo)(如上圖中紅色方框所示)的含義和作用。
什么是iowait
什么是iowait?我們來(lái)看看 Linux 的解釋:
Show the percentage of time that the CPU or CPUs were idle during which the system had an outstanding disk I/O request.
中文翻譯的意思就是:CPU 在等待磁盤 I/O 請(qǐng)求完成時(shí),處于空閑狀態(tài)的時(shí)間百分比(此時(shí)正在運(yùn)行著idle進(jìn)程)。
可以看出,如果系統(tǒng)處于iowait狀態(tài),那么必須滿足以下兩個(gè)條件:
系統(tǒng)中存在等待 I/O 請(qǐng)求完成的進(jìn)程。
系統(tǒng)當(dāng)前正處于空閑狀態(tài),也就是說(shuō)沒有可運(yùn)行的進(jìn)程。
iowait統(tǒng)計(jì)原理
既然我們知道了iowait的含義,那么接下來(lái)看看 Linux 是怎么統(tǒng)計(jì)iowait的比率的。
Linux 會(huì)把iowait占用的時(shí)間輸出到/proc/stat文件中,我們可以通過(guò)一下命令來(lái)獲取到iowait占用的時(shí)間:
cat/proc/stat
命令輸出如下圖所示:

stat
紅色方框中的數(shù)據(jù)就是iowait占用的時(shí)間。
我們可以每隔一段時(shí)間讀取一次/proc/stat文件,然后把兩次獲取到的iowait時(shí)間進(jìn)行相減,得到的結(jié)果是這段時(shí)間內(nèi),CPU處于iowait狀態(tài)的時(shí)間。接著再將其除以總時(shí)間,得到iowait占用總時(shí)間的比率。
現(xiàn)在我們來(lái)看看/proc/stat文件是怎樣獲取iowait的時(shí)間的。
在內(nèi)核中,每個(gè) CPU 都有一個(gè)cpu_usage_stat結(jié)構(gòu),主要用于統(tǒng)計(jì) CPU 一些信息,其定義如下:
structcpu_usage_stat{
cputime64_tuser;
cputime64_tnice;
cputime64_tsystem;
cputime64_tsoftirq;
cputime64_tirq;
cputime64_tidle;
cputime64_tiowait;
cputime64_tsteal;
cputime64_tguest;
cputime64_tguest_nice;
};
cpu_usage_stat結(jié)構(gòu)的iowait字段記錄了 CPU 處于iowait狀態(tài)的時(shí)間。
所以要獲取系統(tǒng)處于iowait狀態(tài)的總時(shí)間,只需要將所有 CPU 的iowait時(shí)間相加即可,代碼如下(位于源文件fs/proc/stat.c):
staticintshow_stat(structseq_file*p,void*v)
{
u64iowait;
...
//1.遍歷系統(tǒng)中的所有CPU
for_each_possible_cpu(i){
...
//2.獲取CPU對(duì)應(yīng)的iowait時(shí)間,并相加
iowait=cputime64_add(iowait,kstat_cpu(i).cpustat.iowait);
...
}
...
return0;
}
show_stat()函數(shù)首先會(huì)遍歷所有 CPU,然后讀取其iowait時(shí)間,并且將它們相加。
增加iowait時(shí)間
從上面的分析可知,每個(gè) CPU 都有一個(gè)用于統(tǒng)計(jì)iowait時(shí)間的計(jì)數(shù)器,那么什么時(shí)候會(huì)增加這個(gè)計(jì)數(shù)器呢?
答案是:系統(tǒng)時(shí)鐘中斷。
在系統(tǒng)時(shí)鐘中斷中,會(huì)調(diào)用account_process_tick()函數(shù)來(lái)更新 CPU 的時(shí)間,代碼如下:
voidaccount_process_tick(structtask_struct*p,intuser_tick)
{
cputime_tone_jiffy_scaled=cputime_to_scaled(cputime_one_jiffy);
structrq*rq=this_rq();
//1.如果當(dāng)前進(jìn)程處于用戶態(tài),那么增加用戶態(tài)的CPU時(shí)間
if(user_tick){
account_user_time(p,cputime_one_jiffy,one_jiffy_scaled);
}
//2.如果前進(jìn)程處于內(nèi)核態(tài),并且不是idle進(jìn)程,那么增加內(nèi)核態(tài)CPU時(shí)間
elseif((p!=rq->idle)||(irq_count()!=HARDIRQ_OFFSET)){
account_system_time(p,HARDIRQ_OFFSET,cputime_one_jiffy,
one_jiffy_scaled);
}
//3.如果當(dāng)前進(jìn)程是idle進(jìn)程,那么調(diào)用account_idle_time()函數(shù)進(jìn)行處理
else{
account_idle_time(cputime_one_jiffy);
}
}
我們主要關(guān)注當(dāng)前進(jìn)程是idle進(jìn)程的情況,這是內(nèi)核會(huì)調(diào)用account_idle_time()函數(shù)進(jìn)行處理,其代碼如下:
voidaccount_idle_time(cputime_tcputime)
{
structcpu_usage_stat*cpustat=&kstat_this_cpu.cpustat;
cputime64_tcputime64=cputime_to_cputime64(cputime);
structrq*rq=this_rq();
//1.如果當(dāng)前有進(jìn)程在等待IO請(qǐng)求的話,那么增加iowait的時(shí)間
if(atomic_read(&rq->nr_iowait)>0){
cpustat->iowait=cputime64_add(cpustat->iowait,cputime64);
}
//2.否則增加idle的時(shí)間
else{
cpustat->idle=cputime64_add(cpustat->idle,cputime64);
}
}
account_idle_time()函數(shù)的邏輯比較簡(jiǎn)單,主要分以下兩種情況進(jìn)行處理:
如果當(dāng)前有進(jìn)程在等待 I/O 請(qǐng)求的話,那么增加iowait的時(shí)間。
如果當(dāng)前沒有進(jìn)程在等待 I/O 請(qǐng)求的話,那么增加idle的時(shí)間。
所以,從上面的分析可知,要增加iowait的時(shí)間需要滿足以下兩個(gè)條件:
當(dāng)前進(jìn)程是idle進(jìn)程,也就是說(shuō) CPU 處于空閑狀態(tài)。
有進(jìn)程在等待 I/O 請(qǐng)求完成。
進(jìn)一步說(shuō),當(dāng) CPU 處于iowait狀態(tài)時(shí),說(shuō)明 CPU 處于空閑狀態(tài),并且系統(tǒng)中有進(jìn)程因?yàn)榈却?I/O 請(qǐng)求而阻塞,也說(shuō)明了 CPU 的利用率不夠充分。
這時(shí),我們可以使用異步 I/O(如iouring)來(lái)優(yōu)化程序,使得進(jìn)程不會(huì)被 I/O 請(qǐng)求阻塞。
審核編輯:劉清
-
cpu
+關(guān)注
關(guān)注
68文章
11202瀏覽量
222225 -
LINUX內(nèi)核
+關(guān)注
關(guān)注
1文章
317瀏覽量
22978 -
時(shí)鐘中斷
+關(guān)注
關(guān)注
0文章
4瀏覽量
7994
原文標(biāo)題:系統(tǒng)性能分析之|iowait是什么?
文章出處:【微信號(hào):LinuxHub,微信公眾號(hào):Linux愛好者】歡迎添加關(guān)注!文章轉(zhuǎn)載請(qǐng)注明出處。
發(fā)布評(píng)論請(qǐng)先 登錄
使用吉時(shí)利DMM的比率功能測(cè)量功率
如何在Linux使用iostat命令
統(tǒng)計(jì)工具箱函數(shù)匯總
linux統(tǒng)計(jì)文件個(gè)數(shù)
絕對(duì)輸出iMEMS陀螺儀與比率ADC的配合使用
算法大全_數(shù)據(jù)的統(tǒng)計(jì)描述和分析
RTD比率式溫度測(cè)量應(yīng)用
小差比率制動(dòng)系數(shù)校驗(yàn)的優(yōu)化
加密貨幣交易中采用的夏普比率是什么
比特幣的庫(kù)存與流動(dòng)比率分析
帶大家看看Linux內(nèi)核如何調(diào)度進(jìn)程的
深入探究Linux系統(tǒng)噪音統(tǒng)計(jì)(osnoise tracer)

看看Linux是怎么統(tǒng)計(jì)iowait比率的?
評(píng)論