我只在终端输出中得到这个。我相信程序在fork()
调用时会卡住,但我不知道为什么。
程序的名称是q9:
prompt>$ ./q9 inputString
Parent: writing to pipe 'inputString'
我尝试通过以下方法解决此问题:
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <fcntl.h>
#include <sys/wait.h>
int main (int argc, char *argv[]) {
// parent RUN
if(argc == 1) {
printf("usage: q9 <string>\n");
return 0;
}
// create two way pipes
int parent_fds[2], child_fds[2];
// create strings to save too
char fromParent[100];
char fromChild[100];
// read:[0] - write:[1]
if (pipe(parent_fds) != 0 && pipe(child_fds) != 0) {
fprintf(stderr, "pipes failed!\n");
}
// close unused pipe end by parent
close(parent_fds[0]);
close(child_fds[1]);
close(child_fds[0]);
// write from terminal to parent pipe FOR child to read
printf("Parent: writing to pipe '%s'\n", argv[1]);
write(parent_fds[1], argv[1], strlen(argv[1]));
close(parent_fds[1]);
// fork() child process
int child = fork();
// NEVER GETS PASSED HERE :(
if (child < 0) {
fprintf(stderr, "fork failed!");
exit(1);
} else if (child == 0) {
printf("I reached the child :)");
// close unwanted pipe ends by child
close(child_fds[0]);
close(parent_fds[1]);
// read from parent pipe
int n = read(parent_fds[0], fromParent, 100);
fromParent[n] = 0;
printf("Child: reading from parent pipe '%s'\n", fromParent);
close(parent_fds[0]);
// Concatinate to what was read in
const char myText[14] = " (added this.)";
strcat(fromParent, myText);
write(child_fds[1], fromParent, strlen(fromParent));
close(child_fds[1]);
printf("Child: writing to pipe - '%s'\n", fromParent);
} else {
// read from child pipe
int n = read(child_fds[0], fromChild, 100);
fromChild[n] = 0;
printf("Parent: reading from pipe - '%s'\n", fromChild);
}
return 0;
}
存在几个问题,并且不能保证您的诊断消息会出现。确保以换行符结束消息。
下面的代码中还有其他多个清理操作。代码(仍然)不能确保写管道操作成功(之前失败)。它确实确保从管道读取的字符串不长于放置它们的缓冲区。它不能确保有足够的空间在子级中附加额外的信息。显示的代码在退出之前等待所有子进程完成。子级执行wait()
调用,但立即失败(子级不打印任何内容)并退出。父母等待孩子完成工作并报告有关情况,然后退出。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/wait.h>
#include <unistd.h>
int main(int argc, char *argv[])
{
if (argc == 1)
{
fprintf(stderr, "Usage: %s <string>\n", argv[0]);
return EXIT_FAILURE;
}
// create two pipes:
// - parent_fds used by parent to write to child
// - child_fds used by child to write to parent
int parent_fds[2], child_fds[2];
// read:[0] - write:[1]
if (pipe(parent_fds) != 0 || pipe(child_fds) != 0) /* || not && */
{
fprintf(stderr, "pipes failed!\n");
return EXIT_FAILURE;
}
// fork() child process
int child = fork();
if (child < 0)
{
fprintf(stderr, "fork failed!");
return EXIT_FAILURE;
}
else if (child == 0)
{
printf("%d: I reached the child :)\n", (int)getpid());
// close unwanted pipe ends by child
close(child_fds[0]);
close(parent_fds[1]);
// read from parent pipe
char fromParent[100];
int n = read(parent_fds[0], fromParent, sizeof(fromParent) - 1);
fromParent[n] = '\0';
printf("%d: Child: read from parent pipe '%s'\n", (int)getpid(), fromParent);
close(parent_fds[0]);
// Append to what was read in
strcat(fromParent, " (added this.)");
write(child_fds[1], fromParent, strlen(fromParent));
close(child_fds[1]);
printf("%d: Child: writing to pipe - '%s'\n", (int)getpid(), fromParent);
}
else
{
// close unwanted pipe ends by parent
close(parent_fds[0]);
close(child_fds[1]);
// write from terminal to parent pipe FOR child to read
printf("%d: Parent: writing to pipe '%s'\n", (int)getpid(), argv[1]);
write(parent_fds[1], argv[1], strlen(argv[1]));
close(parent_fds[1]);
// read from child pipe
char fromChild[100];
int n = read(child_fds[0], fromChild, sizeof(fromChild) - 1);
fromChild[n] = '\0';
close(child_fds[0]);
printf("%d: Parent: read from pipe - '%s'\n", (int)getpid(), fromChild);
}
int corpse;
int status;
while ((corpse = wait(&status)) > 0)
printf("%d: child PID %d exited with status 0x%.4X\n", (int)getpid(), corpse, status);
return EXIT_SUCCESS;
}
样本输出(源pipe43.c
,程序pipe43
):
$ pipe43 'Nobody expects the Spanish Inquisition!'
84543: Parent: writing to pipe 'Nobody expects the Spanish Inquisition!'
84544: I reached the child :)
84544: Child: read from parent pipe 'Nobody expects the Spanish Inquisition!'
84544: Child: writing to pipe - 'Nobody expects the Spanish Inquisition! (added this.)'
84543: Parent: read from pipe - 'Nobody expects the Spanish Inquisition! (added this.)'
84543: child PID 84544 exited with status 0x0000
$