In C how do you redirect stdin/stdout/stderr to files when making an execvp() or similar call?
The right way to do it is to replace the file descriptors STDIN_FILENO
, STDOUT_FILENO
and STDERR_FILENO
with the opened files using dup2()
. You should also then close the original files in the child process:
else if (pid == 0){ dup2(fileno(someopenfile), STDIN_FILENO); dup2(fileno(someotherfile), STDOUT_FILENO); dup2(fileno(somethirdopenfile), STDERR_FILENO); fclose(someopenfile); fclose(someotheropenfile); fclose(somethirdopenfile); execvp(args[0], args); // handle error ...}
Take a look at freopen
function.
I had to do something similar with stdout
and wrote two functions that do the work for me:
static int fd;static fpos_t pos;void switchStdout(const char *newStream){ fflush(stdout); fgetpos(stdout, &pos); fd = dup(fileno(stdout)); freopen(newStream, "w", stdout);}void revertStdout(){ fflush(stdout); dup2(fd, fileno(stdout)); close(fd); clearerr(stdout); fsetpos(stdout, &pos);}
You can use this when stdin , stdout , stderr are terminal-
//change stdin,stdout,stderr freopen("new_stdin","r",stdin); freopen("new_stdout","r",stdout); freopen("new_stderr","r",stderr); //----do something;//reset stdin,stdout,stderr freopen("/dev/tty","r",stdin); freopen("/dev/tty","r",stdout); freopen("/dev/tty","r",stderr);