某所で話題に上がったので軽くまとめてみる
以下のようなテストプログラムを走らせてみる。nice値5とnice値10のスレッドが
ビジーループを何回回すことができるか競争するというプログラムである


struct thread_param {
int prio;
long counter;
};

#define barrier() __asm__ __volatile__("": : :"memory")

void* loop(void* _param)
{
struct thread_param *param = _param;

setpriority(PRIO_PROCESS, 0, param->prio);
usleep(1000);

for(;;) {
param->counter++;
barrier();
}

return NULL;
}

int main()
{
pthread_t thr;
cpu_set_t cpuset;
struct thread_param param1 = {
.prio = 5,
};
struct thread_param param2 = {
.prio = 10,
};

CPU_ZERO(&cpuset);
CPU_SET(0, &cpuset);

sched_setaffinity(0, sizeof(cpu_set_t), &cpuset);

pthread_create(&thr, NULL, loop, ¶m1);
pthread_create(&thr, NULL, loop, ¶m2);

sleep(1);

printf("%ld %ld %f\n", param1.counter, param2.counter,
((double)param1.counter)/param2.counter);

return 0;
}


そうすると、ほぼブレなく、のように、2つのループの差が3倍となる。
219989975 72166990 3.048346

これは kernel watchのスケジューラ特集の回 で説明したように、カーネル内部で優先度1違う毎に1.25倍のボーナスがついているので、1.25^5 ≒ 3 という理屈である。

まとめるとnice値が5変わるごとに3倍CPU時間が変わる。という関係は憶えておくと便利だよ。と