
Ubuntu日本語フォーラム

ログインしていません。
以下のコードの実行が他のLinux(CentOS5, SuSE)と挙動が違うので、報告します。
CentOSやSuSEでは、以下のコードをコンパイル・実行してもCPU Loadが0%です。しかし、
Ubuntu 8.04 では10%以上になります。Threadを作れば作るほど、CPUのLoadが増加するようです。
CentOSやSuSEでは、Threadを5個以下では、CPU Loadが0%です。
nanosleepの待ち時間を10倍にすると、CPU Loadが減少することは分かっています。
CPUの性能とコードの実行を考えても、10%以上になることは、nanosleepがうまく動作していない
か、粒度が他のLinuxと比べて大きいのか、実装に誤りがあるとしか思えません。
理由がお分かりになる方がおられましたら、お教えください。
#include <stdio.h>
#include <stdlib.h>
#include <sys/time.h>
#include <sys/types.h>
#include <unistd.h>
#include <pthread.h>
#include <unistd.h>
void TestFun(void *oo)
{
struct timespec SSet,Result;
for( ; ; ) {
SSet.tv_sec = 0;
SSet.tv_nsec = 1000;
Result.tv_nsec = 0;
nanosleep(&SSet,&Result);
}
}
int main(int argc, char **argv)
{
int i,max;
pthread_t Thread[5];
max = 1;
if( argc > 1 ) {
max = atoi(argv[1]);
}
if( max > 5 ) {
max = 5;
}
for( i = 0 ; i < max ; i++ ) {
if(pthread_create(&Thread[i],(pthread_attr_t *)NULL,
(void *(*)(void *))TestFun,NULL) != 0 ) {
fprintf(stderr,"error pthread\n");
exit(0);
}
}
getchar();
}オフライン
粒度という単語が出ているのでお気づきの通り、単にJiffies「まわり」の違いという話だったりしませんか? そりゃーnanosleepに1000なんて極小値食わせれば、Jiffiesによってはnanosleepが「与えられた値の通りに」動作してbusy loopになるので、CPU負荷率も上がろうかねって話になるわけですが……。
対象もコントロール群もkernel versionが書かれてないので「まわり」としか言えませんし、なにか別の原因であるというオチもありそうですが、nanosleepに食わせる値を増やせば挙動が変わるなら、たぶんJiffiesのというかHZの違いではないでしょうか。
# で、それは.config見ればわかるよねという。
傍証として確認するのであれば、nanosleepに与える数字を全環境で順に大きくしていき、どこかで「飽和」するかどうかを調べれば良いかと。
で、nanosleepはJiffiesに依存してしまうのでこの種のコードはRT以外では書かない方がいい(RTでも外部ハードウェア待ち以外ではスケジューリングを工夫して書くべきではない)ような気もしますが、背後になにか別の問題があるでしょうか?
何が言いたいかというと、背景があるなら示してよという話なのですが。
http://pc11.2ch.net/test/read.cgi/linux/1212567572/195-205
オフライン
解決できました。CentOS5やSuSEでは、単にハードウェアの割り込み周波数を利用しているようです。割込みの周波数が
100Hz程度あろうと思います。このため、割込み周波数以下の値が設定されていても、ハードウェアの割込み周波数を
利用するものと思います。
一方、Ubuntuでは、ハードウェアの割込み周波数以下の値が設定されていると、多分内部でループを行い時間を調整しているように思えます。このため、CPU Loadが上昇したと思えます。
オフライン