I am trying to setup a pipe between one process that is launched with execvp and its parent process.
Right now, I fork/pipe/dup/exec like this:
pid_t child = 0;
int fds[2];
...
void fork_exec(string cmd) {
pipe(fds);
child = fork();
if(child == 0) {
close(fds[1]);
char *input = (char*)cmd.c_str();
char *cmdArg[100];
char *token = strtok(input, " \n");
int i = 0;
cmdArg[i] = token;
//while this is not the last token
while(token != NULL) {
token = strtok(NULL, " \n");
cmdArg[++i] = token;
}
cmdArg[++i] = NULL;
close(fds[0]);
dup2(1, fds[1]);
execvp(cmdArg[0], cmdArg);
} else {
close(fds[1]);
}
}
And then, in another part of the program, when the function returns, some time later another function (running as part of the parent thead) tries to write the piped value to a file.
void out(string name) {
ofstream fout;
fout.open((*cmdIter).c_str(), ofstream::app);
long lSize = 1000;
char * buffer;
buffer = new char[lSize];
close(fds[1]);
read(fds[0], buffer, lSize);
fclose (pFile);
fout.write(buffer, lSize);
fout.close();
delete [] buffer;
waitpid(child, &res, 0);
}
But this part of the code does not work, instead creates the file but does not write anything to it, and also prints the output to the screen. I believe the child thread should block until there is something to write to?
I believe the mistake is here:
From
dup2(2):So you’ve just closed the filedescriptor returned from
pipe(2)a few lines above. Try swapping the two: