【发布时间】:2016-10-06 16:56:55
【问题描述】:
我有一个文件 instructions.txt(由文件指针 fp 表示),它由 12 行组成(每行包含字节 ls\n 和 ps\n 交替)。
最初主进程以读取模式打开文件,创建并初始化共享内存区域mem,并使用fork()创建另外11个进程。
12 个进程中的每一个都应该从文件中读取一行并执行该指令。在进入最外层while块之前,在所有进程中调用ftell(fp)返回0。
问题是,进入最外层if块的第一个进程使用fgets读取一行后,在其他进程中调用ftell返回36(文件大小为12x3 = 36字节)。 ftell 在执行 fgets first 的进程中仍然返回 3(第一行结束)。
所以下次任何进程调用fgets时,它都会返回一个EOF
共享内存区域mem 用作“数组”,其中第 1 到第 12 个元素包含 12 个进程的 PID,第 0 个元素用作索引来决定哪个进程将进入最外层的if 块。
这是导致问题的 sn-p -
while(mem[0] > 0)
{
printf("(%u) pos = %ld\n", curr_pid, ftell(fp));
// only the process whose PID matches the value in
// mem[mem[0]] can enter
if(curr_pid == mem[mem[0]])
{
printf("\n\nprocess %u enters CS\n", curr_pid);
char instr[100];
printf("pos before read = %ld\n", ftell(fp));
if(fgets(instr, 100, fp) == NULL)
{
perror("fgets error or EOF");
//return 1;
}
printf("pos after read = %ld\n", ftell(fp));
instr[strlen(instr)-1] = 0;
printf("process %u executing command: %s, size = %lu\n", curr_pid, instr, strlen(instr));
/* execute instruction */
char *args[] = {instr, NULL};
pid_t exec_pid = fork();
if(exec_pid == -1)
{
perror("fork error");
}
else if(exec_pid == 0) // child execs
{
execvp(instr, args);
perror("execvp error");
return 1;
}
printf("process %u leaving CS\n", curr_pid);
sleep(5);
mem[0]--; // alow next process to enter and read
}
sleep(1);
}
这里
(FILE *) fp是指向instructions.txt文件的文件指针(int *) mem是附加到所有 12 个进程的共享内存mem[0]是在mem中找到要选择进入if块的进程的PID(即mem[mem[0]]包含PIDmem[0]th 进程(pid_t) curr_pid为每个进程存储自己的PID
本质上,只有一个进程进入最外层的if 块,而其他进程通过循环“等待”直到轮到它们
【问题讨论】:
标签: c linux file-io synchronization