c - pipe chain between processes -
c - pipe chain between processes -
i want have 1 parent 2 children.
the parent reads file "a.txt" , sends trough pipe first child; first kid reads chars , sends sec kid lower letter chars.
the sec kid prints in "b.txt" each distinct char , number of appearances(per line) , sends trough pipe parent number of distinct chars. parent prints result sec child.
i've done pipe parent 1 kid , test i've set pipe parent. can't figure out how create pipe go sec child. i've been searching info on dup2
don't on how create work.
#include <stdio.h> #include <stdlib.h> #include <sys/types.h> #include <sys/stat.h> #include <sys/wait.h> #include <unistd.h> #include <ctype.h> #include <fcntl.h> void main() { int pfd1[2], pfd2[2], pid1, pid2, pfin, status, fd; char *c = (char *)malloc(sizeof(char)); if (pipe(pfd1) < 0) { printf("eroare la crearea pipe-ului\n"); exit(1); } if (pipe(pfd2) < 0) { printf("eroare la crearea pipe-ului\n"); exit(1); } if ((pid1 = fork()) < 0) { printf("eroare la fork\n"); exit(1); } if (pid1 == 0) { /*child */ close(pfd1[1]); while (read(pfd1[0], c, 1) > 0) { //printf("%s",c); if (islower(*c)) { close(pfd2[0]); //inchid capul de citire; scriu in pipe write(pfd2[1], c, 1); ////dup?????? } } printf("\n"); write(pfd[1], buff, len); close(pfd1[0]); close(pfd2[1]); exit(0); } if ((pid2 = fork()) < 0) { printf("eroare la fork\n"); exit(1); } if (pid2 == 0) { printf("second child"); exit(0); } /* parent */ close(pfd1[0]); close(pfd2[1]); fd = open("date.txt", o_rdonly); while (read(fd, c, 1) > 0) { write(pfd1[1], c, 1); } close(pfd1[1]); /* la sfarsit inchide si capatul utilizat */ close(pfin); while (read(pfd2[0], c, 1) > 0) printf("%s", c); close(pfd2[0]); printf("%d", wait(&status)); printf("%d", wait(&status)); }
i have few specific comments on code:
char *c = (char *)malloc(sizeof(char));
while there nil wrong this, there no need char
allocated heap. more idiomatic approach utilize char c;
here , pass &c
read(2)
, write(2)
scheme calls. (even more idiomatic utilize c standard io facility; freopen(3)
, getchar(3)
, , putchar(3)
-- not create transition until have code working want to, because additional complication problem you're trying solve.)
if ((pid1 = fork()) < 0) { printf("eroare la fork\n"); exit(1); }
by using own error message, missing out on of import error information. should utilize perror(3)
print error message instead. give , users actual cause errors can search for. fork(2)
can fail if user running setrlimit(2)
nproc
maximum process limit, system-wide process limit, out of kernel memory.
if ((pid1 = fork()) < 0) { perror("eroare la fork"); exit(1); }
you should check homecoming value open(2)
calls. (you're supposed check homecoming values write(2)
, close(2)
errors, handling these errors harder. printing error , quitting start programs.)
while (read(pfd1[0], c, 1) > 0) { //printf("%s",c); if (islower(*c)) { close(pfd2[0]);
this wrong location close(2)
phone call -- shouldn't closing filedescriptor on , on every input character. if checking close(2)
homecoming value, notice errno
set ebadf
because file descriptor no longer valid on sec , subsequent calls.
now, onto problem came here for: sequence of fork()
, pipe()
, , dup2()
calls hook processes in pipeline , send info parent process. since pipe(2)
creates uni-directional pipe(7)
s, need phone call pipe(2)
four times -- both directions between parent , children. if store pipe endpoints in arrays names mean you, easier maintain track of. perhaps create arrays named to_
writing , from_
reading from:
int to_child[2]; int from_parent[2]; int to_parent[2]; int from_child[2]; (int i=0; i<2; i++) { int p[2]; if (pipe(p) == -1) { perror("pipe"); exit(1); } /* parent kid */ to_child[i] = p[1]; from_parent[i] = p[0]; if (pipe(p) == -1) { perror("pipe"); exit(1); } /* kid parent */ to_parent[i] = p[1]; from_child[i] = p[0]; }
note don't need utilize dup2(2)
re-arrange filedescriptors unless want execute other programs handle "filter" task. read(2)
using from_parent[...]
or from_child[...]
descriptors , write(2)
to_child[...]
, to_parent[...]
descriptors.
maybe entire thing easier socketpair(2)
using af_unix
create bi-directional sockets, can read , written in same fashion other bsd-style socket. see socket(7)
, unix(7)
overview.
c pipe dup2
Comments
Post a Comment