c中的管道写入和读取错误:程序冻结
pipe write and read error in c: program freeze up
我是运行fork
的多进程c代码,使用管道让子进程与父进程通信
但是当运行 write
部分时,假设13个过程中有3个成功,然后程序就被冻结了,也就是说,它不能再继续了,既没有segmentation fault
,也没有停止。
我无法使用 gdb
进行调试,即使使用 set follow-fork-mode child
或 Valgrind
,程序也被冻结了。
代码如下:
- 函数:
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <string.h>
#include <unistd.h>
struct IntArrLen {
int length;
int index;
int* arr;
};
struct IntArrLenArr {
struct IntArrLen *intArrLen;
int max_index;
int length;
};
void write_check(int fd, void *buffer, size_t len){
char *p = buffer;
while(len > 0){
size_t wlen = write(fd, p, len);
if(wlen <= 0){
printf("Error when writing.\n");
exit(0);
}
p += wlen;
len -= wlen;
}
}
void write_intArrLen(int fd, struct IntArrLen *p){
write_check(fd, &p->index, sizeof(p->index));
write_check(fd, &p->length, sizeof(p->length));
write_check(fd, p->arr, p->length * sizeof(*p->arr));
}
void write_intArrLenArr(int fd, struct IntArrLenArr *p){
write_check(fd, &p->max_index, sizeof(p->max_index));
write_check(fd, &p->length, sizeof(p->length));
int i;
for(i=0; i<p->length; i++)
write_intArrLen(fd, &p->intArrLen[i]);
}
void read_check(int fd, void *buffer, size_t len){
char *p = buffer;
while (len > 0){
size_t rlen = read(fd, p, len);
if(rlen <= 0){
printf("Error when reading.\n");
exit(0);
}
p += rlen;
len -= rlen;
}
}
void read_intArrLen(int fd, struct IntArrLen *p){
read_check(fd, &p->index, sizeof(p->index));
read_check(fd, &p->length, sizeof(p->length));
p->arr = malloc(p->length * sizeof(*p->arr));
if(!p->arr){
printf("ran out of memory.\n");
exit(0);
}
read_check(fd, p->arr, p->length * sizeof(*p->arr));
}
void read_intArrLenArr(int fd, struct IntArrLenArr *p){
read_check(fd, &p->max_index, sizeof(p->max_index));
read_check(fd, &p->length, sizeof(p->length));
p->intArrLen = malloc(p->length * sizeof(*p->intArrLen));
if(!p->intArrLen){
printf("ran out of memoty.\n");
exit(0);
}
int i;
for(i=0; i<p->length; i++)
read_intArrLen(fd, &p->intArrLen[i]);
}
struct IntArrLenArr getRes(int num1, int num2){
struct IntArrLenArr ret;
ret.length = num1;
ret.max_index = num2;
ret.intArrLen = malloc(sizeof(struct IntArrLen) * num1);
int i, j;
for(i=0; i<num1; i++){
ret.intArrLen[i].length = num1;
ret.intArrLen[i].index = num2;
ret.intArrLen[i].arr = malloc(sizeof(int) * num1);
for(j=0; j<num2; j++){
ret.intArrLen[i].arr[j] = j;
}
}
return ret;
}
int main(void){
struct IntArrLenArr res;
res.max_index = 0;
res.length = 0;
int i;
pid_t child_pid;
int *fds = malloc(sizeof(int) * 13 * 2);
for(i=0; i<13; i++){
if(pipe(fds + i*2) <0)
exit(0);
}
for(i=0; i<13; i++){
//fflush(NULL);
child_pid =fork();
if(child_pid == 0){
close(fds[i*2]);
res = getRes(20, 3000000); // 300,000 works but not with 3000,000
if(res.length != 0){
printf("-----------%d\n", i);
write_intArrLenArr(fds[i*2+1], &res);
printf("+++++++++++%d\n", i);
}
close(fds[i*2+1]);
exit(0);
}else if(child_pid == -1){
printf("fork error\n");
exit(0);
}
}
for(i=0; i<13; i++){
close(fds[i*2+1]);
read_intArrLenArr(fds[i*2], &res);
printf(".................%d\n", i);
if (res.length > 0){
printf("do something\n");
}
}
return 1;
}
res
像这样:
res -> length: 20
-> max_index: 458965845
-> IntArrLen: -> IntArrLen[0] -> length: 125465
-> index: 45687987
-> int * arr: 123,1565,48987,45879,... // 125465 numbers
-> IntArrLen[1] -> length: 5465798956
-> index: 34579999
-> int * arr: 78123,1565,48987,45879,... // 5465798956 numbers
-> IntArrLen[2] -> length: 5465798956
-> ....
-> ...
谁能帮我找出这里出了什么问题?或者有没有其他方法可以以某种方式调试代码?非常感谢!!
我从问题中的代码(源文件 pipe53.c
编译为可执行文件 pipe53
)中提取了这段代码:
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
struct IntArrLen
{
int length;
int index;
int *arr;
};
struct IntArrLenArr
{
struct IntArrLen *intArrLen;
int max_index;
int length;
};
static size_t bytes_allocated = 0;
struct IntArrLenArr getRes(int num1, int num2);
void read_check(int fd, void *buffer, size_t len);
void read_intArrLen(int fd, struct IntArrLen *p);
void read_intArrLenArr(int fd, struct IntArrLenArr *p);
void write_check(int fd, void *buffer, size_t len);
void write_intArrLen(int fd, struct IntArrLen *p);
void write_intArrLenArr(int fd, struct IntArrLenArr *p);
static void fd_close(int fd)
{
close(fd);
//fprintf(stderr, "%d: closing %d\n", (int)getpid(), fd);
}
static void report_memory_used(void)
{
fprintf(stderr, "%d: bytes allocated = %zu\n", (int)getpid(), bytes_allocated);
}
static void *memory_allocator(size_t nbytes)
{
void *vp = malloc(nbytes);
bytes_allocated += nbytes;
report_memory_used(); // Dire straights!
return vp;
}
void write_check(int fd, void *buffer, size_t len)
{
char *p = buffer;
fprintf(stderr, "%d: writing %zu bytes to fd %d\n",
(int)getpid(), len, fd);
while (len > 0)
{
ssize_t wlen = write(fd, p, len);
if (wlen <= 0)
{
fprintf(stderr, "%d: Error when writing fd = %d.\n",
(int)getpid(), fd);
exit(0);
}
p += wlen;
len -= wlen;
}
}
void write_intArrLen(int fd, struct IntArrLen *p)
{
write_check(fd, &p->index, sizeof(p->index));
write_check(fd, &p->length, sizeof(p->length));
write_check(fd, p->arr, p->length * sizeof(*p->arr));
}
void write_intArrLenArr(int fd, struct IntArrLenArr *p)
{
write_check(fd, &p->max_index, sizeof(p->max_index));
write_check(fd, &p->length, sizeof(p->length));
for (int i = 0; i < p->length; i++)
write_intArrLen(fd, &p->intArrLen[i]);
}
void read_check(int fd, void *buffer, size_t len)
{
char *p = buffer;
while (len > 0)
{
ssize_t rlen = read(fd, p, len);
if (rlen < 0)
{
fprintf(stderr, "%d: Error %d (%s) when reading fd = %d.\n",
(int)getpid(), errno, strerror(errno), fd);
exit(0);
}
if (rlen == 0)
{
fprintf(stderr, "%d: Premature EOF when reading fd = %d.\n",
(int)getpid(), fd);
break;
}
p += rlen;
len -= rlen;
}
}
void read_intArrLen(int fd, struct IntArrLen *p)
{
read_check(fd, &p->index, sizeof(p->index));
read_check(fd, &p->length, sizeof(p->length));
p->arr = memory_allocator(p->length * sizeof(*p->arr));
if (!p->arr)
{
printf("ran out of memory.\n");
fprintf(stderr, "%d: ran out of memory (%zu bytes requested)\n",
(int)getpid(), p->length * sizeof(*p->arr));
exit(EXIT_FAILURE);
}
read_check(fd, p->arr, p->length * sizeof(*p->arr));
}
void read_intArrLenArr(int fd, struct IntArrLenArr *p)
{
read_check(fd, &p->max_index, sizeof(p->max_index));
read_check(fd, &p->length, sizeof(p->length));
p->intArrLen = memory_allocator(p->length * sizeof(*p->intArrLen));
if (!p->intArrLen)
{
fprintf(stderr, "%d: ran out of memory (%zu bytes requested)\n",
(int)getpid(), p->length * sizeof(*p->intArrLen));
exit(EXIT_FAILURE);
}
for (int i = 0; i < p->length; i++)
read_intArrLen(fd, &p->intArrLen[i]);
}
struct IntArrLenArr getRes(int num1, int num2)
{
struct IntArrLenArr ret;
ret.length = num1;
ret.max_index = num2;
ret.intArrLen = memory_allocator(sizeof(struct IntArrLen) * num1);
if (ret.intArrLen == NULL)
{
fprintf(stderr, "%d: failed to allocate %zu bytes of memory\n",
(int)getpid(), sizeof(struct IntArrLen) * num1);
exit(EXIT_FAILURE);
}
for (int i = 0; i < num1; i++)
{
ret.intArrLen[i].length = num1;
ret.intArrLen[i].index = num2;
ret.intArrLen[i].arr = memory_allocator(sizeof(int) * num1);
if (ret.intArrLen[i].arr == NULL)
{
fprintf(stderr, "%d: failed to allocate %zu bytes of memory\n",
(int)getpid(), sizeof(int) * num1);
exit(EXIT_FAILURE);
}
for (int j = 0; j < num2; j++)
{
ret.intArrLen[i].arr[j] = j;
}
}
return ret;
}
int main(void)
{
struct IntArrLenArr res;
res.max_index = 0;
res.length = 0;
atexit(report_memory_used);
printf("Parent process: %d\n", (int)getpid());
int *fds = memory_allocator(sizeof(int) * 13 * 2);
for (int i = 0; i < 13; i++)
{
if (pipe(fds + i * 2) < 0)
{
fprintf(stderr, "failed to create pipe %d\n", i);
exit(EXIT_FAILURE);
}
}
for (int i = 0; i < 13; i++)
{
pid_t child_pid = fork();
if (child_pid == 0)
{
printf("%d: Child process: %d - pipe [%d,%d]\n",
(int)getpid(), i, fds[i * 2 + 0], fds[i * 2 + 1]);
for (int j = 0; j < 13; j++)
{
fd_close(fds[j * 2 + 0]);
if (i != j)
fd_close(fds[j * 2 + 1]);
}
//res = getRes(20, 3000000); // 300,000 works but not with 3000,000
res = getRes(20, 300000); // 300,000 works but not with 3000,000
report_memory_used();
if (res.length != 0)
{
printf("-----------%d\n", i);
write_intArrLenArr(fds[i * 2 + 1], &res);
printf("+++++++++++%d\n", i);
}
fd_close(fds[i * 2 + 1]);
exit(0);
}
else if (child_pid == -1)
{
fprintf(stderr, "fork error\n");
exit(EXIT_FAILURE);
}
else
{
fprintf(stderr, "%d: launched child %d\n", (int)getpid(), (int)child_pid);
}
}
for (int i = 0; i < 13; i++)
{
fd_close(fds[i * 2 + 1]);
read_intArrLenArr(fds[i * 2 + 0], &res);
printf(".................%d\n", i);
if (res.length > 0)
{
printf("do something\n");
}
fd_close(fds[i] * 2 + 0);
}
free(fds);
return 0;
}
我从 运行 它(在 MacBook Pro 上)得到的输出示例是:
$ ./pipe53 2>&1 | cat # I actually pipe the output to "so | pbcopy" …
23380: bytes allocated = 104
23380: launched child 23383
23380: launched child 23384
23383: bytes allocated = 424
23383: bytes allocated = 504
23380: launched child 23385
23384: bytes allocated = 424
23384: bytes allocated = 504
23380: launched child 23386
23385: bytes allocated = 424
23385: bytes allocated = 504
23380: launched child 23387
23386: bytes allocated = 424
23386: bytes allocated = 504
23380: launched child 23388
23387: bytes allocated = 424
23387: bytes allocated = 504
23388: bytes allocated = 424
23388: bytes allocated = 504
23380: launched child 23389
23380: launched child 23390
23389: bytes allocated = 424
23389: bytes allocated = 504
23380: launched child 23391
23390: bytes allocated = 424
23390: bytes allocated = 504
23380: launched child 23392
23391: bytes allocated = 424
23391: bytes allocated = 504
23380: launched child 23393
23392: bytes allocated = 424
23392: bytes allocated = 504
23380: launched child 23394
23393: bytes allocated = 424
23393: bytes allocated = 504
23380: launched child 23395
23394: bytes allocated = 424
23394: bytes allocated = 504
23380: Premature EOF when reading fd = 3.
23380: Premature EOF when reading fd = 3.
23395: bytes allocated = 424
23395: bytes allocated = 504
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 5.
23380: Premature EOF when reading fd = 5.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 7.
23380: Premature EOF when reading fd = 7.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 9.
23380: Premature EOF when reading fd = 9.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 11.
23380: Premature EOF when reading fd = 11.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 13.
23380: Premature EOF when reading fd = 13.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 15.
23380: Premature EOF when reading fd = 15.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 17.
23380: Premature EOF when reading fd = 17.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 19.
23380: Premature EOF when reading fd = 19.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 21.
23380: Premature EOF when reading fd = 21.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 23.
23380: Premature EOF when reading fd = 23.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 25.
23380: Premature EOF when reading fd = 25.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 27.
23380: Premature EOF when reading fd = 27.
23380: bytes allocated = 104
23380: bytes allocated = 104
Parent process: 23380
.................0
.................1
.................2
.................3
.................4
.................5
.................6
.................7
.................8
.................9
.................10
.................11
.................12
AFAICT,getRes()
函数(大小为 300,000 和 3,000,000)未触发子进程写入的任何内容。
请注意在调试消息中谨慎使用标识 PID。
您需要修改getRes()
,以便将数据写入父进程。
我是运行fork
的多进程c代码,使用管道让子进程与父进程通信
但是当运行 write
部分时,假设13个过程中有3个成功,然后程序就被冻结了,也就是说,它不能再继续了,既没有segmentation fault
,也没有停止。
我无法使用 gdb
进行调试,即使使用 set follow-fork-mode child
或 Valgrind
,程序也被冻结了。
代码如下:
- 函数:
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <string.h>
#include <unistd.h>
struct IntArrLen {
int length;
int index;
int* arr;
};
struct IntArrLenArr {
struct IntArrLen *intArrLen;
int max_index;
int length;
};
void write_check(int fd, void *buffer, size_t len){
char *p = buffer;
while(len > 0){
size_t wlen = write(fd, p, len);
if(wlen <= 0){
printf("Error when writing.\n");
exit(0);
}
p += wlen;
len -= wlen;
}
}
void write_intArrLen(int fd, struct IntArrLen *p){
write_check(fd, &p->index, sizeof(p->index));
write_check(fd, &p->length, sizeof(p->length));
write_check(fd, p->arr, p->length * sizeof(*p->arr));
}
void write_intArrLenArr(int fd, struct IntArrLenArr *p){
write_check(fd, &p->max_index, sizeof(p->max_index));
write_check(fd, &p->length, sizeof(p->length));
int i;
for(i=0; i<p->length; i++)
write_intArrLen(fd, &p->intArrLen[i]);
}
void read_check(int fd, void *buffer, size_t len){
char *p = buffer;
while (len > 0){
size_t rlen = read(fd, p, len);
if(rlen <= 0){
printf("Error when reading.\n");
exit(0);
}
p += rlen;
len -= rlen;
}
}
void read_intArrLen(int fd, struct IntArrLen *p){
read_check(fd, &p->index, sizeof(p->index));
read_check(fd, &p->length, sizeof(p->length));
p->arr = malloc(p->length * sizeof(*p->arr));
if(!p->arr){
printf("ran out of memory.\n");
exit(0);
}
read_check(fd, p->arr, p->length * sizeof(*p->arr));
}
void read_intArrLenArr(int fd, struct IntArrLenArr *p){
read_check(fd, &p->max_index, sizeof(p->max_index));
read_check(fd, &p->length, sizeof(p->length));
p->intArrLen = malloc(p->length * sizeof(*p->intArrLen));
if(!p->intArrLen){
printf("ran out of memoty.\n");
exit(0);
}
int i;
for(i=0; i<p->length; i++)
read_intArrLen(fd, &p->intArrLen[i]);
}
struct IntArrLenArr getRes(int num1, int num2){
struct IntArrLenArr ret;
ret.length = num1;
ret.max_index = num2;
ret.intArrLen = malloc(sizeof(struct IntArrLen) * num1);
int i, j;
for(i=0; i<num1; i++){
ret.intArrLen[i].length = num1;
ret.intArrLen[i].index = num2;
ret.intArrLen[i].arr = malloc(sizeof(int) * num1);
for(j=0; j<num2; j++){
ret.intArrLen[i].arr[j] = j;
}
}
return ret;
}
int main(void){
struct IntArrLenArr res;
res.max_index = 0;
res.length = 0;
int i;
pid_t child_pid;
int *fds = malloc(sizeof(int) * 13 * 2);
for(i=0; i<13; i++){
if(pipe(fds + i*2) <0)
exit(0);
}
for(i=0; i<13; i++){
//fflush(NULL);
child_pid =fork();
if(child_pid == 0){
close(fds[i*2]);
res = getRes(20, 3000000); // 300,000 works but not with 3000,000
if(res.length != 0){
printf("-----------%d\n", i);
write_intArrLenArr(fds[i*2+1], &res);
printf("+++++++++++%d\n", i);
}
close(fds[i*2+1]);
exit(0);
}else if(child_pid == -1){
printf("fork error\n");
exit(0);
}
}
for(i=0; i<13; i++){
close(fds[i*2+1]);
read_intArrLenArr(fds[i*2], &res);
printf(".................%d\n", i);
if (res.length > 0){
printf("do something\n");
}
}
return 1;
}
res
像这样:
res -> length: 20
-> max_index: 458965845
-> IntArrLen: -> IntArrLen[0] -> length: 125465
-> index: 45687987
-> int * arr: 123,1565,48987,45879,... // 125465 numbers
-> IntArrLen[1] -> length: 5465798956
-> index: 34579999
-> int * arr: 78123,1565,48987,45879,... // 5465798956 numbers
-> IntArrLen[2] -> length: 5465798956
-> ....
-> ...
谁能帮我找出这里出了什么问题?或者有没有其他方法可以以某种方式调试代码?非常感谢!!
我从问题中的代码(源文件 pipe53.c
编译为可执行文件 pipe53
)中提取了这段代码:
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
struct IntArrLen
{
int length;
int index;
int *arr;
};
struct IntArrLenArr
{
struct IntArrLen *intArrLen;
int max_index;
int length;
};
static size_t bytes_allocated = 0;
struct IntArrLenArr getRes(int num1, int num2);
void read_check(int fd, void *buffer, size_t len);
void read_intArrLen(int fd, struct IntArrLen *p);
void read_intArrLenArr(int fd, struct IntArrLenArr *p);
void write_check(int fd, void *buffer, size_t len);
void write_intArrLen(int fd, struct IntArrLen *p);
void write_intArrLenArr(int fd, struct IntArrLenArr *p);
static void fd_close(int fd)
{
close(fd);
//fprintf(stderr, "%d: closing %d\n", (int)getpid(), fd);
}
static void report_memory_used(void)
{
fprintf(stderr, "%d: bytes allocated = %zu\n", (int)getpid(), bytes_allocated);
}
static void *memory_allocator(size_t nbytes)
{
void *vp = malloc(nbytes);
bytes_allocated += nbytes;
report_memory_used(); // Dire straights!
return vp;
}
void write_check(int fd, void *buffer, size_t len)
{
char *p = buffer;
fprintf(stderr, "%d: writing %zu bytes to fd %d\n",
(int)getpid(), len, fd);
while (len > 0)
{
ssize_t wlen = write(fd, p, len);
if (wlen <= 0)
{
fprintf(stderr, "%d: Error when writing fd = %d.\n",
(int)getpid(), fd);
exit(0);
}
p += wlen;
len -= wlen;
}
}
void write_intArrLen(int fd, struct IntArrLen *p)
{
write_check(fd, &p->index, sizeof(p->index));
write_check(fd, &p->length, sizeof(p->length));
write_check(fd, p->arr, p->length * sizeof(*p->arr));
}
void write_intArrLenArr(int fd, struct IntArrLenArr *p)
{
write_check(fd, &p->max_index, sizeof(p->max_index));
write_check(fd, &p->length, sizeof(p->length));
for (int i = 0; i < p->length; i++)
write_intArrLen(fd, &p->intArrLen[i]);
}
void read_check(int fd, void *buffer, size_t len)
{
char *p = buffer;
while (len > 0)
{
ssize_t rlen = read(fd, p, len);
if (rlen < 0)
{
fprintf(stderr, "%d: Error %d (%s) when reading fd = %d.\n",
(int)getpid(), errno, strerror(errno), fd);
exit(0);
}
if (rlen == 0)
{
fprintf(stderr, "%d: Premature EOF when reading fd = %d.\n",
(int)getpid(), fd);
break;
}
p += rlen;
len -= rlen;
}
}
void read_intArrLen(int fd, struct IntArrLen *p)
{
read_check(fd, &p->index, sizeof(p->index));
read_check(fd, &p->length, sizeof(p->length));
p->arr = memory_allocator(p->length * sizeof(*p->arr));
if (!p->arr)
{
printf("ran out of memory.\n");
fprintf(stderr, "%d: ran out of memory (%zu bytes requested)\n",
(int)getpid(), p->length * sizeof(*p->arr));
exit(EXIT_FAILURE);
}
read_check(fd, p->arr, p->length * sizeof(*p->arr));
}
void read_intArrLenArr(int fd, struct IntArrLenArr *p)
{
read_check(fd, &p->max_index, sizeof(p->max_index));
read_check(fd, &p->length, sizeof(p->length));
p->intArrLen = memory_allocator(p->length * sizeof(*p->intArrLen));
if (!p->intArrLen)
{
fprintf(stderr, "%d: ran out of memory (%zu bytes requested)\n",
(int)getpid(), p->length * sizeof(*p->intArrLen));
exit(EXIT_FAILURE);
}
for (int i = 0; i < p->length; i++)
read_intArrLen(fd, &p->intArrLen[i]);
}
struct IntArrLenArr getRes(int num1, int num2)
{
struct IntArrLenArr ret;
ret.length = num1;
ret.max_index = num2;
ret.intArrLen = memory_allocator(sizeof(struct IntArrLen) * num1);
if (ret.intArrLen == NULL)
{
fprintf(stderr, "%d: failed to allocate %zu bytes of memory\n",
(int)getpid(), sizeof(struct IntArrLen) * num1);
exit(EXIT_FAILURE);
}
for (int i = 0; i < num1; i++)
{
ret.intArrLen[i].length = num1;
ret.intArrLen[i].index = num2;
ret.intArrLen[i].arr = memory_allocator(sizeof(int) * num1);
if (ret.intArrLen[i].arr == NULL)
{
fprintf(stderr, "%d: failed to allocate %zu bytes of memory\n",
(int)getpid(), sizeof(int) * num1);
exit(EXIT_FAILURE);
}
for (int j = 0; j < num2; j++)
{
ret.intArrLen[i].arr[j] = j;
}
}
return ret;
}
int main(void)
{
struct IntArrLenArr res;
res.max_index = 0;
res.length = 0;
atexit(report_memory_used);
printf("Parent process: %d\n", (int)getpid());
int *fds = memory_allocator(sizeof(int) * 13 * 2);
for (int i = 0; i < 13; i++)
{
if (pipe(fds + i * 2) < 0)
{
fprintf(stderr, "failed to create pipe %d\n", i);
exit(EXIT_FAILURE);
}
}
for (int i = 0; i < 13; i++)
{
pid_t child_pid = fork();
if (child_pid == 0)
{
printf("%d: Child process: %d - pipe [%d,%d]\n",
(int)getpid(), i, fds[i * 2 + 0], fds[i * 2 + 1]);
for (int j = 0; j < 13; j++)
{
fd_close(fds[j * 2 + 0]);
if (i != j)
fd_close(fds[j * 2 + 1]);
}
//res = getRes(20, 3000000); // 300,000 works but not with 3000,000
res = getRes(20, 300000); // 300,000 works but not with 3000,000
report_memory_used();
if (res.length != 0)
{
printf("-----------%d\n", i);
write_intArrLenArr(fds[i * 2 + 1], &res);
printf("+++++++++++%d\n", i);
}
fd_close(fds[i * 2 + 1]);
exit(0);
}
else if (child_pid == -1)
{
fprintf(stderr, "fork error\n");
exit(EXIT_FAILURE);
}
else
{
fprintf(stderr, "%d: launched child %d\n", (int)getpid(), (int)child_pid);
}
}
for (int i = 0; i < 13; i++)
{
fd_close(fds[i * 2 + 1]);
read_intArrLenArr(fds[i * 2 + 0], &res);
printf(".................%d\n", i);
if (res.length > 0)
{
printf("do something\n");
}
fd_close(fds[i] * 2 + 0);
}
free(fds);
return 0;
}
我从 运行 它(在 MacBook Pro 上)得到的输出示例是:
$ ./pipe53 2>&1 | cat # I actually pipe the output to "so | pbcopy" …
23380: bytes allocated = 104
23380: launched child 23383
23380: launched child 23384
23383: bytes allocated = 424
23383: bytes allocated = 504
23380: launched child 23385
23384: bytes allocated = 424
23384: bytes allocated = 504
23380: launched child 23386
23385: bytes allocated = 424
23385: bytes allocated = 504
23380: launched child 23387
23386: bytes allocated = 424
23386: bytes allocated = 504
23380: launched child 23388
23387: bytes allocated = 424
23387: bytes allocated = 504
23388: bytes allocated = 424
23388: bytes allocated = 504
23380: launched child 23389
23380: launched child 23390
23389: bytes allocated = 424
23389: bytes allocated = 504
23380: launched child 23391
23390: bytes allocated = 424
23390: bytes allocated = 504
23380: launched child 23392
23391: bytes allocated = 424
23391: bytes allocated = 504
23380: launched child 23393
23392: bytes allocated = 424
23392: bytes allocated = 504
23380: launched child 23394
23393: bytes allocated = 424
23393: bytes allocated = 504
23380: launched child 23395
23394: bytes allocated = 424
23394: bytes allocated = 504
23380: Premature EOF when reading fd = 3.
23380: Premature EOF when reading fd = 3.
23395: bytes allocated = 424
23395: bytes allocated = 504
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 5.
23380: Premature EOF when reading fd = 5.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 7.
23380: Premature EOF when reading fd = 7.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 9.
23380: Premature EOF when reading fd = 9.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 11.
23380: Premature EOF when reading fd = 11.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 13.
23380: Premature EOF when reading fd = 13.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 15.
23380: Premature EOF when reading fd = 15.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 17.
23380: Premature EOF when reading fd = 17.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 19.
23380: Premature EOF when reading fd = 19.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 21.
23380: Premature EOF when reading fd = 21.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 23.
23380: Premature EOF when reading fd = 23.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 25.
23380: Premature EOF when reading fd = 25.
23380: bytes allocated = 104
23380: Premature EOF when reading fd = 27.
23380: Premature EOF when reading fd = 27.
23380: bytes allocated = 104
23380: bytes allocated = 104
Parent process: 23380
.................0
.................1
.................2
.................3
.................4
.................5
.................6
.................7
.................8
.................9
.................10
.................11
.................12
AFAICT,getRes()
函数(大小为 300,000 和 3,000,000)未触发子进程写入的任何内容。
请注意在调试消息中谨慎使用标识 PID。
您需要修改getRes()
,以便将数据写入父进程。