Understanding when to use and not use the -F
option for flock(1)
A while back I wrote some notes on understanding how to use
flock(1)
, but those notes omitted a potentially
important option, partly because that option was added somewhere
in between version util-linux version 2.27.1 (which is what Ubuntu
16.04 has) and version 2.31.1 (Ubuntu 18.04). That is the -F
option, which is described in the manpage as:
Do not fork before executing command. Upon execution the flock process is replaced by command which continues to hold the lock. [...]
This option is incompatible with -o
, as mentioned in the manpage.
The straightforward situation where you very much want to use -F
is if you're trying to run a program that reacts specially to
Control-C. If you run 'flock
program
', there will still be a flock
process, it will get
Control-C and exit, and undesirable things will probably happen.
If you use 'flock -F program
', there is only the program and it
can react properly to Control-C without any side effects on other
processes.
(I'm assuming here that if you ran flock
and the program from
inside a shell script, you ran it with 'exec flock ...
'. If you're
in a situation where you have to do things in your shell script
after the program finishes, you can't solve the Control-C problem
just with this.)
However, there is also a situation where you don't want to use -F
,
and to see it we need to understand how the flock
lock is continued
to be held by the command. As covered in the first note, flock(1)
works through flock(2)
, which means
that the lock is 'held' by having the flock()
'd file descriptor
still be open. Most programs are indifferent to inheriting extra
file descriptors, so this additional descriptor from flock
just
hangs around, keeping the lock held. However, some programs actively
seek out and close file descriptors they may have inherited, often
to avoid leaking them into child processes. If you use 'flock -F
'
with such a program, your lock will be released prematurely (before
the program exits) when the program does this.
(The existence of such programs is probably part of why flock -F
is not the default behavior.)
Sidebar: Faking 'flock -F
' if you don't have it
If you have a shell script that has to run on Ubuntu 16.04 and you
need this behavior, you can fake it with 'flock -o
'. It goes like
this:
exec 9 >>/some/lockfile flock -x -n 9 || exit 0 exec program ...
Since 'flock -F
' locks some file descriptor and then exec's the
program, we can imitate it by doing the same manually; we pick a
random file descriptor number, get the shell to open a file on that
file descriptor and leave it open, flock
that file descriptor,
and then have the shell exec our program. Our program will inherit
the locked fd 9 and the lock remains for as long as fd 9 is open.
When the program exits, all of its file descriptors will be closed,
including fd 9, and the lock will be released.
|
|