Issue #3001: Add a C implementation of recursive locks which is used by
default when instantiating a `Threading.RLock` object. This makes
recursive locks as fast as regular non-recursive locks (previously,
they were slower by 10x to 15x).
diff --git a/Lib/test/test_threading.py b/Lib/test/test_threading.py
index 41f57dc..330a2c5 100644
--- a/Lib/test/test_threading.py
+++ b/Lib/test/test_threading.py
@@ -506,8 +506,11 @@
 class LockTests(lock_tests.LockTests):
     locktype = staticmethod(threading.Lock)
 
-class RLockTests(lock_tests.RLockTests):
-    locktype = staticmethod(threading.RLock)
+class PyRLockTests(lock_tests.RLockTests):
+    locktype = staticmethod(threading._PyRLock)
+
+class CRLockTests(lock_tests.RLockTests):
+    locktype = staticmethod(threading._CRLock)
 
 class EventTests(lock_tests.EventTests):
     eventtype = staticmethod(threading.Event)
@@ -527,7 +530,7 @@
 
 
 def test_main():
-    test.support.run_unittest(LockTests, RLockTests, EventTests,
+    test.support.run_unittest(LockTests, PyRLockTests, CRLockTests, EventTests,
                               ConditionAsRLockTests, ConditionTests,
                               SemaphoreTests, BoundedSemaphoreTests,
                               ThreadTests,
diff --git a/Lib/threading.py b/Lib/threading.py
index 4bb0182..0e77060 100644
--- a/Lib/threading.py
+++ b/Lib/threading.py
@@ -27,6 +27,10 @@
 _allocate_lock = _thread.allocate_lock
 _get_ident = _thread.get_ident
 ThreadError = _thread.error
+try:
+    _CRLock = _thread.RLock
+except AttributeError:
+    _CRLock = None
 del _thread
 
 
@@ -79,8 +83,12 @@
 
 Lock = _allocate_lock
 
-def RLock(*args, **kwargs):
-    return _RLock(*args, **kwargs)
+def RLock(verbose=None, *args, **kwargs):
+    if verbose is None:
+        verbose = _VERBOSE
+    if (__debug__ and verbose) or _CRLock is None:
+        return _PyRLock(verbose, *args, **kwargs)
+    return _CRLock(*args, **kwargs)
 
 class _RLock(_Verbose):
 
@@ -156,6 +164,8 @@
     def _is_owned(self):
         return self._owner == _get_ident()
 
+_PyRLock = _RLock
+
 
 def Condition(*args, **kwargs):
     return _Condition(*args, **kwargs)