provide control over an open file
#include <sys/types.h>
#include <unistd.h>
#include <fcntl.h>
int fcntl( int fildes, int cmd, ... );
The fcntl() function provides control over the open file
referenced by file descriptor fildes. The type of control is
specified by the argument cmd, which may require a third data
argument (arg).
At least the following values for cmd() are defined in
<fcntl.h>:
- F_DUPFD
- Allocate and return a new file descriptor that is the lowest numbered
available (that is, not already open) file descriptor greater than or
equal to the third argument, arg(), taken as an
int. The new file descriptor refers to the same file as
fildes, and shares any locks.
- F_GETFD
- Get the file descriptor flags associated with the file descriptor
fildes. File descriptor flags are associated with a single
file descriptor, and don't affect other file descriptors referring to
the same file.
The only defined file descriptor flag is:
- FD_CLOEXEC -
if this flag is clear, the file remains open across
spawn() or exec() calls; else the file is
closed.
- F_SETFD
- Set the file descriptor flags associated with fildes, to the
third argument, arg, taken as type int. See the
above discussion for more details.
- F_GETFL
- Get the file status flags and file access modes associated with
fildes. The flags and modes are defined in the header
<fcntl.h>. The file status flags are:
- O_APPEND - set append mode.
- O_NONBLOCK - no delay.
- O_DSYNC - synchronize data.
- O_SYNC - synchronize data and the file.
- O_TEMP - temporary file I/O.
- O_CACHE - cache data.
These flags are described in more detail in the open()
documentation.
The file access modes are:
- O_RDONLY - Open for reading only.
- O_WRONLY - Open for writing only.
- O_RDWR - Open for reading and writing.
- F_SETFL
- Set the file status flags, as shown above, for the open file
description associated with fildes() from the corresponding
bits in the third argument, arg, taken as type
int. The file access mode can't be changed by this
function call. All bits set in arg, other than the file
status bits, are ignored.
- F_GETLK
- Get the first lock that blocks the lock description pointed to by the
third argument, arg, taken as a pointer to type
struct flock,
as defined in the header file <fcntl.h>, and
documented below. The information returned overwrites the information
passed to fcntl() in the structure pointed to by
arg.
If no lock is found that would prevent this lock from
being created, the structure is left unchanged, except for the lock type,
which is set to F_UNLCK. If a lock is found, the
l_pid member of the structure pointed to by arg
is set to the process ID of the process holding the blocking lock and
l_whence is set to SEEK_SET.
- F_SETLK
- Set or clear a file segment lock, according to the lock description
pointed to by the third argument, arg, taken as a pointer to
type struct flock, as defined in the header file
<fcntl.h>, and documented below. This command is used to
create shared (or read) locks (member l_type set to
F_RDLCK) or exclusive (or write) locks (member
l_type set to F_WRLCK), as well as to remove
either type of lock (member l_type set to
F_UNLCK). The lock types are defined in the header file
<fcntl.h>. If a lock cannot be set, fcntl()
returns immediately.
- F_SETLKW
- This command is the same as F_SETLK, except that if a
lock is blocked by other locks, the process waits until the request can
be satisfied. If a signal that is to be caught is received while
fcntl() is waiting for a region, the call is interrupted
without performing the lock operation, and fcntl()
returns -1 with errno set to EINTR.
The flock() structure members are defined below:
- short l_type
- F_RDLCK, F_WRLCK or
F_UNLCK.
- short l_whence
- Flag for starting offset, one of SEEK_SET,
SEEK_CUR, or SEEK_END to indicate that
the relative offset, l_start, is measured from the start
of the file, the current seek position, or the end of the file,
respectively.
- off_t l_start
- Relative offset in bytes.
- off_t l_len
- Consecutive bytes to lock; if 0, until EOF; if negative, the
preceding bytes up to, but not including, the start byte.
- pid_t l_pid
- Process ID of the process holding the lock, returned when
cmd is F_GETLK.
When a shared lock is set on a segment of a file, other processes can
set shared locks on the same segment, or a portion of it. A shared
lock prevents other processes from setting exclusive locks on any
portion of the protected area. A request for a shared lock fails
if the file was opened write-only.
An exclusive lock prevents any other process from setting a shared or
an exclusive lock on an portion of the protected area. A request for
an exclusive lock fails if the file was opened read-only.
Locks may start and extend beyond the current end of file, but may not
start or extend before the beginning of the file; to attempt to do so
is an error. A lock extends to "infinity" (the largest possible
value for the file offset) if l_len is set to zero. If
l_whence and l_start point to the beginning of the
file, and l_len is zero, the entire file is locked.
The calling process may have only one type of lock set for each byte
of a file. Before successfully returning from a F_SETLK or
F_SETLKW request, the previous lock type (if any) for each
byte in the specified lock region is replaced by the new lock type.
All locks associated with a file for a given process are removed when
a file descriptor for that file is closed by the process, or the
process holding the file descriptor terminates. Locks aren't
inherited by a child process using the fork()
or spawn... functions.
However, locks are inherited across exec...
calls.
On error, fcntl() returns -1, and errno is set to
indicate the error. The successful return value(s) depend on the
request type specified by arg:
- F_DUPFD
- A new file descriptor.
- F_GETFD
- Value of the file descriptor flags (never a negative value).
- F_SETFD
- Value other than -1.
- F_GETFL
- Value of the file status flags and access modes as shown above (never a
negative value).
- F_SETFL
- Value other than -1.
- F_GETLK
- Value other than -1.
- F_SETLK
- Value other than -1.
- F_SETLKW
- Value other than -1.
- EAGAIN
- The argument cmd is F_SETLK, the type of lock
(l_type) is a shared lock (F_RDLCK), and
the segment of a file to be locked is already exclusive-locked by
another process, or the type is an exclusive lock and some portion of
the segment of a file to be locked is already shared-locked or
exclusive-locked by another process.
- EBADF
- The fildes argument isn't a valid file descriptor.
The argument cmd is F_SETLK or
F_SETLKW, the type of lock (l_type) is a
shared lock (F_RDLCK), and fildes isn't a
valid file descriptor open for reading.
The argument cmd is F_SETLK or
F_SETLKW, the type of lock (l_type) is an
exclusive lock (F_WRLCK), and fildes
isn't a valid file descriptor open for writing.
- EDEADLK
- The argument cmd is F_SETLKW, and a deadlock
condition was detected.
- EINTR
- The argument cmd is F_SETLKW, and the
function was interrupted by a signal.
- EINVAL
- The argument cmd is F_DUPFD, and the third
argument is negative, or greater than the configured number of maximum
open file descriptors per process.
The argument cmd is F_GETLK,
F_SETLK or F_SETLKW, and the data
arg isn't valid, or fildes refers to a file
that doesn't support locking.
- EMFILE
- The argument cmd is F_DUPFD, and the
process has no unused file descriptors, or no file descriptors greater
than or equal to arg are available.
- ENOLCK
- The argument cmd is F_SETLK
or F_SETLKW, and satisfying the lock or unlock request
would cause the number of lock regions in the system to exceed the
system-imposed limit.
/*
* This program makes "stdout" synchronous
* to guarantee the data is recoverable
* (if it is redirected to a file).
*/
#include <unistd.h>
#include <fcntl.h>
#include <stdio.h>
int main( void )
{
int flags, retval;
flags = fcntl( STDOUT_FILENO, F_GETFL );
flags |= O_DSYNC;
retval = fcntl( STDOUT_FILENO, F_SETFL, flags );
if( retval == -1 ) {
printf( "error setting stdout flags\n" );
return;
}
printf( "hello QNX world\n" );
return (EXIT_SUCCESS);
}
POSIX 1003.1
Safety: | |
Interrupt handler |
No |
Signal handler |
Yes, but modifies errno |
Thread |
Yes |
close(),
dup(),
dup2(),
exec... functions,
open()