DUP and dup2

Source: Internet
Author: User

Http://www.xxlinux.com/linux/article/development/soft/20090828/17508.html

 

I believe that most programming in Unix/LinuxProgramThey all have the Super classic masterpiece apue. In this book, the author explains DUP/dup2 previously mentioned "file sharing", which is helpful for understanding DUP/dup2. Here is a simple excerpt for later analysis:

Steven s said:
(1) Each process has a record item in the Process Table. Each record item contains an open file descriptor table, which can be considered as a vector, and each descriptor occupies one item. Associated with each file descriptor is:
(A) file descriptor flag.
(B) pointer to a file table item.
(2) The kernel maintains a file table for all open files. Each file table item includes:
(A) File status signs (read, write, add write, synchronization, non-blocking, etc ).
(B) Current file displacement.
(C) pointer to the table entry of the file v node.
Figure:
File descriptor table
------------
Fd0 0 | P0 -------------> File Table 0 ---------> vnode0
------------
Fd1 1 | P1 -------------> File Table 1 ---------> vnode1
------------
Fd2 2 2 | p2
------------
FD3 3 3 | p3
------------
......
......
------------
1. DUP and dup2 in a single process
Assume that process a has an opened file descriptor FD3, and its status is as follows:
Process A's file descriptor table (before dup2)
------------
Fd0 0 | P0
------------
Fd1 1 | P1 -------------> File Table 1 ---------> vnode1
------------
Fd2 2 2 | p2
------------
FD3 3 3 | P3 -------------> File Table 2 ---------> vnode2
------------
......
......
------------
It is called as follows:
N_fd = dup2 (FD3, stdout_fileno); The process status is as follows:
Process A's file descriptor table (after dup2)
------------
Fd0 0 | P0
------------
N_fd 1 | P1 ------------
------------
Fd2 2 2 | p2
------------ _ |
FD3 3 3 | P3 -------------> File Table 2 ---------> vnode2
------------
......
......
------------
Explanation:

N_fd = dup2 (FD3,
Stdout_fileno) indicates that n_fd shares a file table item with FD3 (their file table Pointer Points to the same file table item). The position of n_fd in the file descriptor table is
The position of stdout_fileno, and the file table entry pointed to by the original stdout_fileno is disabled, I think this should be clearly reflected. According to the above explanation
Some problems raised in Cu can be explained:
(1) "Must the first parameter of dup2 be a valid enabled filedes? "-- Answer: required.
(2) "Can the second parameter of dup2 be a filedes value in any valid range? "-- Answer: Yes. In UNIX, the value range is [0,255].
In addition, I feel that a good way to understand dup2 is to regard FD as a struct type, as shown in the figure above. We may wish to define it:
Struct fd_t {
Int index;
Filelistitem * PTR;
};
Then, dup2 matches the index and modifies the PTR to complete the dup2 operation.
When studying dup2, you always encounter the word "redirection", which completes a "redirection from standard output to file ", after dup2, any I/O operations such as printf with the target stdout_fileno of process a will flow into the file corresponding to fd3. The following is an example program:
# Define teststr "Hello dup2n"
Int main (){
Int FD3;
FD3 = open ("testdup2.dat", 0666 );
If (FD <0 ){
Printf ("Open errorn ");
Exit (-1 );
}
If (dup2 (FD3, stdout_fileno) <0 ){
Printf ("err in dup2n ");
}
Printf (teststr );
Return 0;
}
The result is that you can see "Hello dup2" in testdup2.dat ".
2. Restore after redirection
There is such a post on Cu, that is, how to restore the original state after redirection? First, you can think of saving the file descriptor before redirection. So how to save it, like below?
Int s_fd = stdout_fileno;
Int n_fd = dup2 (FD3, stdout_fileno );
Or can this happen?
Int s_fd = DUP (stdout_fileno );
Int n_fd = dup2 (FD3, stdout_fileno );

What is the difference between the two methods? The answer is that the second solution is correct. The analysis is as follows: according to the first method, we only save the equivalent fd_t on the surface.
Method), and after calling dup2, the file table items pointed to by PTR are closed because the Count value is already zero. If we call dup2 (s_fd,
FD3) will cause an error (the cause of the error is described above ). In the second method, we first perform a copy. The copied status is shown in:
Process A's file descriptor table (after DUP)
------------
Fd0 0 | P0
------------
Fd1 1 | P1 -------------> File Table 1 ---------> vnode1
------------/|
Fd2 2 2 | P2/
------------/
FD3 3 3 | P3 -------------> File Table 2 ---------> vnode2
------------/
S_fd 4 | P4 ------/
------------
......
......
------------
After calling dup2, the status is:
Process A's file descriptor table (after dup2)
------------
Fd0 0 | P0
------------
N_fd 1 | P1 ------------
------------
Fd2 2 2 | p2
------------ _ |
FD3 3 3 | P3 -------------> File Table 2 ---------> vnode2
------------
S_fd 4 | P4 -------------> File Table 1 ---------> vnode1
------------
......
......
------------
The meaning of DUP (FD) is that the new file descriptor returned shares a file table item with FD. Just like s_fd and fd1 shared file table 1 in the after DUP diagram.
After determining the second scheme, it is easy to restore the redirection. You only need to call dup2 (s_fd, n_fd. The following is a complete example program:
# Define teststr "Hello dup2n"
# Define sizeofteststr 11
Int main (){
Int FD3;
Int s_fd;
Int n_fd;
FD3 = open ("testdup2.dat", 0666 );
If (FD3 <0 ){
Printf ("Open errorn ");
Exit (-1 );
}
/* Copy the standard output descriptor */
S_fd = DUP (stdout_fileno );
If (s_fd <0 ){
Printf ("err in dupn ");
}
/* Redirect standard output to file */
N_fd = dup2 (FD3, stdout_fileno );
If (n_fd <0 ){
Printf ("err in dup2n ");
}
Write (stdout_fileno, teststr, sizeofteststr);/* write to testdup2.dat */
/* Redirect recovery standard output */
If (dup2 (s_fd, n_fd) <0 ){
Printf ("err in dup2n ");
}
Write (stdout_fileno, teststr, sizeofteststr);/* output to the screen */
Return 0;
}

Note that when I output data, I use the write library function without buffering. If I use printf with a buffer, the final result is two rows of "hello" output on the screen.
Dup2 ", while the testdup2.dat file is empty, the reason is that the buffer is strange. Because the final target is the screen, the program finally outputs the buffer content to the screen.

3. DUP/dup2 between parent and child Processes

The same file descriptor of the child process and the parent process called by fork shares the same file table item, as shown in:
File descriptor table of parent process
------------
Fd0 0 | P0
------------
Fd1 1 | P1 -------------> File Table 1 ---------> vnode1
------------/|
Fd2 2 2 | P2 |
------------ |
|
File descriptor table of sub-process B |
------------ |
Fd0 0 | P0 |
------------ |
Fd1 1 | P1 ------------------- |
------------
Fd2 2 2 | p2
------------
Therefore, the proper use of dup2 and DUP can establish a "communication bridge" between the parent and child processes ". This is not detailed here.
Iv. Summary
The flexible use of DUP/dup2 can bring you a lot of powerful functions, it took some time to summarize the above so much, do not know whether you understand thoroughly, it can only be explored in future practices.

 

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.