jump to navigation

flock vs fcntl 2014 November 18 12:46

Posted by diamond in : Tech , trackback

Both flock(2) and fcntl(2) can create advisory locks on unix. What i hadn’t realised, until it bit me this morning, is that the semantics are subtly different. flock() creates a lock at the open file table level. fcntl() creates a lock at the file region level. This means that if you open a file twice, flock() will treat both FDs independently, whereas fcntl() treats them as being the same thing. Here’s a demonstration using python.

First, fcntl() (note that fcntl.lockf uses fcntl() underneath):


Python 2.7.3 (default, Mar 13 2014, 11:03:55)
[GCC 4.7.2] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import fcntl
>>> a=open("/tmp/testy", "w")
>>> b=open("/tmp/testy", "w")
>>> fcntl.lockf(a, fcntl.LOCK_EX | fcntl.LOCK_NB)
>>> fcntl.lockf(b, fcntl.LOCK_EX | fcntl.LOCK_NB)
>>>

Second, flock():

Python 2.7.3 (default, Mar 13 2014, 11:03:55)
[GCC 4.7.2] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import fcntl
>>> a=open("/tmp/testy", "w")
>>> b=open("/tmp/testy", "w")
>>> fcntl.flock(a, fcntl.LOCK_EX | fcntl.LOCK_NB)
>>> fcntl.flock(b, fcntl.LOCK_EX | fcntl.LOCK_NB)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
IOError: [Errno 11] Resource temporarily unavailable
>>>

The reason i came across this was i was trying to write unittests around some locking code, and couldn’t figure out why opening the same file twice and locking both FDs never failed. Eventually i spotted that flock() was working while fcntl() was not, and careful reading of the manpages indicated why 🙂

Comments»

no comments yet - be the first?