As most developers will be aware processes define three file descriptors which we know more commonly as stdin
, stdout
and stderr
.
From what I can tell the fd
for each of these are statically defined as 0, 1 and 2 respectively. This is explicitly stated in the POSIX standard: http://pubs.opengroup.org/onlinepubs/009695399/functions/stdin.html
Now lets say I have a group of processes which require a 4th. For example a child process created with fork()
exec()
requiring a handle to a control socket created with socketpair()
before the fork()
. For this example the purpose of the 4th handle (socket) is to provide a link between parent and child process. Now the question comes... how does the child know which FD is the control socket? Is there any reason why I can't use a static number for this (eg: #define CONTROL_SOCKET 3
) as long as I dup2(new_socket,CONTROL_SOCKET)
between the fork()
and the exec()
. I'd then just be able to foo = write(CONTROL_SOCKET, bar, baz)
inside the child. Lets take it as read that any other FDs
open my app are expected to close on exec so my logic is that dup2()
won't close anything that won't be closed anyway by exec()
.
I know that there are several possible work-arounds to avoid doing this (eg: passing the FD in an environment variable or program arguments) and there are a number of examples on the web showing how to do so. What I don't understand is what is being worked around? What's the problem with statically defining an FD that's being avoided? It feels at first glance to be avoiding a problem which doesn't exist. Do some systems use FDs other than 0, 1 and 2 and might I be overwriting something important by dup2(<some fd>,3)
before an exec?
Note: This question is really a question about writing code which is portable between existing POSIX operating systems.