我有一个程序,它应该允许两个进程在执行某个任务之间交替。在子进程第五次执行其任务之后,它必须销毁一个信号量,并且父进程应该因为它而停止。
这听起来相当容易,但我很难捕获sem_wait()
函数的返回值。
这是我的档案:
#include "Part2Defs.h"
int main() {
FILE *fptr = 0;
sem_t *child = mmap(0, sizeof(sem_t), PROT_READ|PROT_WRITE,
MAP_SHARED|MAP_ANONYMOUS, -1, 0);
sem_t *parent = mmap(0, sizeof(sem_t), PROT_READ|PROT_WRITE,
MAP_SHARED|MAP_ANONYMOUS, -1, 0);
/* save the number that we'll be writing to the file */
int number = 1, removed = 0;
sem_init(child, 1, 1);
sem_init(parent, 1, 0);
fptr = fopen(BUFFER, "r+");
if(fptr == 0) {
printf("An error occurred while opening the file\n");
}
fprintf(fptr, "%d", number);
fclose(fptr);
int pID = fork();
if(pID == 0) {
/* do this FOREVER. */
while(1) {
/* I was hoping to get the return value here */
if(sem_wait(parent) == 0) {
/* open the file */
fptr = fopen(BUFFER, "r+");
printf("B. The number [] was modified by parent\n");
fclose(fptr);
sem_post(child);
}
else {
printf("--parent-- waiting for new number to be READ: Identifier removed");
}
}
return 0;
}
else if(pID > 0) {
/* make a counter to go from 0 to 5 */
int i = 0;
while(1) {
sem_wait(child);
if(i++ == 5) {
/* delete the semaphore */
sem_destroy(parent);
printf("Semaphore removed\n");
break;
}
/* open the file */
fptr = fopen(BUFFER, "r+");
printf("A. The number [] was modified by child\n");
fclose(fptr);
sem_post(parent);
}
return 0;
}
else {
printf("There was an error creating the fork.\n");
exit(1);
}
}
这是我的输出:
A. The number [] was modified by child
B. The number [] was modified by parent
A. The number [] was modified by child
B. The number [] was modified by parent
A. The number [] was modified by child
B. The number [] was modified by parent
A. The number [] was modified by child
B. The number [] was modified by parent
A. The number [] was modified by child
B. The number [] was modified by parent
Semaphore removed
这几乎正是我所希望的,除了父进程永远不会以包含错误的消息结束。
顺便说一句:这是家庭作业,但由于我缺乏声誉,我不应该在自己的帖子上添加家庭作业标签。
答案 0 :(得分:0)
sem_wait
的返回值仅反映其获取锁定的失败/失败。如果要在进程之间进行通信,则需要其他机制(例如,共享内存)。
答案 1 :(得分:0)
http://man7.org/linux/man-pages/man3/sem_destroy.3.html:
“销毁其他进程或线程当前的信号量 阻塞(在sem_wait(3)中)产生未定义的行为。“
我找到了一种方法,可以使用其中一个信号量作为标志来告诉父母何时完成。
#include "Part2Defs.h"
int main() {
FILE *fptr = 0;
sem_t *child = mmap(0, sizeof(sem_t), PROT_READ|PROT_WRITE,
MAP_SHARED|MAP_ANONYMOUS, -1, 0);
sem_t *parent = mmap(0, sizeof(sem_t), PROT_READ|PROT_WRITE,
MAP_SHARED|MAP_ANONYMOUS, -1, 0);
/* save the number that we'll be writing to the file */
int number = 1, removed = 0;
sem_init(child, 1, 0);
sem_init(parent, 1, 0);
fptr = fopen(BUFFER, "r+");
if(fptr == 0) {
printf("An error occurred while opening the file\n");
}
fprintf(fptr, "%d", number);
fclose(fptr);
int pID = fork();
if(pID == 0) {
/* do this FOREVER. */
while(1) {
sem_post(child);
sem_wait(parent);
if(!sem_trywait(child))
break;
/* open the file */
fptr = fopen(BUFFER, "r+");
printf("B. The number [] was modified by parent\n");
fflush(stdout);
fclose(fptr);
}
sem_destroy(child);
sem_destroy(parent);
printf("--parent-- waiting for new number to be READ: Identifier removed");
return 0;
}
else if(pID > 0) {
/* make a counter to go from 0 to 5 */
int i = 0;
while(1) {
sem_wait(child);
if(i++ == 5) {
sem_post(child);
sem_post(parent);
//Signal the parent that it's done by adding one to child.
printf("Semaphore removed\n");
break;
}
/* open the file */
fptr = fopen(BUFFER, "r+");
printf("A. The number [] was modified by child\n");
fflush(stdout);
fclose(fptr);
sem_post(parent);
}
return 0;
}
else {
printf("There was an error creating the fork.\n");
exit(1);
}
}