bpo-39542: Make _Py_NewReference() opaque in C API (GH-18346) · python/cpython@40e547d (original) (raw)

5 files changed

lines changed

Original file line number Diff line number Diff line change
@@ -169,6 +169,40 @@ PyAPI_FUNC(int) _PyMem_GetAllocatorName(
169 169 PYMEM_ALLOCATOR_NOT_SET does nothing. */
170 170 PyAPI_FUNC(int) _PyMem_SetupAllocators(PyMemAllocatorName allocator);
171 171
172 +/* bpo-35053: Expose _Py_tracemalloc_config for _Py_NewReference()
173 + which access directly _Py_tracemalloc_config.tracing for best
174 + performances. */
175 +struct _PyTraceMalloc_Config {
176 +/* Module initialized?
177 + Variable protected by the GIL */
178 +enum {
179 +TRACEMALLOC_NOT_INITIALIZED,
180 +TRACEMALLOC_INITIALIZED,
181 +TRACEMALLOC_FINALIZED
182 + } initialized;
183 +
184 +/* Is tracemalloc tracing memory allocations?
185 + Variable protected by the GIL */
186 +int tracing;
187 +
188 +/* limit of the number of frames in a traceback, 1 by default.
189 + Variable protected by the GIL. */
190 +int max_nframe;
191 +
192 +/* use domain in trace key?
193 + Variable protected by the GIL. */
194 +int use_domain;
195 +};
196 +
197 +#define _PyTraceMalloc_Config_INIT \
198 + {.initialized = TRACEMALLOC_NOT_INITIALIZED, \
199 + .tracing = 0, \
200 + .max_nframe = 1, \
201 + .use_domain = 0}
202 +
203 +PyAPI_DATA(struct _PyTraceMalloc_Config) _Py_tracemalloc_config;
204 +
205 +
172 206 #ifdef __cplusplus
173 207 }
174 208 #endif
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
1 1 #ifndef Py_OBJECT_H
2 2 #define Py_OBJECT_H
3 3
4 -#include "pymem.h" /* _Py_tracemalloc_config */
5 -
6 4 #ifdef __cplusplus
7 5 extern "C" {
8 6 #endif
@@ -390,28 +388,13 @@ PyAPI_FUNC(Py_ssize_t) _Py_GetRefTotal(void);
390 388 when a memory block is reused from a free list. */
391 389 PyAPI_FUNC(int) _PyTraceMalloc_NewReference(PyObject *op);
392 390
391 +PyAPI_FUNC(void) _Py_NewReference(PyObject *op);
392 +
393 393 #ifdef Py_TRACE_REFS
394 394 /* Py_TRACE_REFS is such major surgery that we call external routines. */
395 395 PyAPI_FUNC(void) _Py_ForgetReference(PyObject *);
396 -PyAPI_FUNC(void) _Py_AddToAllObjects(PyObject *, int force);
397 396 #endif
398 397
399 -
400 -static inline void _Py_NewReference(PyObject *op)
401 -{
402 -if (_Py_tracemalloc_config.tracing) {
403 -_PyTraceMalloc_NewReference(op);
404 - }
405 -#ifdef Py_REF_DEBUG
406 -_Py_RefTotal++;
407 -#endif
408 -Py_REFCNT(op) = 1;
409 -#ifdef Py_TRACE_REFS
410 -_Py_AddToAllObjects(op, 1);
411 -#endif
412 -}
413 -
414 -
415 398 PyAPI_FUNC(void) _Py_Dealloc(PyObject *);
416 399
417 400 static inline void _Py_INCREF(PyObject *op)
Original file line number Diff line number Diff line change
@@ -101,41 +101,6 @@ PyAPI_FUNC(void) PyMem_Free(void *ptr);
101 101 #define PyMem_Del PyMem_Free
102 102 #define PyMem_DEL PyMem_FREE
103 103
104 -/* bpo-35053: expose _Py_tracemalloc_config for performance:
105 - _Py_NewReference() needs an efficient check to test if tracemalloc is
106 - tracing.
107 -
108 - It has to be defined in pymem.h, before object.h is included. */
109 -struct _PyTraceMalloc_Config {
110 -/* Module initialized?
111 - Variable protected by the GIL */
112 -enum {
113 -TRACEMALLOC_NOT_INITIALIZED,
114 -TRACEMALLOC_INITIALIZED,
115 -TRACEMALLOC_FINALIZED
116 - } initialized;
117 -
118 -/* Is tracemalloc tracing memory allocations?
119 - Variable protected by the GIL */
120 -int tracing;
121 -
122 -/* limit of the number of frames in a traceback, 1 by default.
123 - Variable protected by the GIL. */
124 -int max_nframe;
125 -
126 -/* use domain in trace key?
127 - Variable protected by the GIL. */
128 -int use_domain;
129 -};
130 -
131 -PyAPI_DATA(struct _PyTraceMalloc_Config) _Py_tracemalloc_config;
132 -
133 -#define _PyTraceMalloc_Config_INIT \
134 - {.initialized = TRACEMALLOC_NOT_INITIALIZED, \
135 - .tracing = 0, \
136 - .max_nframe = 1, \
137 - .use_domain = 0}
138 -
139 104
140 105 #ifndef Py_LIMITED_API
141 106 # define Py_CPYTHON_PYMEM_H
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
1 1 #include "Python.h"
2 +#include "pycore_pymem.h"
2 3 #include "pycore_traceback.h"
3 4 #include "hashtable.h"
4 5 #include "frameobject.h"
Original file line number Diff line number Diff line change
@@ -93,7 +93,7 @@ static PyObject refchain = {&refchain, &refchain};
93 93 * way, though; exceptions include statically allocated type objects, and
94 94 * statically allocated singletons (like Py_True and Py_None).
95 95 */
96 -void
96 +static void
97 97 _Py_AddToAllObjects(PyObject *op, int force)
98 98 {
99 99 #ifdef Py_DEBUG
@@ -1805,6 +1805,22 @@ _PyTypes_Init(void)
1805 1805 }
1806 1806
1807 1807
1808 +void
1809 +_Py_NewReference(PyObject *op)
1810 +{
1811 +if (_Py_tracemalloc_config.tracing) {
1812 +_PyTraceMalloc_NewReference(op);
1813 + }
1814 +#ifdef Py_REF_DEBUG
1815 +_Py_RefTotal++;
1816 +#endif
1817 +Py_REFCNT(op) = 1;
1818 +#ifdef Py_TRACE_REFS
1819 +_Py_AddToAllObjects(op, 1);
1820 +#endif
1821 +}
1822 +
1823 +
1808 1824 #ifdef Py_TRACE_REFS
1809 1825 void
1810 1826 _Py_ForgetReference(PyObject *op)