Unless you have specific memory management requirements, it is
recommended to use PyObject_{New, NewVar, Del}. */
-/*
- * Core object memory allocator
- * ============================
- */
-
-/* The purpose of the object allocator is to make the distinction
- between "object memory" and the rest within the Python heap.
-
- Object memory is the one allocated by PyObject_{New, NewVar}, i.e.
- the one that holds the object's representation defined by its C
- type structure, *excluding* any object-specific memory buffers that
- might be referenced by the structure (for type structures that have
- pointer fields). By default, the object memory allocator is
- implemented on top of the raw memory allocator.
-
- The PyCore_* macros can be defined to make the interpreter use a
- custom object memory allocator. They are reserved for internal
- memory management purposes exclusively. Both the core and extension
- modules should use the PyObject_* API. */
-
-#ifdef WITH_PYMALLOC
-void *_PyCore_ObjectMalloc(size_t nbytes);
-void *_PyCore_ObjectRealloc(void *p, size_t nbytes);
-void _PyCore_ObjectFree(void *p);
-#define PyCore_OBJECT_MALLOC _PyCore_ObjectMalloc
-#define PyCore_OBJECT_REALLOC _PyCore_ObjectRealloc
-#define PyCore_OBJECT_FREE _PyCore_ObjectFree
-#endif /* !WITH_PYMALLOC */
-
-#ifndef PyCore_OBJECT_MALLOC
-#undef PyCore_OBJECT_REALLOC
-#undef PyCore_OBJECT_FREE
-#define PyCore_OBJECT_MALLOC(n) PyCore_MALLOC(n)
-#define PyCore_OBJECT_REALLOC(p, n) PyCore_REALLOC((p), (n))
-#define PyCore_OBJECT_FREE(p) PyCore_FREE(p)
-#endif
-
/*
* Raw object memory interface
* ===========================
/* Functions */
-/* Wrappers around PyCore_OBJECT_MALLOC and friends; useful if you
- need to be sure that you are using the same object memory allocator
- as Python. These wrappers *do not* make sure that allocating 0
- bytes returns a non-NULL pointer. Returned pointers must be checked
- for NULL explicitly; no action is performed on failure. */
+/* Wrappers that useful if you need to be sure that you are using the
+ same object memory allocator as Python. These wrappers *do not* make
+ sure that allocating 0 bytes returns a non-NULL pointer. Returned
+ pointers must be checked for NULL explicitly; no action is performed
+ on failure. */
extern DL_IMPORT(void *) PyObject_Malloc(size_t);
extern DL_IMPORT(void *) PyObject_Realloc(void *, size_t);
extern DL_IMPORT(void) PyObject_Free(void *);
/* Macros */
-#define PyObject_MALLOC(n) PyCore_OBJECT_MALLOC(n)
-#define PyObject_REALLOC(op, n) PyCore_OBJECT_REALLOC((void *)(op), (n))
-#define PyObject_FREE(op) PyCore_OBJECT_FREE((void *)(op))
+#define PyObject_MALLOC(n) _PyMalloc_MALLOC(n)
+#define PyObject_REALLOC(op, n) _PyMalloc_REALLOC((void *)(op), (n))
+#define PyObject_FREE(op) _PyMalloc_FREE((void *)(op))
/*
* Generic object allocator interface
extern "C" {
#endif
-/*
- * Core memory allocator
- * =====================
- */
-
-/* To make sure the interpreter is user-malloc friendly, all memory
- APIs are implemented on top of this one.
-
- The PyCore_* macros can be defined to make the interpreter use a
- custom allocator. Note that they are for internal use only. Both
- the core and extension modules should use the PyMem_* API. */
-
-#ifndef PyCore_MALLOC
-#undef PyCore_REALLOC
-#undef PyCore_FREE
-#define PyCore_MALLOC(n) malloc(n)
-#define PyCore_REALLOC(p, n) realloc((p), (n))
-#define PyCore_FREE(p) free(p)
-#endif
-
/* BEWARE:
Each interface exports both functions and macros. Extension modules
* ====================
*/
+/* To make sure the interpreter is user-malloc friendly, all memory
+ APIs are implemented on top of this one. */
+
/* Functions */
-/* Function wrappers around PyCore_MALLOC and friends; useful if you
+/* Function wrappers around PyMem_MALLOC and friends; useful if you
need to be sure that you are using the same memory allocator as
Python. Note that the wrappers make sure that allocating 0 bytes
returns a non-NULL pointer, even if the underlying malloc
/* Starting from Python 1.6, the wrappers Py_{Malloc,Realloc,Free} are
no longer supported. They used to call PyErr_NoMemory() on failure. */
-/* Macros */
-#define PyMem_MALLOC(n) PyCore_MALLOC(n)
-#define PyMem_REALLOC(p, n) PyCore_REALLOC((void *)(p), (n))
-#define PyMem_FREE(p) PyCore_FREE((void *)(p))
+/* Macros (override these if you want to a different malloc */
+#ifndef PyMem_MALLOC
+#define PyMem_MALLOC(n) malloc(n)
+#define PyMem_REALLOC(p, n) realloc((void *)(p), (n))
+#define PyMem_FREE(p) free((void *)(p))
+#endif
/*
* Type-oriented memory interface
it is recommended to write the test explicitly in the code.
Note that according to ANSI C, free(NULL) has no effect. */
+
+/* pymalloc (private to the interpreter) */
+#ifdef WITH_PYMALLOC
+void *_PyMalloc_Malloc(size_t nbytes);
+void *_PyMalloc_Realloc(void *p, size_t nbytes);
+void _PyMalloc_Free(void *p);
+#define _PyMalloc_MALLOC _PyMalloc_Malloc
+#define _PyMalloc_REALLOC _PyMalloc_Realloc
+#define _PyMalloc_FREE _PyMalloc_Free
+#else
+#define _PyMalloc_MALLOC PyMem_MALLOC
+#define _PyMalloc_REALLOC PyMem_REALLOC
+#define _PyMalloc_FREE PyMem_FREE
+#endif
+
+
#ifdef __cplusplus
}
#endif
#ifdef WITH_PYMALLOC
#include "obmalloc.c"
-#endif
+#else
+void *_PyMalloc_Malloc(size_t n)
+{
+ return PyMem_MALLOC(n);
+}
+
+void *_PyMalloc_Realloc(void *p, size_t n)
+{
+ return PyMem_REALLOC(p, n);
+}
+
+void _PyMalloc_Free(void *p)
+{
+ PyMem_FREE(p);
+}
+#endif /* !WITH_PYMALLOC */
*/
void *
-_PyCore_ObjectMalloc(size_t nbytes)
+_PyMalloc_Malloc(size_t nbytes)
{
block *bp;
poolp pool;
* With malloc, we can't avoid loosing one page address space
* per arena due to the required alignment on page boundaries.
*/
- bp = (block *)PyCore_MALLOC(ARENA_SIZE + SYSTEM_PAGE_SIZE);
+ bp = (block *)PyMem_MALLOC(ARENA_SIZE + SYSTEM_PAGE_SIZE);
if (bp == NULL) {
UNLOCK();
goto redirect;
* last chance to serve the request) or when the max memory limit
* has been reached.
*/
- return (void *)PyCore_MALLOC(nbytes);
+ return (void *)PyMem_MALLOC(nbytes);
}
/* free */
void
-_PyCore_ObjectFree(void *p)
+_PyMalloc_Free(void *p)
{
poolp pool;
poolp next, prev;
offset = (off_t )p & POOL_SIZE_MASK;
pool = (poolp )((block *)p - offset);
if (pool->pooladdr != pool || pool->magic != (uint )POOL_MAGIC) {
- PyCore_FREE(p);
+ PyMem_FREE(p);
return;
}
/* realloc */
void *
-_PyCore_ObjectRealloc(void *p, size_t nbytes)
+_PyMalloc_Realloc(void *p, size_t nbytes)
{
block *bp;
poolp pool;
#endif
if (p == NULL)
- return _PyCore_ObjectMalloc(nbytes);
+ return _PyMalloc_Malloc(nbytes);
/* realloc(p, 0) on big blocks is redirected. */
pool = (poolp )((block *)p - ((off_t )p & POOL_SIZE_MASK));
size = nbytes;
goto malloc_copy_free;
}
- bp = (block *)PyCore_REALLOC(p, nbytes);
+ bp = (block *)PyMem_REALLOC(p, nbytes);
}
else {
/* We're in charge of this block */
/* Don't bother if a smaller size was requested
except for realloc(p, 0) == free(p), ret NULL */
if (nbytes == 0) {
- _PyCore_ObjectFree(p);
+ _PyMalloc_Free(p);
bp = NULL;
}
else
malloc_copy_free:
- bp = (block *)_PyCore_ObjectMalloc(nbytes);
+ bp = (block *)_PyMalloc_Malloc(nbytes);
if (bp != NULL) {
memcpy(bp, p, size);
- _PyCore_ObjectFree(p);
+ _PyMalloc_Free(p);
}
}
}
/* -- unused --
void *
-_PyCore_ObjectCalloc(size_t nbel, size_t elsz)
+_PyMalloc_Calloc(size_t nbel, size_t elsz)
{
void *p;
size_t nbytes;
#endif
nbytes = nbel * elsz;
- p = _PyCore_ObjectMalloc(nbytes);
+ p = _PyMalloc_Malloc(nbytes);
if (p != NULL)
memset(p, 0, nbytes);
return p;
#ifdef WITH_MALLOC_HOOKS
void
-_PyCore_ObjectMalloc_SetHooks( void *(*malloc_func)(size_t),
- void *(*calloc_func)(size_t, size_t),
- void *(*realloc_func)(void *, size_t),
- void (*free_func)(void *) )
+_PyMalloc_SetHooks( void *(*malloc_func)(size_t),
+ void *(*calloc_func)(size_t, size_t),
+ void *(*realloc_func)(void *, size_t),
+ void (*free_func)(void *) )
{
LOCK();
malloc_hook = malloc_func;
}
void
-_PyCore_ObjectMalloc_FetchHooks( void *(**malloc_funcp)(size_t),
- void *(**calloc_funcp)(size_t, size_t),
- void *(**realloc_funcp)(void *, size_t),
- void (**free_funcp)(void *) )
+_PyMalloc_FetchHooks( void *(**malloc_funcp)(size_t),
+ void *(**calloc_funcp)(size_t, size_t),
+ void *(**realloc_funcp)(void *, size_t),
+ void (**free_funcp)(void *) )
{
LOCK();
*malloc_funcp = malloc_hook;