我真的很难弄清楚父亲和孩子之间的沟通问题。当我运行主程序时,似乎什么也没发生。 我确实在网上搜索了解决方案,但到目前为止,没有任何帮助。 我知道我在这里发布了很多代码,但是从我的旧帖子中得知了同样的问题,人们让我一次又一次地阅读该人,但仍然,这里有些不正确,我不知道确切地知道什么。 我希望你们能帮助我
#include <stdio.h>
#include <stdlib.h> //for exit
#include <fcntl.h>
#include <errno.h>
#include <sys/wait.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h> //for sleep(),execvp()
#include <ctype.h>
#include <fcntl.h>
#define IN 0
#define OUT 1
#define SIZE 81
#define EXEC "./child"
int main(int argc, char * argv[])
{
int fd[2];
int fdr; // file descriptors
int i;
char result[3];
pid_t pid;
char charMatrix[SIZE] ={ 0 };
int matrix[9][9]={0};
if (argc < 2)
{
printf("No files added, abort program\n");
exit(EXIT_FAILURE);
}
if (pipe(fd) == -1)
{
printf("Pipe Failed");
return 1;
}
fdr = open(argv[1], O_RDONLY); // open files
if (fdr < 0)
{ //validation for error
perror("failed to open input or output files");
exit(EXIT_FAILURE);
}
char c;
charMatrix[81] = '\0';
i=0;
int j=0;
while (read(fdr, &c, 1)) // read/write a single char
{ // from/to the files
if (c != ' ' && c != '\n')
{
charMatrix[i++]=c-'0';
}
}
close(fdr); // close the file
int index=0; //convert to matrix
for (i = 0; i < 9; i++) { /* Iterate of each row */
for (j = 0; j < 9; j++) { /* In each row, go over each col element */
matrix[i][j]=charMatrix[index++];
}
}
for (i = 0; i < 9; i++) {// Iterate of each row
for (j = 0; j < 9; j++) { //In each row, go over each col element
printf("%d ", matrix[i][j]);// Print each row element
}
printf("\n");// Finish a row, start a new line
}
pid = fork();
if (pid < 0)
{
fputs("error in fork", stderr);
exit(EXIT_FAILURE);
}
//child
if(pid == 0)
{
close(fd[0]);
close(STDOUT_FILENO);
dup(fd[1]);
execl(EXEC, charMatrix, NULL);
}
//parent
else{
close(fd[1]);
close(STDIN_FILENO);
dup(fd[0]);
read(fd[0], &result, sizeof(result));
wait(NULL);
}
exit(EXIT_SUCCESS);
}
执行文件
#include <stdio.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdlib.h>
int main(int argc, char * argv[]){
int matrix[9][9];
char charMatrix[81];
char ans;
int i, j;
printf("got here");
read(0,&charMatrix,sizeof(charMatrix));
int index=0; //convert to matrix
for (i = 0; i < 9; i++) { /* Iterate of each row */
for (j = 0; j < 9; j++) { /* In each row, go over each col element */
matrix[i][j]=charMatrix[index++];
}
}
write(4, "a", sizeof(char));
for (i = 0; i < 9; i++) { /* Iterate of each row */
for (j = 0; j < 9; j++) { /* In each row, go over each col element */
printf("%d ", matrix[i][j]); /* Print each row element */
}
printf("\n"); /* Finish a row, start a new line */
}
exit(0);
}
在提出建议的解决方案之后,我尝试添加另一个孩子,但仍然弄错了。 这是代码以及如何解释的解释
dup2(pipe1[0], STDIN_FILENO); //makes the input( 0 in the stack) to the pipe1[0] which means point to its
close(pipe1[0]);
close(pipe1[1]); //closing before pointes
dup2(pipe2[1], STDOUT_FILENO); //makes the output (1 in the stack) to point pip1[1]
close(pipe2[0]);
close(pipe2[1]);//closing
execl(EXEC, EXEC, NULL);//exec
我曾尝试用新烟斗与另一个孩子做同样的事情,但没有成功。我将父亲pipe1接到第二个孩子的pipe3的答案
// --------------------------------------------- ---------------------- //
#define SIZE 81
#define EXEC "./child"
#define EXEC2 "./child2"
int main(int argc, char *argv[])
{
char charMatrix[SIZE] = { 0 };
int matrix[9][9] = { 0 };
char chilesStatus[3]={0};
if (argc != 2)
{
fprintf(stderr, "Usage: %s matrix file \n", argv[0]);
exit(EXIT_FAILURE);
}
int fdr = open(argv[1], O_RDONLY);
if (fdr < 0)
{
perror("failed to open input or output files");
exit(EXIT_FAILURE);
}
char c;
int k = 0;
while (read(fdr, &c, 1) == 1 && k < (int)sizeof(charMatrix))
{
if (c != ' ' && c != '\n')
charMatrix[k++] = c - '0';
}
close(fdr);
int index = 0;
for (int i = 0; i < 9; i++)
{
for (int j = 0; j < 9; j++)
matrix[i][j] = charMatrix[index++];
}
printf("Input matrix:\n");
for (int i = 0; i < 9; i++)
{
printf("P: ");
for (int j = 0; j < 9; j++)
printf(" %d", matrix[i][j]);
printf("\n");
}
fflush(stdout); // Making sure output is flushed even if it is going to a pipe
int pipe1[2];
int pipe2[2];
int pipe3[2];
int pipe4[2];
if (pipe(pipe1) == -1 || pipe(pipe2) == -1 || pipe(pipe3) == -1) //pipe validation
{
perror("Pipe failed");
exit(EXIT_FAILURE);
}
pid_t fChild = fork();
if (fChild < 0)
{
perror("Fork failed");
exit(EXIT_FAILURE);
}
if (fChild == 0)
{
dup2(pipe1[0], STDIN_FILENO);
close(pipe1[0]);
close(pipe1[1]);
dup2(pipe2[1], STDOUT_FILENO);
close(pipe2[0]);
close(pipe2[1]);
execl(EXEC, EXEC, NULL);
int errnum = errno;
fprintf(stderr, "Failed to execute '%s' (%d: %s)\n", EXEC, errnum, strerror(errnum));
exit(EXIT_FAILURE);
}
else
{
pid_t sChild = fork();
if(sChild==0)
{
dup2(pipe2[0], STDIN_FILENO);
close(pipe2[0]);
close(pipe2[1]);
dup2(pipe3[1], STDOUT_FILENO);
close(pipe3[0]);
close(pipe3[1]);
execl(EXEC2, EXEC2, NULL);
int errnum = errno;
fprintf(stderr, "Failed to execute '%s' (%d: %s)\n", EXEC, errnum, strerror(errnum));
exit(EXIT_FAILURE);
}
else
{
}
close(pipe2[0]);
close(pipe1[0]);
if (write(pipe1[1], charMatrix, sizeof(charMatrix)) != sizeof(charMatrix))
{
perror("failed to write to child");
exit(EXIT_FAILURE);
}
if (write(pipe1[2], charMatrix, sizeof(charMatrix)) != sizeof(charMatrix))
{
perror("failed to write to child");
exit(EXIT_FAILURE);
}
close(pipe1[1]);
close(pipe2[1]);
close(pipe3[1]);
char result[3];
int nbytes = read(pipe2[0], &result, sizeof(result));
int nbytes2 = read(pipe3[0], &result, sizeof(result));
if (nbytes <= 0 ||nbytes2 <= 0)
{
perror("Failed to read from pipe");
exit(EXIT_FAILURE);
}
close(pipe2[0]);
close(pipe3[0]);
int corpse;
int status;
while ((corpse = wait(&status)) > 0)
printf("Child %d exited with status 0x%.4X\n", corpse, status);
printf("Received '%.*s' from child\n", nbytes, result);
}
return(EXIT_SUCCESS);
}
答案 0 :(得分:0)
两个源文件-parent.c
和child.c
的主要修订版本。
parent.c
#include <errno.h>
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <unistd.h>
#define SIZE 81
#define EXEC "./child"
int main(int argc, char *argv[])
{
char charMatrix[SIZE] = { 0 };
int matrix[9][9] = { 0 };
if (argc != 2)
{
fprintf(stderr, "Usage: %s matrixfile\n", argv[0]);
exit(EXIT_FAILURE);
}
int fdr = open(argv[1], O_RDONLY);
if (fdr < 0)
{
perror("failed to open input or output files");
exit(EXIT_FAILURE);
}
char c;
int k = 0;
while (read(fdr, &c, 1) == 1 && k < (int)sizeof(charMatrix))
{
if (c != ' ' && c != '\n')
charMatrix[k++] = c - '0';
}
close(fdr);
int index = 0;
for (int i = 0; i < 9; i++)
{
for (int j = 0; j < 9; j++)
matrix[i][j] = charMatrix[index++];
}
printf("Input matrix:\n");
for (int i = 0; i < 9; i++)
{
printf("P: ");
for (int j = 0; j < 9; j++)
printf(" %d", matrix[i][j]);
printf("\n");
}
fflush(stdout); // Make sure output is flushed even it it is going to a pipe
int pipe1[2];
int pipe2[2];
if (pipe(pipe1) == -1 || pipe(pipe2) == -1)
{
perror("Pipe failed");
exit(EXIT_FAILURE);
}
pid_t pid = fork();
if (pid < 0)
{
perror("Fork failed");
exit(EXIT_FAILURE);
}
if (pid == 0)
{
dup2(pipe1[0], STDIN_FILENO);
close(pipe1[0]);
close(pipe1[1]);
dup2(pipe2[1], STDOUT_FILENO);
close(pipe2[0]);
close(pipe2[1]);
execl(EXEC, EXEC, NULL);
int errnum = errno;
fprintf(stderr, "Failed to execute '%s' (%d: %s)\n", EXEC, errnum, strerror(errnum));
exit(EXIT_FAILURE);
}
else
{
close(pipe1[0]);
if (write(pipe1[1], charMatrix, sizeof(charMatrix)) != sizeof(charMatrix))
{
perror("failed to write to child");
exit(EXIT_FAILURE);
}
close(pipe1[1]);
close(pipe2[1]);
char result[3];
int nbytes = read(pipe2[0], &result, sizeof(result));
if (nbytes <= 0)
{
perror("Failed to read from pipe");
exit(EXIT_FAILURE);
}
close(pipe2[0]);
int corpse;
int status;
while ((corpse = wait(&status)) > 0)
printf("Child %d exited with status 0x%.4X\n", corpse, status);
printf("Received '%.*s' from child\n", nbytes, result);
}
return(EXIT_SUCCESS);
}
child.c
#include <stdio.h>
#include <sys/stat.h>
#include <unistd.h>
int main(void)
{
int matrix[9][9];
char charMatrix[81];
fprintf(stderr, "got here\n");
int nbytes = read(STDIN_FILENO, charMatrix, sizeof(charMatrix));
fprintf(stderr, "got %d bytes\n", nbytes);
int index = 0;
for (int i = 0; i < 9; i++)
{
for (int j = 0; j < 9; j++)
matrix[i][j] = charMatrix[index++];
}
write(STDOUT_FILENO, "a", sizeof(char));
fprintf(stderr, "Ack written to parent\n");
fprintf(stderr, "Child matrix:\n");
for (int i = 0; i < 9; i++)
{
fprintf(stderr, "C: ");
for (int j = 0; j < 9; j++)
fprintf(stderr, " %d", matrix[i][j]);
fprintf(stderr, "\n");
}
return(0);
}
6 9 4 5 3 2 6 1 2
2 7 1 5 1 9 1 5 7
1 5 3 1 6 6 7 1 8
6 3 2 4 2 8 9 5 2
2 2 7 9 4 1 3 7 7
3 1 7 8 6 5 5 2 4
6 5 9 1 6 7 7 8 7
5 4 9 5 1 8 9 2 1
3 5 6 8 3 6 9 6 9
$ ./parent random.matrix
Input matrix:
P: 6 9 4 5 3 2 6 1 2
P: 2 7 1 5 1 9 1 5 7
P: 1 5 3 1 6 6 7 1 8
P: 6 3 2 4 2 8 9 5 2
P: 2 2 7 9 4 1 3 7 7
P: 3 1 7 8 6 5 5 2 4
P: 6 5 9 1 6 7 7 8 7
P: 5 4 9 5 1 8 9 2 1
P: 3 5 6 8 3 6 9 6 9
got here
got 81 bytes
Ack written to parent
Child matrix:
C: 6 9 4 5 3 2 6 1 2
C: 2 7 1 5 1 9 1 5 7
C: 1 5 3 1 6 6 7 1 8
C: 6 3 2 4 2 8 9 5 2
C: 2 2 7 9 4 1 3 7 7
C: 3 1 7 8 6 5 5 2 4
C: 6 5 9 1 6 7 7 8 7
C: 5 4 9 5 1 8 9 2 1
C: 3 5 6 8 3 6 9 6 9
Child 9498 exited with status 0x0000
Received 'a' from child
$
不清楚为什么要定义,但不要在修订后的代码中使用pipe4
。我认为这样会更容易。当您从1到2进程移动时,带有数字后缀的命名约定变得令人讨厌(但是下面的代码仍然使用它)。最好考虑数组。我修改了子进程以发送更大的消息,并修改了父代码以接收它们-它可以更好地识别正在发生的事情。孩子们的输出可以交错。
我不清楚您如何设想管道的三重奏。使用四个管道,管道1和2连接到子节点1;管道1和2连接到子节点1。管道3和4通往子代2。奇数管道将信息传递给子代。偶数管道传达孩子的信息。 close()
有很多电话。
pipe47.c
/* SO 5609-3694 */
#include <errno.h>
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <unistd.h>
#define SIZE 81
#define EXEC1 "./child2"
#define EXEC2 "./child2"
int main(int argc, char *argv[])
{
char charMatrix[SIZE] = { 0 };
int matrix[9][9] = { 0 };
if (argc != 2)
{
fprintf(stderr, "Usage: %s matrix file \n", argv[0]);
exit(EXIT_FAILURE);
}
int fdr = open(argv[1], O_RDONLY);
if (fdr < 0)
{
perror("failed to open input or output files");
exit(EXIT_FAILURE);
}
char c;
int k = 0;
while (read(fdr, &c, 1) == 1 && k < (int)sizeof(charMatrix))
{
if (c != ' ' && c != '\n')
charMatrix[k++] = c - '0';
}
close(fdr);
int index = 0;
for (int i = 0; i < 9; i++)
{
for (int j = 0; j < 9; j++)
matrix[i][j] = charMatrix[index++];
}
printf("Input matrix:\n");
for (int i = 0; i < 9; i++)
{
printf("P: ");
for (int j = 0; j < 9; j++)
printf(" %d", matrix[i][j]);
printf("\n");
}
fflush(stdout); // Making sure output is flushed even if it is going to a pipe
int pipe1[2];
int pipe2[2];
int pipe3[2];
int pipe4[2];
if (pipe(pipe1) == -1 || pipe(pipe2) == -1 || pipe(pipe3) == -1 || pipe(pipe4) == -1) // pipe validation
{
perror("Pipe failed");
exit(EXIT_FAILURE);
}
pid_t fChild = fork();
if (fChild < 0)
{
perror("Fork failed (child 1)");
exit(EXIT_FAILURE);
}
if (fChild == 0)
{
dup2(pipe1[0], STDIN_FILENO);
dup2(pipe2[1], STDOUT_FILENO);
close(pipe1[0]);
close(pipe1[1]);
close(pipe2[0]);
close(pipe2[1]);
close(pipe3[0]);
close(pipe3[1]);
close(pipe4[0]);
close(pipe4[1]);
execl(EXEC1, EXEC1, NULL);
int errnum = errno;
fprintf(stderr, "Failed to execute '%s' (1) (%d: %s)\n", EXEC1, errnum, strerror(errnum));
exit(EXIT_FAILURE);
}
pid_t sChild = fork();
if (sChild < 0)
{
perror("Fork failed (child 2)");
exit(EXIT_FAILURE);
}
if (sChild == 0)
{
dup2(pipe3[0], STDIN_FILENO);
dup2(pipe4[1], STDOUT_FILENO);
close(pipe1[0]);
close(pipe1[1]);
close(pipe2[0]);
close(pipe2[1]);
close(pipe3[0]);
close(pipe3[1]);
close(pipe4[0]);
close(pipe4[1]);
execl(EXEC2, EXEC2, NULL);
int errnum = errno;
fprintf(stderr, "Failed to execute '%s' (2) (%d: %s)\n", EXEC2, errnum, strerror(errnum));
exit(EXIT_FAILURE);
}
close(pipe1[0]);
close(pipe2[1]);
close(pipe3[0]);
close(pipe4[1]);
if (write(pipe1[1], charMatrix, sizeof(charMatrix)) != sizeof(charMatrix))
{
perror("failed to write to child 1");
exit(EXIT_FAILURE);
}
close(pipe1[1]);
if (write(pipe3[1], charMatrix, sizeof(charMatrix)) != sizeof(charMatrix))
{
perror("failed to write to child 2");
exit(EXIT_FAILURE);
}
close(pipe3[1]);
char result1[64];
int nbytes1 = read(pipe2[0], &result1, sizeof(result1));
close(pipe2[0]);
if (nbytes1 <= 0)
{
perror("Failed to read from child 1");
exit(EXIT_FAILURE);
}
char result2[64];
int nbytes2 = read(pipe4[0], &result2, sizeof(result2));
close(pipe4[0]);
if (nbytes2 <= 0)
{
perror("Failed to read from child 2");
exit(EXIT_FAILURE);
}
int corpse;
int status;
while ((corpse = wait(&status)) > 0)
printf("Child %d exited with status 0x%.4X\n", corpse, status);
printf("Received '%.*s' from child 1\n", nbytes1, result1);
printf("Received '%.*s' from child 2\n", nbytes2, result2);
return(EXIT_SUCCESS);
}
child2.c
/* SO 5609-3694 */
#include <stdio.h>
#include <sys/stat.h>
#include <unistd.h>
int main(void)
{
int matrix[9][9];
char charMatrix[81];
int pid = getpid();
fprintf(stderr, "PID %d: got here\n", pid);
int nbytes = read(STDIN_FILENO, charMatrix, sizeof(charMatrix));
fprintf(stderr, "PID %d: got %d bytes\n", pid, nbytes);
int index = 0;
for (int i = 0; i < 9; i++)
{
for (int j = 0; j < 9; j++)
matrix[i][j] = charMatrix[index++];
}
//write(STDOUT_FILENO, "a", sizeof(char));
printf("PID %d: message received", pid);
fprintf(stderr, "PID %d: Ack written to parent\n", pid);
fprintf(stderr, "PID %d: Child matrix:\n", pid);
for (int i = 0; i < 9; i++)
{
fprintf(stderr, "PID %d: ", pid);
for (int j = 0; j < 9; j++)
fprintf(stderr, " %d", matrix[i][j]);
fprintf(stderr, "\n");
}
return(0);
}
请注意,两个子项的输出相互穿插。可以设计一种避免这种情况的机制。
$ ./pipe47 random.matrix
Input matrix:
P: 6 9 4 5 3 2 6 1 2
P: 2 7 1 5 1 9 1 5 7
P: 1 5 3 1 6 6 7 1 8
P: 6 3 2 4 2 8 9 5 2
P: 2 2 7 9 4 1 3 7 7
P: 3 1 7 8 6 5 5 2 4
P: 6 5 9 1 6 7 7 8 7
P: 5 4 9 5 1 8 9 2 1
P: 3 5 6 8 3 6 9 6 9
PID 11903: got here
PID 11903: got 81 bytes
PID 11903: Ack written to parent
PID 11903: Child matrix:
PID 11903: 6 9 4 5 3 2 6 1 2
PID 11903: 2 7 1 5 1PID 11904: got here
9 1 5 7
PID 11903: 1 5 3 1PID 11904: got 81 bytes
6 6 7 1 8
PID 11903: 6 3 2PID 11904: Ack written to parent
4PID 11904: Child matrix:
2PID 11904: 8 6 9 9 5 4 2 5
3PID 11903: 2 2 6 2 1 7 2 9 4 1
3PID 11904: 7 2 7 7
1PID 11903: 5 3 1 1 9 7 1 8 5 6 7 5
5PID 11904: 2 1 4 5
3PID 11903: 1 6 6 5 6 9 7 1 1 6 8 7
7PID 11904: 8 6 7 3
2PID 11903: 4 5 2 4 8 9 9 5 5 1 2 8
9PID 11904: 2 2 1 2
7PID 11903: 9 3 4 5 1 6 3 8 7 3 7 6
9PID 11904: 6 3 9 1
7 8 6 5 5 2 4
PID 11904: 6 5 9 1 6 7 7 8 7
PID 11904: 5 4 9 5 1 8 9 2 1
PID 11904: 3 5 6 8 3 6 9 6 9
Child 11903 exited with status 0x0000
Child 11904 exited with status 0x0000
Received 'PID 11903: message received' from child 1
Received 'PID 11904: message received' from child 2
$