| DUP(2) | System Calls Manual | DUP(2) | 
dup, dup2,
  dup3 —
#include <unistd.h>
int
  
  dup(int
    oldfd);
int
  
  dup2(int
    oldfd, int
  newfd);
int
  
  dup3(int
    oldfd, int newfd,
    int flags);
dup() family of calls duplicates an existing file
  descriptor oldfd. A new file descriptor is produced; it
  is a new reference to the same underlying system object. The object in
  question does not distinguish between the descriptors referencing it in any
  way. Thus for files, read(2),
  write(2) and
  lseek(2) calls all move a single
  shared seek position. Similarly, all object modes, settings, properties, and
  behavior other than the close-on-exec flag are shared between references. This
  includes the setting of append mode, non-blocking I/O actions, asynchronous
  I/O operations in progress, socket options, and so forth. The close-on-exec
  flag, however, is a property of the descriptor rather than the object and can
  be set independently for each reference.
To get an independent handle with its own seek position and settings, an additional open(2) call must be issued. (This is not generally possible for pipes and sockets.)
The dup() call chooses the new descriptor:
    it is the lowest-numbered descriptor not currently in use. The
    dup2() and dup3() calls
    allow the caller to choose the new descriptor by passing
    newfd, which must be within the range of valid
    descriptors. If newfd is the same as
    oldfd, the call has no effect. Otherwise, if
    newfd is already in use, it is closed as if
    close(2) had been called.
File descriptors are small non-negative integers that index into
    the per-process file table. Values 0, 1, and 2 have the special property
    that they are treated as standard input, standard output, and standard error
    respectively. (The constants STDIN_FILENO,
    STDOUT_FILENO, and
    STDERR_FILENO are provided as symbolic forms for
    these values.) The maximum value for a file descriptor is one less than the
    file table size. The file table size can be interrogated with
    getdtablesize(3) and
    can to some extent be adjusted with
    setrlimit(2).
The dup3() call includes an additional
    flags argument supporting a subset of the
    open(2) flags:
O_CLOEXECO_NONBLOCKO_NOSIGPIPESIGPIPE when a
      write is made to a broken pipe. Instead, the write will fail with
      EPIPE.dup3() operation.
In the case of dup() and
    dup2() the close-on-exec flag on the new file
    descriptor is always left unset and all the modes and settings of the
    underlying object are left unchanged.
Functionality similar to dup() with
    slightly different semantics is also available via
    fcntl(2).
dup2() and dup3() this is
  always the same as newfd. If an error occurs, the value
  -1 is returned and errno is set to indicate what
  happened.
#include <unistd.h>
int fds[2];
pid_t pid;
pipe(fds);
pid = fork();
if (pid == 0) {
	/* child; use read end of pipe to stdin */
	dup2(fds[0], STDIN_FILENO);
	close(fds[0]);
	close(fds[1]);
	execv("/some/program", args);
}
/* parent process; return write end of pipe */
close(fds[0]);
return fds[1];
dup() and dup2() functions
  conform to IEEE Std 1003.1-1990
  (“POSIX.1”).
dup3() function originated in Linux and appeared in
  NetBSD 6.0.
| December 24, 2013 | NetBSD 9.4 |