I have to close pipe FDs of the process but I want them open in the child process. One solution could be to close FDs after fork() call. It offers solution if I have to call it once. I am calling this in a loop so even though I close FDs after fork(), it will work for first iteration. In the next iteration, it will again have theirs FDs closed. So how can I tackle a situation like this. The code in which I am trying to achieve this is as follows:
//I want to execute pwd|sort > file.txt
char commands[2][30] = {"pwd", "sort"};
char directory [2][30] = {"/usr/bin/pwd", "/usr/bin/sort"}
char outputFile[30] = "file.txt"
int totalCommands = 2;
bool isOutputFilePresent = true;
//creating two pipes
int fd1[2];
int fd2[2];
pipe(fd1);
pipe(fd2);
//Closing the writing ends but keeping the reading ends open as closing them will destroy both the pipes
close (fd1[1]);
close (fd2[1]);
//loop to execute each command by creating a child process in each iteration
for (int i = 0; i < totalCommands; ++i)
{
pid_t pid = fork();
if (pid == 0)
{
if (i == totalCommands - 1)
{
if (i%2 == 0)
{
close(fd1[1]);
close(fd2[0]);
dup2(fd1[0], 0);
dup2(fd2[1], 1);
}
else
{
close(fd2[1]);
close(fd1[0]);
dup2(fd2[0], 0);
dup2(fd1[1], 1);
}
}
else
{
if (i%2 == 0)
{
close(fd2[0]);
close(fd2[1]);
close(fd1[1]);
dup2(fd1[0], 0);
}
else
{
close(fd1[0]);
close(fd1[1]);
close(fd2[1]);
dup2(fd2[0], 0);
}
if(isOutputFilePresent)
{
int outputFD = open (outputFile, O_WRONLY | O_CREAT);
dup2(outputFD, 1);
}
}
execv(directory[i], commands[i]) //ignore the fact that i am passing command name instead of argument vector
}
wait(NULL);
}