Unix C で共有メモリ、セマフォ、およびフォークを使用する際に問題があります。私のセマフォは posix ではありません。共有メモリ 2*sizeof(float) へのポインタを作成します。semctl でセマフォの値を 2 に初期化します。for ループ (i<2) で fork() を実行します。子プロセス (fork() == 0 の場合) では、各子はセマフォで ap 操作を行い (-1)、共有メモリに書き込み、次に av 操作を行い (+1)、終了します。親プロセスは、セマフォで ap 操作 (-2) を実行し、(for ループを使用して) 共有メモリ セグメント全体を読み取り、av 操作 (+2) を実行します。彼は、ゾンビを避けるために終了する前に子プロセスを待機します。出力の問題は、次のようになることです。
Parent reading 0
Parent reading 1
Parent reading 0
Parent reading 1
Child writing 0
Child writing 1
私が取得する必要があるのはいつですか:
Child writing 0
Child writing 1
Parent reading 0
Parent reading 1
セマフォを 2 ではなく 1 に初期化しようとしましたが、セマフォの値が 2 になることはなく、親プロセスが読み取れないため、プログラムが停止するだけです。
セマフォについて私が理解していることが正しければ、セマフォを 2 に初期化するということは、子プロセスが何も書き込んでいないにもかかわらず、親プロセスが直接読み取ることができることを意味します。この問題を解決するにはどうすればよいですか?
編集: リクエスト後にコードの簡易版を追加しました。エラー チェックを削除し、子供が長さを短くするのを待ちました。
/** OPEN MEMORY **/
int shmid1 = shmget(1990, (size), IPC_CREAT | 0666 );
float * shmPt = (float*)shmat(shmid1, NULL, 0);
/** CREATE INITIALIZE SEMAPHORE **/
semun1.val = 2;
int semid = semget(1991, 1, 0666 | IPC_CREAT)
semctl(semid, 0, SETVAL, semun1 )
/** CREATE PROCESSES **/
for ( ii = 0; ii < 2; ++ii) {
if ((p = fork()) == 0) {
int semid = semget(1991, 1, 0666);
struct sembuf p_buf;
p_buf.sem_num = 0;p_buf.sem_op = -1;p_buf.sem_flg = SEM_UNDO;
/** LOCK **/
semop(semid, &p_buf,1);
/** WRITE **/
shmPt[ii] = RandomFloat;
v_buf.sem_num = 0;v_buf.sem_op = 1;v_buf.sem_flg = SEM_UNDO;
/** UNLOCK **/
semop(semid, &v_buf,1)
exit(0);
}
else {
int semid = semget(1991, 1, 0666);
struct sembuf p_buf;
p_buf.sem_num = 0;p_buf.sem_op = -2;p_buf.sem_flg = SEM_UNDO;
/** LOCK **/
semop(semid, &p_buf,1);
/** READ **/
for(int j =0;j<2;j++) tabFloat[j] = shmPt[j];
v_buf.sem_num = 0;v_buf.sem_op = 2;v_buf.sem_flg = SEM_UNDO;
/** UNLOCK **/
semop(semid, &v_buf,1)
}
}
編集: 私の最終的な目標は、24 人の子供が同じサイズの共有メモリ セグメントに 1 つずつ書き込み、それがいっぱいになったときにのみ、親がすべてを読み取って情報を処理できるようにすることです。さらに、これらすべてを while ループにする必要があります (最初の車が 50 周を完了するまで、1 周を完了するたびにランダムな時間を生成し続ける 24 台の車を想像してください)。