[英]Ordinary pipeline for inter process communication
我正在學習在Linux中使用普通管道進行父子進程之間通信的方法。 基本任務只是將消息從父進程發送到子進程,然后子進程進行一些轉換並將結果傳遞回父進程。 我顯示的結果是一些隨機字符,如 。 我已經考慮了很長時間了,但仍然找不到錯誤。 謝謝你的幫助。
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#define READ_END 0
#define WRITE_END 1
void convert(char* str);
int main(int argc, char *argv[]){
int pid; /* Process ID */
int status;
char *input;
char *read_msg_c;
char *read_msg_p;
int pfd1[2], pfd2[2];
if (argc !=2){/* argc should be 2 for correct execution */
/* We print argv[0] assuming it is the program name */
printf("Please provide the string for conversion \n");
exit(-1);
}
input = argv[1];
if(pipe(pfd1) < 0 || pipe(pfd2) < 0){
printf("Failed to create a pipe between parent and child \n");
exit(-1);
}
if((pid = fork()) < 0){ /* Fork the process */
printf("Fork error \n");
exit(-1);
}
else if(pid > 0){ /* Parent code */
close(pfd1[READ_END]);
close(pfd2[WRITE_END]);
printf("Process ID of the parent is %d. \n", getpid()); /* Print parent's process ID */
write(pfd1[WRITE_END],input,strlen(input)+1);
close(pfd1[WRITE_END]);
read(pfd2[READ_END],read_msg_p,strlen(input)+1);
printf("%s\n",read_msg_p);
close(pfd2[READ_END]);
}
else if(pid == 0){ /* Child code */
close(pfd1[WRITE_END]);
close(pfd2[READ_END]);
printf("Process ID of the child is %d. \n", getpid()); /* Print child's process ID */
read(pfd1[READ_END],read_msg_c, strlen(input)+1);
printf("Child: Reversed the case of the received string. \n");
write(pfd2[WRITE_END],read_msg_c,strlen(input)+1);
close(pfd1[READ_END]);
close(pfd2[WRITE_END]);
exit(0); /* Child exits */
}
}
void convert(char *str){
int i = 0;
while (str[i]){
if (isupper(str[i])){
str[i] = tolower(str[i]);
}
else if (islower(str[i])){
str[i] = toupper(str[i]);
}
i++;
}
}
您的主要錯誤是變量read_msg_p
和read_msg_c
是未初始化的指針。
將它們分成數組:
char read_msg_p[1024];
char read_msg_c[1024];
您似乎缺少了<stdio.h>
(但是您實際上不再需要<sys/types.h>
)。 您應該對讀和寫進行錯誤檢查; 為讀取分配空間后,您的讀取可能會使用不同的最大大小。 等等。
我通過查看編譯器警告發現了問題:
$ gcc -O3 -g -std=c99 -Wall -Wextra pipes-14420398.c -o pipes-14420398
pipes-14420398.c: In function ‘main’:
pipes-14420398.c:40:22: warning: ‘read_msg_p’ may be used uninitialized in this function [-Wuninitialized]
pipes-14420398.c:52:22: warning: ‘read_msg_c’ may be used uninitialized in this function [-Wuninitialized]
$
忽略行號; 在這些是剩下的唯一警告時,我已經對您的代碼進行了認真的攻擊。 但是有問題的行是read()
調用。
被黑的代碼的示例輸出正常工作。
$ ./pipes-14420398 string-to-convert
Process ID of the parent is 37327.
Process ID of the child is 37328.
Child read 18 bytes: <<string-to-convert>>
Parent read 18 bytes: <<string-to-convert>>
$
請注意,下面的代碼讀取18個字節(包括null),但不打印null(因為printf()
的nbytes-1
參數printf()
。
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#define READ_END 0
#define WRITE_END 1
int main(int argc, char *argv[])
{
int pid; /* Process ID */
char *input;
char read_msg_c[1024];
char read_msg_p[1024];
int pfd1[2], pfd2[2];
if (argc !=2){/* argc should be 2 for correct execution */
/* We print argv[0] assuming it is the program name */
fprintf(stderr, "Usage: %s string-to-convert\n", argv[0]);
exit(-1);
}
input = argv[1];
if(pipe(pfd1) < 0 || pipe(pfd2) < 0){
printf("Failed to create a pipe between parent and child \n");
exit(-1);
}
if((pid = fork()) < 0){ /* Fork the process */
printf("Fork error \n");
exit(-1);
}
else if(pid > 0){ /* Parent code */
close(pfd1[READ_END]);
close(pfd2[WRITE_END]);
printf("Process ID of the parent is %d. \n", getpid()); /* Print parent's process ID */
write(pfd1[WRITE_END], input, strlen(input)+1);
close(pfd1[WRITE_END]);
int nbytes = read(pfd2[READ_END], read_msg_p, sizeof(read_msg_p));
if (nbytes <= 0)
printf("Parent: read failed\n");
else
printf("Parent read %d bytes: <<%.*s>>\n", nbytes, nbytes-1, read_msg_p);
close(pfd2[READ_END]);
}
else if(pid == 0){ /* Child code */
close(pfd1[WRITE_END]);
close(pfd2[READ_END]);
printf("Process ID of the child is %d. \n", getpid()); /* Print child's process ID */
int nbytes = read(pfd1[READ_END], read_msg_c, sizeof(read_msg_c));
if (nbytes <= 0)
printf("Child: read failed\n");
else
{
printf("Child read %d bytes: <<%.*s>>\n", nbytes, nbytes-1, read_msg_c);
write(pfd2[WRITE_END], read_msg_c, nbytes);
}
close(pfd1[READ_END]);
close(pfd2[WRITE_END]);
exit(0); /* Child exits */
}
}
正如WhozCraig指出的那樣 ,還可以進行許多其他更改。 但是,這可以使工作正常進行。 您非常接近OK。
注意調試技巧:
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.