Functions of the select () function
The system calls the back-end Implementation of select and poll, and uses these two system calls to query whether the device can read or write, or whether it is in a certain state. If poll is empty, the driver is considered readable and writable. The returned value is a status mask.
How to Use the select () function?
The Select () function interface is mainly based on the 'fd _ set' type. It ('fd _ set') is a collection of file descriptors (FD. Because the length of the fd_set type varies on different platforms, a set of standard macro definitions should be used to process such variables:
Fd_set set;
Fd_zero (& set );
Fd_set (FD, & set );
Fd_clr (FD, & set );
Fd_isset (FD, & set );
In the past, an fd_set usually only contains less than or equal to 32 file descriptors, because fd_set actually uses only one int bit vector. In most cases, checking that fd_set can include any value of the file descriptor is the responsibility of the system, but determining how much your fd_set can put sometimes you should check/modify the value of the macro fd_setsize. * This value is related to the system. * Check the select () MAN manual in your system. Some systems have problems with support for more than 1024 file descriptors. [Translator's note: Linux is such a system! You will find that the result of sizeof (fd_set) is 128 (* 8 = fd_setsize = 1024), although this rarely happens to you.]
The basic Select Interface is very simple:
Int select (INT NFDs, fd_set * readset, fd_set * writeset,
Fd_set * effectset, struct timeval * timeout );
Where:
NFDs
Number of file descriptors to be checked. The value must be the largest among the three fd_sets.
Larger, not the total number of actual file descriptors.
Readset
A set of file descriptors used to check readability.
Writeset
A set of file descriptors used to check the writability.
Effectset
The file descriptor used to check the unexpected state. (Note: errors are not unexpected)
Timeout
Null Pointer indicates infinite waiting; otherwise, it is a pointer to the timeval structure, representing
Long wait time. (If both TV _sec and TV _usec are equal to 0, the file descriptor
Is not affected, but the function is not suspended)
The function returns the total number of Operation file descriptors corresponding to the response operation, and the three groups of data are modified at the appropriate position. Only some of the response operations are not modified. Then we should use the fd_isset macro to find the returned file descriptor group.
Here is a simple example of testing the readability of a single file descriptor:
Int isready (int fd)
{
Int RC;
Fd_set FDS;
Struct timeval TV;
Fd_zero (& FDs );
Fd_set (FD, & FDs );
// TV. TV _sec = TV. TV _usec = 0;
// Rc = select (FD + 1, & FDS, null, null, & TV );
Rc = select (FD + 1, & FDS, null );
If (RC <0)
Return-1;
Return fd_isset (FD, & FDs )? 1: 0;
}
Of course, if we pass the NULL pointer As fd_set, it means we are not interested in this operation, but select () will still wait until it occurs or exceeds the waiting time.
[Translator's note: in Linux, timeout refers to the time spent by the program in a non-sleep state, rather than the actual past time, this may cause time issues for migration to non-Linux platforms. Porting also involves that in the system v style, select () sets timeout to an undefined null state before exiting the function, but not in BSD, linux follows System V at this point, so you should pay attention to the problem of reusing the timeout pointer]
Linux
The following select call process:
1. the user-layer application calls select (), and the underlying calls poll ())
2. The core layer calls sys_select () ------> do_select ()
Finally, call the poll function of struct file_operations * f_op for the struct file type variable corresponding to the file descriptor FD.
The function pointed to by poll returns the read/write information.
1) if read/write is enabled, read/write information is returned.
2) if read/write is not available, the process will be blocked, wait for the driver to wake up, call the poll function again, or return a response timeout.
3. the driver needs to implement the poll function.
When the driver finds that data can be read and written, it notifies the core layer and the core layer to re-call the function query information pointed to by poll.
Poll_wait (filp, & wait_q, wait) // Add the current process to the waiting queue, but it is not blocked.
Use wake_up_interruptible (& wait_q) to wake up the waiting queue during interruption
This article from the csdn blog, reproduced please indicate the source: http://blog.csdn.net/dingyuanpu/archive/2010/05/09/5572352.aspx