1313#include "pycore_ceval.h" // _PyEval_GetBuiltin()
1414#include "pycore_modsupport.h" // _PyArg_NoKeywords()
1515#include "pycore_moduleobject.h" // _PyModule_GetState()
16+ #include "pycore_object.h" // _PyObject_GC_TRACK()
1617#include "pycore_weakref.h" // FT_CLEAR_WEAKREFS()
1718
1819#include <stddef.h> // offsetof()
@@ -696,7 +697,8 @@ class array.array "arrayobject *" "ArrayType"
696697/*[clinic end generated code: output=da39a3ee5e6b4b0d input=a5c29edf59f176a3]*/
697698
698699static PyObject *
699- newarrayobject (PyTypeObject * type , Py_ssize_t size , const struct arraydescr * descr )
700+ newarrayobject_untracked (PyTypeObject * type , Py_ssize_t size ,
701+ const struct arraydescr * descr )
700702{
701703 arrayobject * op ;
702704 size_t nbytes ;
@@ -711,7 +713,7 @@ newarrayobject(PyTypeObject *type, Py_ssize_t size, const struct arraydescr *des
711713 return PyErr_NoMemory ();
712714 }
713715 nbytes = size * descr -> itemsize ;
714- op = (arrayobject * ) type -> tp_alloc (type , 0 );
716+ op = (arrayobject * ) _PyType_AllocNoTrack (type , 0 );
715717 if (op == NULL ) {
716718 return NULL ;
717719 }
@@ -733,6 +735,16 @@ newarrayobject(PyTypeObject *type, Py_ssize_t size, const struct arraydescr *des
733735 return (PyObject * ) op ;
734736}
735737
738+ static PyObject *
739+ newarrayobject (PyTypeObject * type , Py_ssize_t size , const struct arraydescr * descr )
740+ {
741+ PyObject * op = newarrayobject_untracked (type , size , descr );
742+ if (op != NULL ) {
743+ _PyObject_GC_TRACK (op );
744+ }
745+ return op ;
746+ }
747+
736748static PyObject *
737749getarrayitem (PyObject * op , Py_ssize_t i )
738750{
@@ -942,13 +954,14 @@ array_slice(arrayobject *a, Py_ssize_t ilow, Py_ssize_t ihigh)
942954 ihigh = ilow ;
943955 else if (ihigh > Py_SIZE (a ))
944956 ihigh = Py_SIZE (a );
945- np = (arrayobject * ) newarrayobject (state -> ArrayType , ihigh - ilow , a -> ob_descr );
957+ np = (arrayobject * ) newarrayobject_untracked (state -> ArrayType , ihigh - ilow , a -> ob_descr );
946958 if (np == NULL )
947959 return NULL ;
948960 if (ihigh > ilow ) {
949961 memcpy (np -> ob_item , a -> ob_item + ilow * a -> ob_descr -> itemsize ,
950962 (ihigh - ilow ) * a -> ob_descr -> itemsize );
951963 }
964+ _PyObject_GC_TRACK (np );
952965 return (PyObject * )np ;
953966}
954967
@@ -1019,7 +1032,7 @@ array_concat(PyObject *op, PyObject *bb)
10191032 return PyErr_NoMemory ();
10201033 }
10211034 size = Py_SIZE (a ) + Py_SIZE (b );
1022- np = (arrayobject * ) newarrayobject (state -> ArrayType , size , a -> ob_descr );
1035+ np = (arrayobject * ) newarrayobject_untracked (state -> ArrayType , size , a -> ob_descr );
10231036 if (np == NULL ) {
10241037 return NULL ;
10251038 }
@@ -1030,6 +1043,7 @@ array_concat(PyObject *op, PyObject *bb)
10301043 memcpy (np -> ob_item + Py_SIZE (a )* a -> ob_descr -> itemsize ,
10311044 b -> ob_item , Py_SIZE (b )* b -> ob_descr -> itemsize );
10321045 }
1046+ _PyObject_GC_TRACK (np );
10331047 return (PyObject * )np ;
10341048#undef b
10351049}
@@ -1047,16 +1061,19 @@ array_repeat(PyObject *op, Py_ssize_t n)
10471061 return PyErr_NoMemory ();
10481062 }
10491063 Py_ssize_t size = array_length * n ;
1050- arrayobject * np = (arrayobject * ) newarrayobject (state -> ArrayType , size , a -> ob_descr );
1064+ arrayobject * np = (arrayobject * ) newarrayobject_untracked (state -> ArrayType , size , a -> ob_descr );
10511065 if (np == NULL )
10521066 return NULL ;
1053- if (size == 0 )
1067+ if (size == 0 ) {
1068+ _PyObject_GC_TRACK (np );
10541069 return (PyObject * )np ;
1070+ }
10551071
10561072 const Py_ssize_t oldbytes = array_length * a -> ob_descr -> itemsize ;
10571073 const Py_ssize_t newbytes = oldbytes * n ;
10581074 _PyBytes_Repeat (np -> ob_item , newbytes , a -> ob_item , oldbytes );
10591075
1076+ _PyObject_GC_TRACK (np );
10601077 return (PyObject * )np ;
10611078}
10621079
@@ -2534,17 +2551,17 @@ array_subscr(PyObject *op, PyObject *item)
25342551 return newarrayobject (state -> ArrayType , 0 , self -> ob_descr );
25352552 }
25362553 else if (step == 1 ) {
2537- PyObject * result = newarrayobject (state -> ArrayType ,
2538- slicelength , self -> ob_descr );
2554+ PyObject * result = newarrayobject_untracked (state -> ArrayType , slicelength , self -> ob_descr );
25392555 if (result == NULL )
25402556 return NULL ;
25412557 memcpy (((arrayobject * )result )-> ob_item ,
25422558 self -> ob_item + start * itemsize ,
25432559 slicelength * itemsize );
2560+ _PyObject_GC_TRACK (result );
25442561 return result ;
25452562 }
25462563 else {
2547- result = newarrayobject (state -> ArrayType , slicelength , self -> ob_descr );
2564+ result = newarrayobject_untracked (state -> ArrayType , slicelength , self -> ob_descr );
25482565 if (!result ) return NULL ;
25492566
25502567 ar = (arrayobject * )result ;
@@ -2556,6 +2573,7 @@ array_subscr(PyObject *op, PyObject *item)
25562573 itemsize );
25572574 }
25582575
2576+ _PyObject_GC_TRACK (result );
25592577 return result ;
25602578 }
25612579 }
@@ -2855,7 +2873,7 @@ array_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
28552873 else
28562874 len = 0 ;
28572875
2858- a = newarrayobject (type , len , descr );
2876+ a = newarrayobject_untracked (type , len , descr );
28592877 if (a == NULL ) {
28602878 Py_XDECREF (it );
28612879 return NULL ;
@@ -2943,6 +2961,8 @@ array_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
29432961 }
29442962 Py_DECREF (it );
29452963 }
2964+ // Track only once fully built.
2965+ _PyObject_GC_TRACK (a );
29462966 return a ;
29472967 }
29482968 }
@@ -3035,7 +3055,7 @@ static PyType_Slot array_slots[] = {
30353055 {Py_tp_methods , array_methods },
30363056 {Py_tp_members , array_members },
30373057 {Py_tp_getset , array_getsets },
3038- {Py_tp_alloc , PyType_GenericAlloc },
3058+ {Py_tp_alloc , _PyType_AllocNoTrack },
30393059 {Py_tp_new , array_new },
30403060 {Py_tp_traverse , array_tp_traverse },
30413061
0 commit comments