Skip to content
Merged
Show file tree
Hide file tree
Changes from 8 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions Include/internal/pycore_dict.h
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,10 @@ PyAPI_FUNC(int) _PyDict_SetItem_KnownHash(PyObject *mp, PyObject *key,
// Export for '_asyncio' shared extension
PyAPI_FUNC(int) _PyDict_DelItem_KnownHash(PyObject *mp, PyObject *key,
Py_hash_t hash);

extern int _PyDict_DelItem_KnownHash_LockHeld(PyObject *mp, PyObject *key,
Py_hash_t hash);

extern int _PyDict_Contains_KnownHash(PyObject *, PyObject *, Py_hash_t);

// "Id" variants
Expand All @@ -47,6 +51,8 @@ extern int _PyDict_HasOnlyStringKeys(PyObject *mp);
// Export for '_ctypes' shared extension
PyAPI_FUNC(Py_ssize_t) _PyDict_SizeOf(PyDictObject *);

extern Py_ssize_t _PyDict_SizeOf_LockHeld(PyDictObject *);

#define _PyDict_HasSplitTable(d) ((d)->ma_values != NULL)

/* Like PyDict_Merge, but override can be 0, 1 or 2. If override is 0,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Fix thread safety of :class:`collections.OrderedDict`. Patch by Kumar Aditya.
106 changes: 105 additions & 1 deletion Objects/clinic/odictobject.c.h

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

16 changes: 9 additions & 7 deletions Objects/dictobject.c
Original file line number Diff line number Diff line change
Expand Up @@ -2819,8 +2819,8 @@ PyDict_DelItem(PyObject *op, PyObject *key)
return _PyDict_DelItem_KnownHash(op, key, hash);
}

static int
delitem_knownhash_lock_held(PyObject *op, PyObject *key, Py_hash_t hash)
int
_PyDict_DelItem_KnownHash_LockHeld(PyObject *op, PyObject *key, Py_hash_t hash)
{
Py_ssize_t ix;
PyDictObject *mp;
Expand Down Expand Up @@ -2855,7 +2855,7 @@ _PyDict_DelItem_KnownHash(PyObject *op, PyObject *key, Py_hash_t hash)
{
int res;
Py_BEGIN_CRITICAL_SECTION(op);
res = delitem_knownhash_lock_held(op, key, hash);
res = _PyDict_DelItem_KnownHash_LockHeld(op, key, hash);
Py_END_CRITICAL_SECTION();
return res;
}
Expand Down Expand Up @@ -4703,9 +4703,11 @@ dict_tp_clear(PyObject *op)

static PyObject *dictiter_new(PyDictObject *, PyTypeObject *);

static Py_ssize_t
sizeof_lock_held(PyDictObject *mp)
Py_ssize_t
_PyDict_SizeOf_LockHeld(PyDictObject *mp)
{
_Py_CRITICAL_SECTION_ASSERT_OBJECT_LOCKED(mp);

size_t res = _PyObject_SIZE(Py_TYPE(mp));
if (_PyDict_HasSplitTable(mp)) {
res += shared_keys_usable_size(mp->ma_keys) * sizeof(PyObject*);
Expand All @@ -4724,7 +4726,7 @@ _PyDict_SizeOf(PyDictObject *mp)
{
Py_ssize_t res;
Py_BEGIN_CRITICAL_SECTION(mp);
res = sizeof_lock_held(mp);
res = _PyDict_SizeOf_LockHeld(mp);
Py_END_CRITICAL_SECTION();

return res;
Expand Down Expand Up @@ -6909,7 +6911,7 @@ _PyDict_SetItem_LockHeld(PyDictObject *dict, PyObject *name, PyObject *value)
dict_unhashable_type(name);
return -1;
}
return delitem_knownhash_lock_held((PyObject *)dict, name, hash);
return _PyDict_DelItem_KnownHash_LockHeld((PyObject *)dict, name, hash);
} else {
return setitem_lock_held(dict, name, value);
}
Expand Down
Loading
Loading