summaryrefslogtreecommitdiffstats
path: root/Python
diff options
context:
space:
mode:
authorDino Viehland <dinoviehland@meta.com>2024-04-22 05:57:05 (GMT)
committerGitHub <noreply@github.com>2024-04-22 05:57:05 (GMT)
commit8b541c017ea92040add608b3e0ef8dc85e9e6060 (patch)
tree880ff7c97041f374d21197b1b486686f2d64c998 /Python
parent1446024124fb98c3051199760380685f8a2fd127 (diff)
downloadcpython-8b541c017ea92040add608b3e0ef8dc85e9e6060.zip
cpython-8b541c017ea92040add608b3e0ef8dc85e9e6060.tar.gz
cpython-8b541c017ea92040add608b3e0ef8dc85e9e6060.tar.bz2
gh-112075: Make instance attributes stored in inline "dict" thread safe (#114742)
Make instance attributes stored in inline "dict" thread safe on free-threaded builds
Diffstat (limited to 'Python')
-rw-r--r--Python/bytecodes.c15
-rw-r--r--Python/executor_cases.c.h10
-rw-r--r--Python/generated_cases.c.h13
-rw-r--r--Python/specialize.c3
4 files changed, 17 insertions, 24 deletions
diff --git a/Python/bytecodes.c b/Python/bytecodes.c
index c1fbd3c..b7511b9 100644
--- a/Python/bytecodes.c
+++ b/Python/bytecodes.c
@@ -1947,15 +1947,13 @@ dummy_func(
op(_CHECK_ATTR_WITH_HINT, (owner -- owner)) {
assert(Py_TYPE(owner)->tp_flags & Py_TPFLAGS_MANAGED_DICT);
- PyManagedDictPointer *managed_dict = _PyObject_ManagedDictPointer(owner);
- PyDictObject *dict = managed_dict->dict;
+ PyDictObject *dict = _PyObject_GetManagedDict(owner);
DEOPT_IF(dict == NULL);
assert(PyDict_CheckExact((PyObject *)dict));
}
op(_LOAD_ATTR_WITH_HINT, (hint/1, owner -- attr, null if (oparg & 1))) {
- PyManagedDictPointer *managed_dict = _PyObject_ManagedDictPointer(owner);
- PyDictObject *dict = managed_dict->dict;
+ PyDictObject *dict = _PyObject_GetManagedDict(owner);
DEOPT_IF(hint >= (size_t)dict->ma_keys->dk_nentries);
PyObject *name = GETITEM(FRAME_CO_NAMES, oparg>>1);
if (DK_IS_UNICODE(dict->ma_keys)) {
@@ -2072,14 +2070,15 @@ dummy_func(
op(_GUARD_DORV_NO_DICT, (owner -- owner)) {
assert(Py_TYPE(owner)->tp_dictoffset < 0);
assert(Py_TYPE(owner)->tp_flags & Py_TPFLAGS_INLINE_VALUES);
- DEOPT_IF(_PyObject_ManagedDictPointer(owner)->dict);
+ DEOPT_IF(_PyObject_GetManagedDict(owner));
DEOPT_IF(_PyObject_InlineValues(owner)->valid == 0);
}
op(_STORE_ATTR_INSTANCE_VALUE, (index/1, value, owner --)) {
STAT_INC(STORE_ATTR, hit);
- assert(_PyObject_ManagedDictPointer(owner)->dict == NULL);
+ assert(_PyObject_GetManagedDict(owner) == NULL);
PyDictValues *values = _PyObject_InlineValues(owner);
+
PyObject *old_value = values->values[index];
values->values[index] = value;
if (old_value == NULL) {
@@ -2088,6 +2087,7 @@ dummy_func(
else {
Py_DECREF(old_value);
}
+
Py_DECREF(owner);
}
@@ -2102,8 +2102,7 @@ dummy_func(
assert(type_version != 0);
DEOPT_IF(tp->tp_version_tag != type_version);
assert(tp->tp_flags & Py_TPFLAGS_MANAGED_DICT);
- PyManagedDictPointer *managed_dict = _PyObject_ManagedDictPointer(owner);
- PyDictObject *dict = managed_dict->dict;
+ PyDictObject *dict = _PyObject_GetManagedDict(owner);
DEOPT_IF(dict == NULL);
assert(PyDict_CheckExact((PyObject *)dict));
PyObject *name = GETITEM(FRAME_CO_NAMES, oparg);
diff --git a/Python/executor_cases.c.h b/Python/executor_cases.c.h
index df87f91..841ce8c 100644
--- a/Python/executor_cases.c.h
+++ b/Python/executor_cases.c.h
@@ -1998,8 +1998,7 @@
PyObject *owner;
owner = stack_pointer[-1];
assert(Py_TYPE(owner)->tp_flags & Py_TPFLAGS_MANAGED_DICT);
- PyManagedDictPointer *managed_dict = _PyObject_ManagedDictPointer(owner);
- PyDictObject *dict = managed_dict->dict;
+ PyDictObject *dict = _PyObject_GetManagedDict(owner);
if (dict == NULL) {
UOP_STAT_INC(uopcode, miss);
JUMP_TO_JUMP_TARGET();
@@ -2015,8 +2014,7 @@
oparg = CURRENT_OPARG();
owner = stack_pointer[-1];
uint16_t hint = (uint16_t)CURRENT_OPERAND();
- PyManagedDictPointer *managed_dict = _PyObject_ManagedDictPointer(owner);
- PyDictObject *dict = managed_dict->dict;
+ PyDictObject *dict = _PyObject_GetManagedDict(owner);
if (hint >= (size_t)dict->ma_keys->dk_nentries) {
UOP_STAT_INC(uopcode, miss);
JUMP_TO_JUMP_TARGET();
@@ -2159,7 +2157,7 @@
owner = stack_pointer[-1];
assert(Py_TYPE(owner)->tp_dictoffset < 0);
assert(Py_TYPE(owner)->tp_flags & Py_TPFLAGS_INLINE_VALUES);
- if (_PyObject_ManagedDictPointer(owner)->dict) {
+ if (_PyObject_GetManagedDict(owner)) {
UOP_STAT_INC(uopcode, miss);
JUMP_TO_JUMP_TARGET();
}
@@ -2177,7 +2175,7 @@
value = stack_pointer[-2];
uint16_t index = (uint16_t)CURRENT_OPERAND();
STAT_INC(STORE_ATTR, hit);
- assert(_PyObject_ManagedDictPointer(owner)->dict == NULL);
+ assert(_PyObject_GetManagedDict(owner) == NULL);
PyDictValues *values = _PyObject_InlineValues(owner);
PyObject *old_value = values->values[index];
values->values[index] = value;
diff --git a/Python/generated_cases.c.h b/Python/generated_cases.c.h
index a426d9e..058cac8 100644
--- a/Python/generated_cases.c.h
+++ b/Python/generated_cases.c.h
@@ -4017,16 +4017,14 @@
// _CHECK_ATTR_WITH_HINT
{
assert(Py_TYPE(owner)->tp_flags & Py_TPFLAGS_MANAGED_DICT);
- PyManagedDictPointer *managed_dict = _PyObject_ManagedDictPointer(owner);
- PyDictObject *dict = managed_dict->dict;
+ PyDictObject *dict = _PyObject_GetManagedDict(owner);
DEOPT_IF(dict == NULL, LOAD_ATTR);
assert(PyDict_CheckExact((PyObject *)dict));
}
// _LOAD_ATTR_WITH_HINT
{
uint16_t hint = read_u16(&this_instr[4].cache);
- PyManagedDictPointer *managed_dict = _PyObject_ManagedDictPointer(owner);
- PyDictObject *dict = managed_dict->dict;
+ PyDictObject *dict = _PyObject_GetManagedDict(owner);
DEOPT_IF(hint >= (size_t)dict->ma_keys->dk_nentries, LOAD_ATTR);
PyObject *name = GETITEM(FRAME_CO_NAMES, oparg>>1);
if (DK_IS_UNICODE(dict->ma_keys)) {
@@ -5309,7 +5307,7 @@
{
assert(Py_TYPE(owner)->tp_dictoffset < 0);
assert(Py_TYPE(owner)->tp_flags & Py_TPFLAGS_INLINE_VALUES);
- DEOPT_IF(_PyObject_ManagedDictPointer(owner)->dict, STORE_ATTR);
+ DEOPT_IF(_PyObject_GetManagedDict(owner), STORE_ATTR);
DEOPT_IF(_PyObject_InlineValues(owner)->valid == 0, STORE_ATTR);
}
// _STORE_ATTR_INSTANCE_VALUE
@@ -5317,7 +5315,7 @@
{
uint16_t index = read_u16(&this_instr[4].cache);
STAT_INC(STORE_ATTR, hit);
- assert(_PyObject_ManagedDictPointer(owner)->dict == NULL);
+ assert(_PyObject_GetManagedDict(owner) == NULL);
PyDictValues *values = _PyObject_InlineValues(owner);
PyObject *old_value = values->values[index];
values->values[index] = value;
@@ -5380,8 +5378,7 @@
assert(type_version != 0);
DEOPT_IF(tp->tp_version_tag != type_version, STORE_ATTR);
assert(tp->tp_flags & Py_TPFLAGS_MANAGED_DICT);
- PyManagedDictPointer *managed_dict = _PyObject_ManagedDictPointer(owner);
- PyDictObject *dict = managed_dict->dict;
+ PyDictObject *dict = _PyObject_GetManagedDict(owner);
DEOPT_IF(dict == NULL, STORE_ATTR);
assert(PyDict_CheckExact((PyObject *)dict));
PyObject *name = GETITEM(FRAME_CO_NAMES, oparg);
diff --git a/Python/specialize.c b/Python/specialize.c
index 5e14bb5..ee51781 100644
--- a/Python/specialize.c
+++ b/Python/specialize.c
@@ -852,8 +852,7 @@ specialize_dict_access(
instr->op.code = values_op;
}
else {
- PyManagedDictPointer *managed_dict = _PyObject_ManagedDictPointer(owner);
- PyDictObject *dict = managed_dict->dict;
+ PyDictObject *dict = _PyObject_GetManagedDict(owner);
if (dict == NULL || !PyDict_CheckExact(dict)) {
SPECIALIZATION_FAIL(base_op, SPEC_FAIL_NO_DICT);
return 0;