助けてください。プロセス XYZ がマイグレートしません 下記で Moshe Bar 氏はなぜプロセスにマイグレートするもの、しないものが あるのかを説明しています。いつものように /proc/$pid/ を見る前に、 cantmoveを見てください。該当プロセスがなぜマイグレート できないのかわかるでしょう。
プロセスをロックすることもできますが、プロセスがロックされていないか どうかもチェックできます。
cat /proc/$PID/lock |
では、Moshe 氏自身がこの件について述べたことを挙げます。
よくあるのは、同じカーネルを使ってはいるが、RedHat と Debian が混在している といったようなディストリビューションに相違があるケースです。ディストリ ビューションが異なると、rc スクリプトが異なるやり方で openMosix を起動する 傾向にあります。 ある実装では /etc/inittab をすっかり書き換えてデーモンすべて(とその子供も)を
mosrun -h |
それでは、下記の単純なプログラムをローカルの CPU 数より多く起動して、常に マイグレートさせてみましょう。2-way SMP システムでは、このプログラムを 3 回 起動し、クラスタ内にあるノードがローカルのシステムと似たような速度を持って いれば、マイグレートします。
int main() { unsigned int i; while (1) { i++; } return 0; } |
下記のような内容を持つサンプルプログラムは、決してマイグレートしません。
#include <sys/types.h> #include <sys/ipc.h> #include <sys/shm.h> ... key_t key; /* key to be passed to shmget() */ int shmflg; /* shmflg to be passed to shmget() */ int shmid; /* return value from shmget() */ int size; /* size to be passed to shmget() */ ... key = ... size = ... shmflg) = ... if ((shmid = shmget (key, size, shmflg)) == -1) { perror("shmget: shmget failed"); exit(1); } else { (void) fprintf(stderr, "shmget: shmget returned %d\n", shmid); exit(0); } ... |
下記のようなパイプを使ったプログラムは、うまくマイグレートします。
int pdes[2]; pipe(pdes); if ( fork() == 0 ) { /* child */ close(pdes[1]); /* not required */ read( pdes[0]); /* read from parent */ ..... } else { close(pdes[0]); /* not required */ write( pdes[1]); /* write to child */ ..... } |
// // Very simple program demonstrating the use of threads. // // Command-line argument is P (number of threads). // // Each thread writes "hello" message to standard output, with // no attempt to synchronize. Output will likely be garbled. // #include <iostream> #include <cstdlib> // has exit(), etc. #include <unistd.h> // has usleep() #include <pthread.h> // has pthread_ routines // declaration for function to be executed by each thread void * printHello(void * threadArg); // ---- Main program ------------------------------------------------- int main(int argc, char* argv[]) { if (argc < 2) { cerr << "Usage: " << argv[0] << " numThreads\n"; exit(EXIT_FAILURE); } int P = atoi(argv[1]); // Set up IDs for threads (need a separate variable for each // since they're shared among threads). int * threadIDs = new int[P]; for (int i = 0; i < P; ++i) threadIDs[i] = i; // Start P new threads, each with different ID. pthread_t * threads = new pthread_t[P]; for (int i = 0; i < P; ++i) pthread_create(&threads[i], NULL, printHello, (void *) &threadIDs[i]); // Wait for all threads to complete. for (int i = 0; i < P; ++i) pthread_join(threads[i], NULL); // Clean up and exit. delete [] threadIDs; delete [] threads; cout << "That's all, folks!\n"; return EXIT_SUCCESS; } // ---- Code to be executed by each thread --------------------------- // pre: *threadArg is an integer "thread ID". // post: "hello" message printed to standard output. // return value is null pointer. void * printHello(void * threadArg) { int * myID = (int *) threadArg; cout << "hello, world, "; // pointless pause, included to make the effects of // synchronization (or lack thereof) more obvious usleep(10); cout << "from thread " << *myID << endl; pthread_exit((void* ) NULL); } |
(上記のコードは Moshe 氏によるものです。Moshe Bar 氏個人によるもの、もしくは Qlusters, Inc. の CTO としての Moshe 氏のどちらかの立場です)。
openMosix の man も参照してください。プロセスがどうしてマイグレート しないかについて、それなりに説明してあります。
何らかの理由で、意図せずにプロセスがロックしたままになってしまった場合、 ロックされたプロセスをマイグレートするには、下記の記述を
# tell shells to allow subprocs to migrate to other nodes echo 0 > /proc/self/lock |