8000 gh-133980: use atomic store in `PyObject_GenericSetDict` (#133988) · python/cpython@ec39fd2 · GitHub
[go: up one dir, main page]

Skip to content

Commit ec39fd2

Browse files
gh-133980: use atomic store in PyObject_GenericSetDict (#133988)
1 parent 317c496 commit ec39fd2

File tree

2 files changed

+23
-1
lines changed

2 files changed

+23
-1
lines changed

Lib/test/test_free_threading/test_dict.py

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -228,6 +228,22 @@ def reader_func():
228228

229229
self.assertEqual(count, 0)
230230

231+
def test_racing_object_get_set_dict(self):
232+
e = Exception()
233+
234+
def writer():
235+
for i in range(10000):
236+
e.__dict__ = {1:2}
237+
238+
def reader():
239+
for i in range(10000):
240+
e.__dict__
241+
242+
t1 = Thread(target=writer)
243+
t2 = Thread(target=reader)
244+
245+
with threading_helper.start_threads([t1, t2]):
246+
pass
231247

232248
if __name__ == "__main__":
233249
unittest.main()

Objects/object.c

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1931,7 +1931,13 @@ PyObject_GenericSetDict(PyObject *obj, PyObject *value, void *context)
19311931
return -1;
19321932
}
19331933
Py_BEGIN_CRITICAL_SECTION(obj);
1934-
Py_XSETREF(*dictptr, Py_NewRef(value));
1934+
PyObject *olddict = *dictptr;
1935+
FT_ATOMIC_STORE_PTR_RELEASE(*dictptr, Py_NewRef(value));
1936+
#ifdef Py_GIL_DISABLED
1937+
_PyObject_XDecRefDelayed(olddict);
1938+
#else
1939+
Py_XDECREF(olddict);
1940+
#endif
19351941
Py_END_CRITICAL_SECTION();
19361942
return 0;
19371943
}

0 commit comments

Comments
 (0)
0