Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP

Loading…

LRUCache may fail to release lock #10

Closed
snordhausen opened this Issue · 3 comments

2 participants

@snordhausen

Locking in LRUCache is done like this:

self.lock.acquire()
try:
  something()
finally:
  self.lock.release()

This will fail to release the lock in case an exception occurs after the acquire() but before the try: block is entered. Such an exception could be a KeyboardError that is caused by somebody pressing CTRL+C on a program running in a terminal.

To check that this really happens, I wrote the below program and pressed CTRL+C while it was running. Failed 7 out of 10 times for me. Much less likely to happen in a real program, but still a race condition.

#!/usr/bin/python
import threading
LOCK = threading.Lock()
def run():
    while 1:
        LOCK.acquire()
        try:
            pass
        finally:
            LOCK.release()
if __name__ == "__main__":
    try:
        run()
    finally:
        if LOCK.locked():
            print "ooops"
        else:
            print "OK"
@snordhausen

After consulting the local Python guru it seems impossible to reliably release a lock in any reasonable way in Python. With "reasonable" being defined as "without interfering with the program using the LRUCache". The program using the LRUCache (or anything else that uses locking) will need to set up a signal handler at the very least.

@tseaver
Owner

We might get away with using the 'with' statement to make the window smaller. I can't make the following variation oops at all:

#!/usr/bin/python
import threading
LOCK = threading.Lock()
def run():
    while 1:
        with LOCK:
            pass
if __name__ == "__main__":
    try:
        run()
    finally:
        if LOCK.locked():
            print "ooops"
        else:
            print "OK"
@tseaver
Owner

The trunk now uses 'with' on all locks to avoid this race.

@tseaver tseaver closed this
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Something went wrong with that request. Please try again.