天天看點

CFS排程器中子程序被喚醒後的細節--實驗和理論

在我送出并自己打上child-runs-first更新檔之前,我做了一個實驗,目的是驗證一下我先前理論分析的結果,我覺得子程序無論如何搶占父程序的幾率都會比不搶占要大些,當然前提是要有的,具體見下面的試驗。空有理論是沒有用的,理論上cfs排程器執行嚴格的歸一化,然而實際上卻不是那樣的,實踐結果永遠比理論更加現實,因為不執行歸一化絲毫影響不了cfs排程器選擇最小vruntime的程序,這很簡單,每一個程序按照自己的權值和目前的系統排程周期執行動态時間片的時間,同時按照不同的速率推進自己的虛拟時間,排程器隻要能保證各個程序在運作按照其權值分給它們的不同時間片之後可以向前推進相同的虛拟時間就可以了,管他什麼歸一化呢?正是這樣,cfs排程器運作的很好。

環境:單cpu,HZ=250,linux-2.6.28原始核心(沒有打我的child_runs_first更新檔)

核心配置與實驗前提:sysctl_sched_child_runs_first=0,sysctl_sched_features=(僅打開AKEUP_PREEMPT),sysctl_sched_wakeup_granularity=0,sysctl_sched_latency_ns=20000000.

目的:在沒有sysctl_sched_child_runs_first政策的情況下測試cfs排程器在子程序被喚醒時的行為

測試程式:

-------stub--------

/*模拟cpu程序,将cfs_rq的nr_running提高到一定數量*/

int main(int argc,char*argv[] )

{

nice(atoi(argv[1]));

int a = 1,b=0;

while(a++||1)

b+=a;

}

-------child_run_delay--------

/*父程序延遲一會再fork,避免托shell在fork父程序時給了父程序min_vruntime的福*/

#include.h>

#include

int main(int argc,char *argv[])

int v = atoi(argv[1]);

nice(v);

unsigned long i = 1000000;

while(i-->0)

v++;

if(fork() == 0)

printf("sub/n");

exit(0);

printf("main,%d/n",v);

-------child_run_nodelay--------

/*馬上fork子程序,托父程序vruntime很小的福*/

printf("main/n");

測試過程:連續建立9個stub程序,nice值分散開來,然後以不同的nice值運作child_run_delay和child_run_nodelay。

結果:

測試代碼中i=1000時的測試結果

 本文轉自 dog250 51CTO部落格,原文連結:http://blog.51cto.com/dog250/1274136