[Python-checkins] r80157 - in python/branches/py3k: Doc/library/threading.rst Lib/test/lock_tests.py Lib/threading.py Misc/ACKS Misc/NEWS

antoine.pitrou python-checkins at python.org
Sun Apr 18 01:51:58 CEST 2010


Author: antoine.pitrou
Date: Sun Apr 18 01:51:58 2010
New Revision: 80157

Log:
Issue #850728: Add a *timeout* parameter to the `acquire()` method of
`threading.Semaphore` objects.  Original patch by Torsten Landschoff.



Modified:
   python/branches/py3k/Doc/library/threading.rst
   python/branches/py3k/Lib/test/lock_tests.py
   python/branches/py3k/Lib/threading.py
   python/branches/py3k/Misc/ACKS
   python/branches/py3k/Misc/NEWS

Modified: python/branches/py3k/Doc/library/threading.rst
==============================================================================
--- python/branches/py3k/Doc/library/threading.rst	(original)
+++ python/branches/py3k/Doc/library/threading.rst	Sun Apr 18 01:51:58 2010
@@ -596,7 +596,7 @@
    defaults to ``1``. If the *value* given is less than 0, :exc:`ValueError` is
    raised.
 
-   .. method:: acquire(blocking=True)
+   .. method:: acquire(blocking=True, timeout=None)
 
       Acquire a semaphore.
 
@@ -607,14 +607,18 @@
       interlocking so that if multiple :meth:`acquire` calls are blocked,
       :meth:`release` will wake exactly one of them up.  The implementation may
       pick one at random, so the order in which blocked threads are awakened
-      should not be relied on.  There is no return value in this case.
-
-      When invoked with *blocking* set to true, do the same thing as when called
-      without arguments, and return true.
+      should not be relied on.  Returns true (or blocks indefinitely).
 
       When invoked with *blocking* set to false, do not block.  If a call
-      without an argument would block, return false immediately; otherwise, do
-      the same thing as when called without arguments, and return true.
+      without an argument would block, return false immediately; otherwise,
+      do the same thing as when called without arguments, and return true.
+
+      When invoked with a *timeout* other than None, it will block for at
+      most *timeout* seconds.  If acquire does not complete successfully in
+      that interval, return false.  Return true otherwise.
+
+      .. versionchanged:: 3.2
+         The *timeout* parameter is new.
 
    .. method:: release()
 

Modified: python/branches/py3k/Lib/test/lock_tests.py
==============================================================================
--- python/branches/py3k/Lib/test/lock_tests.py	(original)
+++ python/branches/py3k/Lib/test/lock_tests.py	Sun Apr 18 01:51:58 2010
@@ -521,6 +521,19 @@
         # ordered.
         self.assertEqual(sorted(results), [False] * 7 + [True] *  3 )
 
+    def test_acquire_timeout(self):
+        sem = self.semtype(2)
+        self.assertRaises(ValueError, sem.acquire, False, timeout=1.0)
+        self.assertTrue(sem.acquire(timeout=0.005))
+        self.assertTrue(sem.acquire(timeout=0.005))
+        self.assertFalse(sem.acquire(timeout=0.005))
+        sem.release()
+        self.assertTrue(sem.acquire(timeout=0.005))
+        t = time.time()
+        self.assertFalse(sem.acquire(timeout=0.5))
+        dt = time.time() - t
+        self.assertTimeout(dt, 0.5)
+
     def test_default_value(self):
         # The default initial value is 1.
         sem = self.semtype()

Modified: python/branches/py3k/Lib/threading.py
==============================================================================
--- python/branches/py3k/Lib/threading.py	(original)
+++ python/branches/py3k/Lib/threading.py	Sun Apr 18 01:51:58 2010
@@ -290,8 +290,11 @@
         self._cond = Condition(Lock())
         self._value = value
 
-    def acquire(self, blocking=True):
+    def acquire(self, blocking=True, timeout=None):
+        if not blocking and timeout is not None:
+            raise ValueError("can't specify timeout for non-blocking acquire")
         rc = False
+        endtime = None
         self._cond.acquire()
         while self._value == 0:
             if not blocking:
@@ -299,7 +302,14 @@
             if __debug__:
                 self._note("%s.acquire(%s): blocked waiting, value=%s",
                            self, blocking, self._value)
-            self._cond.wait()
+            if timeout is not None:
+                if endtime is None:
+                    endtime = _time() + timeout
+                else:
+                    timeout = endtime - _time()
+                    if timeout <= 0:
+                        break
+            self._cond.wait(timeout)
         else:
             self._value = self._value - 1
             if __debug__:

Modified: python/branches/py3k/Misc/ACKS
==============================================================================
--- python/branches/py3k/Misc/ACKS	(original)
+++ python/branches/py3k/Misc/ACKS	Sun Apr 18 01:51:58 2010
@@ -431,6 +431,7 @@
 Andrew Kuchling
 Vladimir Kushnir
 Cameron Laird
+Torsten Landschoff
 Tino Lange
 Andrew Langmead
 Detlef Lannert

Modified: python/branches/py3k/Misc/NEWS
==============================================================================
--- python/branches/py3k/Misc/NEWS	(original)
+++ python/branches/py3k/Misc/NEWS	Sun Apr 18 01:51:58 2010
@@ -315,6 +315,9 @@
 Library
 -------
 
+- Issue #850728: Add a *timeout* parameter to the `acquire()` method of
+  `threading.Semaphore` objects.  Patch by Torsten Landschoff.
+
 - Issue #8322: Add a *ciphers* argument to SSL sockets, so as to change the
   available cipher list.  Helps fix test_ssl with OpenSSL 1.0.0.
 


More information about the Python-checkins mailing list