In contrast to process-associated record locks (see File Locks), open file description record locks are associated with an open file description rather than a process.
Using fcntl to apply an open file description lock on a region that
already has an existing open file description lock that was created via the
same file descriptor will never cause a lock conflict.
Open file description locks are also inherited by child processes across
fork, or clone with CLONE_FILES set
(see Creating a Process), along with the file descriptor.
It is important to distinguish between the open file description (an
instance of an open file, usually created by a call to open) and
an open file descriptor, which is a numeric value that refers to the
open file description. The locks described here are associated with the
open file description and not the open file descriptor.
Using dup (see Duplicating Descriptors) to copy a file
descriptor does not give you a new open file description, but rather copies a
reference to an existing open file description and assigns it to a new
file descriptor. Thus, open file description locks set on a file
descriptor cloned by dup will never conflict with open file
description locks set on the original descriptor since they refer to the
same open file description. Depending on the range and type of lock
involved, the original lock may be modified by a F_OFD_SETLK or
F_OFD_SETLKW command in this situation however.
Open file description locks always conflict with process-associated locks, even if acquired by the same process or on the same open file descriptor.
Open file description locks use the same struct flock as
process-associated locks as an argument (see File Locks) and the
macros for the command values are also declared in the header file
fcntl.h. To use them, the macro _GNU_SOURCE must be
defined prior to including any header file.
In contrast to process-associated locks, any struct flock used as
an argument to open file description lock commands must have the l_pid
value set to 0. Also, when returning information about an
open file description lock in a F_GETLK or F_OFD_GETLK request,
the l_pid field in struct flock will be set to -1
to indicate that the lock is not associated with a process.
When the same struct flock is reused as an argument to a
F_OFD_SETLK or F_OFD_SETLKW request after being used for an
F_OFD_GETLK request, it is necessary to inspect and reset the
l_pid field to 0.
int F_OFD_GETLK ¶This macro is used as the command argument to fcntl, to
specify that it should get information about a lock. This command
requires a third argument of type struct flock * to be passed
to fcntl, so that the form of the call is:
fcntl (filedes, F_OFD_GETLK, lockp)
If there is a lock already in place that would block the lock described
by the lockp argument, information about that lock is written to
*lockp. Existing locks are not reported if they are
compatible with making a new lock as specified. Thus, you should
specify a lock type of F_WRLCK if you want to find out about both
read and write locks, or F_RDLCK if you want to find out about
write locks only.
There might be more than one lock affecting the region specified by the
lockp argument, but fcntl only returns information about
one of them. Which lock is returned in this situation is undefined.
The l_whence member of the lockp structure are set to
SEEK_SET and the l_start and l_len fields are set
to identify the locked region.
If no conflicting lock exists, the only change to the lockp structure
is to update the l_type field to the value F_UNLCK.
The normal return value from fcntl with this command is either 0
on success or -1, which indicates an error. The following errno
error conditions are defined for this command:
EBADFThe filedes argument is invalid.
EINVALEither the lockp argument doesn’t specify valid lock information, the operating system kernel doesn’t support open file description locks, or the file associated with filedes doesn’t support locks.
int F_OFD_SETLK ¶This macro is used as the command argument to fcntl, to
specify that it should set or clear a lock. This command requires a
third argument of type struct flock * to be passed to
fcntl, so that the form of the call is:
fcntl (filedes, F_OFD_SETLK, lockp)
If the open file already has a lock on any part of the
region, the old lock on that part is replaced with the new lock. You
can remove a lock by specifying a lock type of F_UNLCK.
If the lock cannot be set, fcntl returns immediately with a value
of -1. This command does not wait for other tasks
to release locks. If fcntl succeeds, it returns 0.
The following errno error conditions are defined for this
command:
EAGAINThe lock cannot be set because it is blocked by an existing lock on the file.
EBADFEither: the filedes argument is invalid; you requested a read lock but the filedes is not open for read access; or, you requested a write lock but the filedes is not open for write access.
EINVALEither the lockp argument doesn’t specify valid lock information, the operating system kernel doesn’t support open file description locks, or the file associated with filedes doesn’t support locks.
ENOLCKThe system has run out of file lock resources; there are already too many file locks in place.
Well-designed file systems never report this error, because they have no limitation on the number of locks. However, you must still take account of the possibility of this error, as it could result from network access to a file system on another machine.
int F_OFD_SETLKW ¶This macro is used as the command argument to fcntl, to
specify that it should set or clear a lock. It is just like the
F_OFD_SETLK command, but causes the process to wait until the request
can be completed.
This command requires a third argument of type struct flock *, as
for the F_OFD_SETLK command.
The fcntl return values and errors are the same as for the
F_OFD_SETLK command, but these additional errno error conditions
are defined for this command:
EINTRThe function was interrupted by a signal while it was waiting. See Primitives Interrupted by Signals.
Open file description locks are useful in the same sorts of situations as
process-associated locks. They can also be used to synchronize file
access between threads within the same process by having each thread perform
its own open of the file, to obtain its own open file description.
Because open file description locks are automatically freed only upon closing the last file descriptor that refers to the open file description, this locking mechanism avoids the possibility that locks are inadvertently released due to a library routine opening and closing a file without the application being aware.
As with process-associated locks, open file description locks are advisory.