1 # portalocker.py - Cross-platform (posix/nt) API for flock-style file locking.
2 # Requires python 1.5.2 or better.
4 # ID line added by richard for Roundup file tracking
5 # $Id: portalocker.py,v 1.9 2006-09-09 05:42:45 richard Exp $
7 """Cross-platform (posix/nt) API for flock-style file locking.
12 file = open("somefile", "r+")
13 portalocker.lock(file, portalocker.LOCK_EX)
18 If you know what you're doing, you may choose to::
20 portalocker.unlock(file)
22 before closing the file, but why?
35 I learned the win32 technique for locking files from sample code
36 provided by John Nielsen <nielsenjf@my-deja.com> in the documentation
37 that accompanies the win32 modules.
39 :Author: Jonathan Feinberg <jdf@pobox.com>
40 :Version: Id: portalocker.py,v 1.3 2001/05/29 18:47:55 Administrator Exp
41 **un-cvsified by richard so the version doesn't change**
43 __docformat__
= 'restructuredtext'
51 LOCK_EX
= win32con
.LOCKFILE_EXCLUSIVE_LOCK
52 LOCK_SH
= 0 # the default
53 LOCK_NB
= win32con
.LOCKFILE_FAIL_IMMEDIATELY
54 # is there any reason not to reuse the following structure?
55 __overlapped
= pywintypes
.OVERLAPPED()
56 elif os
.name
== 'posix':
58 LOCK_EX
= fcntl
.LOCK_EX
59 LOCK_SH
= fcntl
.LOCK_SH
60 LOCK_NB
= fcntl
.LOCK_NB
62 raise RuntimeError("PortaLocker only defined for nt and posix platforms")
65 # eugh, we want 0xffff0000 here, but python 2.3 won't let us :(
67 def lock(file, flags
):
68 hfile
= win32file
._get_osfhandle(file.fileno())
69 # LockFileEx is not supported on all Win32 platforms (Win95, Win98,
71 # If it's not supported, win32file will raise an exception.
72 # Try LockFileEx first, as it has more functionality and handles
73 # blocking locks more efficiently.
75 win32file
.LockFileEx(hfile
, flags
, 0, FFFF0000
, __overlapped
)
76 except win32file
.error
, e
:
78 # Propagate upwards all exceptions other than not-implemented.
79 if e
[0] != winerror
.ERROR_CALL_NOT_IMPLEMENTED
:
82 # LockFileEx is not supported. Use LockFile.
83 # LockFile does not support shared locking -- always exclusive.
84 # Care: the low/high length params are reversed compared to
86 if not flags
& LOCK_EX
:
88 warnings
.warn("PortaLocker does not support shared "
89 "locking on Win9x", RuntimeWarning)
90 # LockFile only supports immediate-fail locking.
92 win32file
.LockFile(hfile
, 0, 0, FFFF0000
, 0)
94 # Emulate a blocking lock with a polling loop.
99 win32file
.LockFile(hfile
, 0, 0, FFFF0000
, 0)
101 except win32file
.error
, e
:
102 # Propagate upwards all exceptions other than lock
104 if e
[0] != winerror
.ERROR_LOCK_VIOLATION
:
106 # Sleep and poll again.
108 # TODO: should this return the result of the lock?
111 hfile
= win32file
._get_osfhandle(file.fileno())
112 # UnlockFileEx is not supported on all Win32 platforms (Win95, Win98,
114 # If it's not supported, win32file will raise an api_error exception.
116 win32file
.UnlockFileEx(hfile
, 0, FFFF0000
, __overlapped
)
117 except win32file
.error
, e
:
119 # Propagate upwards all exceptions other than not-implemented.
120 if e
[0] != winerror
.ERROR_CALL_NOT_IMPLEMENTED
:
123 # UnlockFileEx is not supported. Use UnlockFile.
124 # Care: the low/high length params are reversed compared to
126 win32file
.UnlockFile(hfile
, 0, 0, FFFF0000
, 0)
128 elif os
.name
=='posix':
129 def lock(file, flags
):
130 fcntl
.flock(file.fileno(), flags
)
131 # TODO: should this return the result of the lock?
134 fcntl
.flock(file.fileno(), fcntl
.LOCK_UN
)
136 if __name__
== '__main__':
137 from time
import time
, strftime
, localtime
140 log
= open('log.txt', "a+")
143 timestamp
= strftime("%m/%d/%Y %H:%M:%S\n", localtime(time()))
144 log
.write( timestamp
)
146 print "Wrote lines. Hit enter to release lock."
147 dummy
= sys
.stdin
.readline()