mirror of
https://github.com/python/cpython.git
synced 2026-06-28 03:41:13 +00:00
gh-150902: Optimize PyCriticalSection2 to skip locking the same locks held by the current CS2
This mimics an optimization already present for the single-mutex critical section.
This commit is contained in:
parent
7edcaedc53
commit
c2ca7724af
3 changed files with 20 additions and 4 deletions
|
|
@ -196,10 +196,9 @@ _PyCriticalSection2_Begin(PyThreadState *tstate, PyCriticalSection2 *c, PyObject
|
|||
static inline void
|
||||
_PyCriticalSection2_End(PyThreadState *tstate, PyCriticalSection2 *c)
|
||||
{
|
||||
// if mutex1 is NULL, we used the fast path in
|
||||
// _PyCriticalSection_BeginSlow for mutexes that are already held,
|
||||
// which should only happen when mutex1 and mutex2 were the same mutex,
|
||||
// and mutex2 should also be NULL.
|
||||
// if mutex1 is NULL, we used the fast path in either
|
||||
// _PyCriticalSection_BeginSlow or _PyCriticalSection2_BeginSlow for mutexes
|
||||
// that are already held, and mutex2 should also be NULL.
|
||||
if (c->_cs_base._cs_mutex == NULL) {
|
||||
assert(c->_cs_mutex2 == NULL);
|
||||
return;
|
||||
|
|
|
|||
|
|
@ -0,0 +1 @@
|
|||
Apply an existing optimization of PyCriticalSection (single mutex) to PyCriticalSection2: avoid acquiring the same locks that the current CS has already acquired.
|
||||
|
|
@ -72,6 +72,22 @@ _PyCriticalSection2_BeginSlow(PyThreadState *tstate, PyCriticalSection2 *c, PyMu
|
|||
c->_cs_base._cs_prev = 0;
|
||||
return;
|
||||
}
|
||||
// Same optimization as in _PyCriticalSection_BeginSlow: skip locking when
|
||||
// recursively acquiring the same locks.
|
||||
if (tstate->critical_section &&
|
||||
tstate->critical_section & _Py_CRITICAL_SECTION_TWO_MUTEXES) {
|
||||
PyCriticalSection2 *prev2 = (PyCriticalSection2 *)
|
||||
untag_critical_section(tstate->critical_section);
|
||||
assert((uintptr_t)m1 < (uintptr_t)m2);
|
||||
assert((uintptr_t)prev2->_cs_base._cs_mutex <
|
||||
(uintptr_t)prev2->_cs_mutex2);
|
||||
if (prev2->_cs_base._cs_mutex == m1 && prev2->_cs_mutex2 == m2) {
|
||||
c->_cs_base._cs_mutex = NULL;
|
||||
c->_cs_mutex2 = NULL;
|
||||
c->_cs_base._cs_prev = 0;
|
||||
return;
|
||||
}
|
||||
}
|
||||
c->_cs_base._cs_mutex = NULL;
|
||||
c->_cs_mutex2 = NULL;
|
||||
c->_cs_base._cs_prev = tstate->critical_section;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue