Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commitfc2cb86

Browse files
authored
gh-107073: Make PyObject_VisitManagedDict() public (#108763)
Make PyObject_VisitManagedDict() and PyObject_ClearManagedDict()functions public in Python 3.13 C API.* Rename _PyObject_VisitManagedDict() to PyObject_VisitManagedDict().* Rename _PyObject_ClearManagedDict() to PyObject_ClearManagedDict().* Document these functions.
1 parent6387b53 commitfc2cb86

File tree

12 files changed

+77
-24
lines changed

12 files changed

+77
-24
lines changed

‎Doc/c-api/object.rst‎

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -489,3 +489,21 @@ Object Protocol
489489
:c:macro:`Py_TPFLAGS_ITEMS_AT_END` set.
490490
491491
..versionadded::3.12
492+
493+
..c:function::intPyObject_VisitManagedDict(PyObject *obj, visitproc visit, void *arg)
494+
495+
Visit the managed dictionary of *obj*.
496+
497+
This function must only be called in a traverse function of the type which
498+
has the:c:macro:`Py_TPFLAGS_MANAGED_DICT` flag set.
499+
500+
..versionadded::3.13
501+
502+
..c:function::voidPyObject_ClearManagedDict(PyObject *obj)
503+
504+
Clear the managed dictionary of *obj*.
505+
506+
This function must only be called in a traverse function of the type which
507+
has the:c:macro:`Py_TPFLAGS_MANAGED_DICT` flag set.
508+
509+
..versionadded::3.13

‎Doc/c-api/typeobj.rst‎

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1131,6 +1131,9 @@ and :c:data:`PyType_Type` effectively act as defaults.)
11311131

11321132
If this flag is set,:c:macro:`Py_TPFLAGS_HAVE_GC` should also be set.
11331133

1134+
The type traverse function must call:c:func:`PyObject_VisitManagedDict`
1135+
and its clear function must call:c:func:`PyObject_ClearManagedDict`.
1136+
11341137
..versionadded::3.12
11351138

11361139
**Inheritance:**
@@ -1368,6 +1371,23 @@ and :c:data:`PyType_Type` effectively act as defaults.)
13681371
debugging aid you may want to visit it anyway just so the:mod:`gc` module's
13691372
:func:`~gc.get_referents` function will include it.
13701373

1374+
Heap types (:c:macro:`Py_TPFLAGS_HEAPTYPE`) must visit their type with::
1375+
1376+
Py_VISIT(Py_TYPE(self));
1377+
1378+
It is only needed since Python 3.9. To support Python 3.8 and older, this
1379+
line must be conditionnal::
1380+
1381+
#if PY_VERSION_HEX >= 0x03090000
1382+
Py_VISIT(Py_TYPE(self));
1383+
#endif
1384+
1385+
If the:c:macro:`Py_TPFLAGS_MANAGED_DICT` bit is set in the
1386+
:c:member:`~PyTypeObject.tp_flags` field, the traverse function must call
1387+
:c:func:`PyObject_VisitManagedDict` like this::
1388+
1389+
PyObject_VisitManagedDict((PyObject*)self, visit, arg);
1390+
13711391
..warning::
13721392
When implementing:c:member:`~PyTypeObject.tp_traverse`, only the
13731393
members that the instance *owns* (by having:term:`strong references
@@ -1451,6 +1471,12 @@ and :c:data:`PyType_Type` effectively act as defaults.)
14511471
so that *self* knows the contained object can no longer be used. The
14521472
:c:func:`Py_CLEAR` macro performs the operations in a safe order.
14531473

1474+
If the:c:macro:`Py_TPFLAGS_MANAGED_DICT` bit is set in the
1475+
:c:member:`~PyTypeObject.tp_flags` field, the traverse function must call
1476+
:c:func:`PyObject_ClearManagedDict` like this::
1477+
1478+
PyObject_ClearManagedDict((PyObject*)self);
1479+
14541480
Note that:c:member:`~PyTypeObject.tp_clear` is not *always* called
14551481
before an instance is deallocated. For example, when reference counting
14561482
is enough to determine that an object is no longer used, the cyclic garbage
@@ -1801,7 +1827,7 @@ and :c:data:`PyType_Type` effectively act as defaults.)
18011827
field is ``NULL`` then no:attr:`~object.__dict__` gets created for instances.
18021828

18031829
If the:c:macro:`Py_TPFLAGS_MANAGED_DICT` bit is set in the
1804-
:c:member:`~PyTypeObject.tp_dict` field, then
1830+
:c:member:`~PyTypeObject.tp_flags` field, then
18051831
:c:member:`~PyTypeObject.tp_dictoffset` will be set to ``-1``, to indicate
18061832
that it is unsafe to use this field.
18071833

‎Doc/whatsnew/3.12.rst‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2123,7 +2123,7 @@ Porting to Python 3.12
21232123
The use of ``tp_dictoffset`` and ``tp_weaklistoffset`` is still
21242124
supported, but does not fully support multiple inheritance
21252125
(:gh:`95589`), and performance may be worse.
2126-
Classes declaring:c:macro:`Py_TPFLAGS_MANAGED_DICT`should call
2126+
Classes declaring:c:macro:`Py_TPFLAGS_MANAGED_DICT`must call
21272127
:c:func:`!_PyObject_VisitManagedDict` and:c:func:`!_PyObject_ClearManagedDict`
21282128
to traverse and clear their instance's dictionaries.
21292129
To clear weakrefs, call:c:func:`PyObject_ClearWeakRefs`, as before.

‎Doc/whatsnew/3.13.rst‎

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -995,6 +995,12 @@ New Features
995995
references) now supports the:ref:`Limited API<limited-c-api>`.
996996
(Contributed by Victor Stinner in:gh:`108634`.)
997997

998+
* Add:c:func:`PyObject_VisitManagedDict` and
999+
:c:func:`PyObject_ClearManagedDict` functions which must be called by the
1000+
traverse and clear functions of a type using
1001+
:c:macro:`Py_TPFLAGS_MANAGED_DICT` flag.
1002+
(Contributed by Victor Stinner in:gh:`107073`.)
1003+
9981004
Porting to Python 3.13
9991005
----------------------
10001006

‎Include/cpython/object.h‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -444,8 +444,8 @@ PyAPI_FUNC(int) _PyTrash_cond(PyObject *op, destructor dealloc);
444444

445445
PyAPI_FUNC(void*)PyObject_GetItemData(PyObject*obj);
446446

447-
PyAPI_FUNC(int)_PyObject_VisitManagedDict(PyObject*obj,visitprocvisit,void*arg);
448-
PyAPI_FUNC(void)_PyObject_ClearManagedDict(PyObject*obj);
447+
PyAPI_FUNC(int)PyObject_VisitManagedDict(PyObject*obj,visitprocvisit,void*arg);
448+
PyAPI_FUNC(void)PyObject_ClearManagedDict(PyObject*obj);
449449

450450
#defineTYPE_MAX_WATCHERS 8
451451

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
Add:c:func:`PyObject_VisitManagedDict` and:c:func:`PyObject_ClearManagedDict`
2+
functions which must be called by the traverse and clear functions of a type
3+
using:c:macro:`Py_TPFLAGS_MANAGED_DICT` flag. Patch by Victor Stinner.

‎Modules/_asynciomodule.c‎

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -816,7 +816,7 @@ FutureObj_clear(FutureObj *fut)
816816
Py_CLEAR(fut->fut_source_tb);
817817
Py_CLEAR(fut->fut_cancel_msg);
818818
Py_CLEAR(fut->fut_cancelled_exc);
819-
_PyObject_ClearManagedDict((PyObject*)fut);
819+
PyObject_ClearManagedDict((PyObject*)fut);
820820
return0;
821821
}
822822

@@ -834,7 +834,7 @@ FutureObj_traverse(FutureObj *fut, visitproc visit, void *arg)
834834
Py_VISIT(fut->fut_source_tb);
835835
Py_VISIT(fut->fut_cancel_msg);
836836
Py_VISIT(fut->fut_cancelled_exc);
837-
_PyObject_VisitManagedDict((PyObject*)fut,visit,arg);
837+
PyObject_VisitManagedDict((PyObject*)fut,visit,arg);
838838
return0;
839839
}
840840

@@ -2181,7 +2181,7 @@ TaskObj_traverse(TaskObj *task, visitproc visit, void *arg)
21812181
Py_VISIT(fut->fut_source_tb);
21822182
Py_VISIT(fut->fut_cancel_msg);
21832183
Py_VISIT(fut->fut_cancelled_exc);
2184-
_PyObject_VisitManagedDict((PyObject*)fut,visit,arg);
2184+
PyObject_VisitManagedDict((PyObject*)fut,visit,arg);
21852185
return0;
21862186
}
21872187

‎Modules/_testcapi/heaptype.c‎

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -805,21 +805,21 @@ static int
805805
heapmanaged_traverse(HeapCTypeObject*self,visitprocvisit,void*arg)
806806
{
807807
Py_VISIT(Py_TYPE(self));
808-
return_PyObject_VisitManagedDict((PyObject*)self,visit,arg);
808+
returnPyObject_VisitManagedDict((PyObject*)self,visit,arg);
809809
}
810810

811811
staticint
812812
heapmanaged_clear(HeapCTypeObject*self)
813813
{
814-
_PyObject_ClearManagedDict((PyObject*)self);
814+
PyObject_ClearManagedDict((PyObject*)self);
815815
return0;
816816
}
817817

818818
staticvoid
819819
heapmanaged_dealloc(HeapCTypeObject*self)
820820
{
821821
PyTypeObject*tp=Py_TYPE(self);
822-
_PyObject_ClearManagedDict((PyObject*)self);
822+
PyObject_ClearManagedDict((PyObject*)self);
823823
PyObject_GC_UnTrack(self);
824824
PyObject_GC_Del(self);
825825
Py_DECREF(tp);

‎Modules/_testcapimodule.c‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2923,7 +2923,7 @@ settrace_to_error(PyObject *self, PyObject *list)
29232923
staticPyObject*
29242924
clear_managed_dict(PyObject*self,PyObject*obj)
29252925
{
2926-
_PyObject_ClearManagedDict(obj);
2926+
PyObject_ClearManagedDict(obj);
29272927
Py_RETURN_NONE;
29282928
}
29292929

‎Objects/dictobject.c‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5649,7 +5649,7 @@ _PyObject_FreeInstanceAttributes(PyObject *self)
56495649
}
56505650

56515651
int
5652-
_PyObject_VisitManagedDict(PyObject*obj,visitprocvisit,void*arg)
5652+
PyObject_VisitManagedDict(PyObject*obj,visitprocvisit,void*arg)
56535653
{
56545654
PyTypeObject*tp=Py_TYPE(obj);
56555655
if((tp->tp_flags&Py_TPFLAGS_MANAGED_DICT)==0) {
@@ -5672,7 +5672,7 @@ _PyObject_VisitManagedDict(PyObject *obj, visitproc visit, void *arg)
56725672
}
56735673

56745674
void
5675-
_PyObject_ClearManagedDict(PyObject*obj)
5675+
PyObject_ClearManagedDict(PyObject*obj)
56765676
{
56775677
PyTypeObject*tp=Py_TYPE(obj);
56785678
if((tp->tp_flags&Py_TPFLAGS_MANAGED_DICT)==0) {

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp