numpy  2.0.0
src/multiarray/alloc.c File Reference
#include <Python.h>
#include "structmember.h"
#include <numpy/ndarraytypes.h>
#include "numpy/arrayobject.h"
#include <numpy/npy_common.h>
#include "npy_config.h"
#include <assert.h>

Data Structures

struct  cache_bucket

Defines

#define PY_SSIZE_T_CLEAN
#define NPY_NO_DEPRECATED_API   NPY_API_VERSION
#define _MULTIARRAYMODULE
#define NBUCKETS   1024
#define NBUCKETS_DIM   16
#define NCACHE   7

Functions

static NPY_INLINE void * _npy_alloc_cache (npy_uintp nelem, npy_uintp esz, npy_uint msz, cache_bucket *cache, void *(*alloc)(size_t))
static NPY_INLINE void _npy_free_cache (void *p, npy_uintp nelem, npy_uint msz, cache_bucket *cache, void(*dealloc)(void *))
NPY_NO_EXPORT void * npy_alloc_cache (npy_uintp sz)
NPY_NO_EXPORT void * npy_alloc_cache_zero (npy_uintp sz)
NPY_NO_EXPORT void npy_free_cache (void *p, npy_uintp sz)
NPY_NO_EXPORT void * npy_alloc_cache_dim (npy_uintp sz)
NPY_NO_EXPORT void npy_free_cache_dim (void *p, npy_uintp sz)
NPY_NO_EXPORT
PyDataMem_EventHookFunc
PyDataMem_SetEventHook (PyDataMem_EventHookFunc *newhook, void *user_data, void **old_data)
NPY_NO_EXPORT void * PyDataMem_NEW (size_t size)
NPY_NO_EXPORT void * PyDataMem_NEW_ZEROED (size_t size, size_t elsize)
NPY_NO_EXPORT void PyDataMem_FREE (void *ptr)
NPY_NO_EXPORT void * PyDataMem_RENEW (void *ptr, size_t size)

Variables

static cache_bucket datacache [NBUCKETS]
static cache_bucket dimcache [NBUCKETS_DIM]
NPY_NO_EXPORT
PyDataMem_EventHookFunc
_PyDataMem_eventhook
NPY_NO_EXPORT void * _PyDataMem_eventhook_user_data

Define Documentation

#define NBUCKETS   1024
number of buckets for data

Referenced by _npy_free_cache().

#define NBUCKETS_DIM   16
number of buckets for dimensions/strides

Referenced by npy_free_cache().

#define NCACHE   7
number of cache entries per bucket

Referenced by _npy_alloc_cache().

#define NPY_NO_DEPRECATED_API   NPY_API_VERSION

Function Documentation

static NPY_INLINE void* _npy_alloc_cache ( npy_uintp  nelem,
npy_uintp  esz,
npy_uint  msz,
cache_bucket cache,
void *(*)(size_t)  alloc 
) [static]
very simplistic small memory block cache to avoid more expensive libc allocations base function for data cache with 1 byte buckets and dimension cache with sizeof(npy_intp) byte buckets

References cache_bucket::available, NCACHE, and cache_bucket::ptrs.

Referenced by _npy_free_cache().

static NPY_INLINE void _npy_free_cache ( void *  p,
npy_uintp  nelem,
npy_uint  msz,
cache_bucket cache,
void(*)(void *)  dealloc 
) [static]
return pointer p to cache, nelem is number of elements of the cache bucket size (1 or sizeof(npy_intp)) of the block pointed too

References _npy_alloc_cache(), NBUCKETS, and PyDataMem_NEW().

Referenced by npy_free_cache().

array data cache, sz is number of bytes to allocate
dimension/stride cache, uses a different allocator and is always a multiple of npy_intp
dims + strides
zero initialized data, sz is number of bytes to allocate
NPY_NO_EXPORT void npy_free_cache_dim ( void *  p,
npy_uintp  sz 
)
dims + strides

References _PyDataMem_eventhook, NPY_ALLOW_C_API, and NPY_ALLOW_C_API_DEF.

NPY_NO_EXPORT void PyDataMem_FREE ( void *  ptr)
Free memory for array data.
NPY_NO_EXPORT void* PyDataMem_NEW ( size_t  size)
Allocates memory for array data.

Referenced by _npy_free_cache().

NPY_NO_EXPORT void* PyDataMem_NEW_ZEROED ( size_t  size,
size_t  elsize 
)
Allocates zeroed memory for array data.
NPY_NO_EXPORT void* PyDataMem_RENEW ( void *  ptr,
size_t  size 
)
Reallocate/resize memory for array data.

Referenced by PyArray_Arange(), and PyArray_Empty().

NPY_NO_EXPORT PyDataMem_EventHookFunc* PyDataMem_SetEventHook ( PyDataMem_EventHookFunc newhook,
void *  user_data,
void **  old_data 
)
Sets the allocation event hook for numpy array data.
Takes a PyDataMem_EventHookFunc *, which has the signature:
System Message: WARNING/2 (<string>, line 4); backlink Inline emphasis start-string without end-string.

<blockquote>

void hook(void *old, void *new, size_t size, void *user_data).

System Message: WARNING/2 (<string>, line 3); backlink Inline emphasis start-string without end-string.
System Message: WARNING/2 (<string>, line 3); backlink Inline emphasis start-string without end-string.
System Message: WARNING/2 (<string>, line 3); backlink Inline emphasis start-string without end-string.

</blockquote>

System Message: WARNING/2 (<string>, line 4) Block quote ends without a blank line; unexpected unindent.

Also takes a void *user_data, and void **old_data.

System Message: WARNING/2 (<string>, line 4); backlink Inline emphasis start-string without end-string.
System Message: WARNING/2 (<string>, line 4); backlink Inline strong start-string without end-string.

Returns a pointer to the previous hook or NULL. If old_data is non-NULL, the previous user_data pointer will be copied to it.

If not NULL, hook will be called at the end of each PyDataMem_NEW/FREE/RENEW:

result = PyDataMem_NEW(size) -> (*hook)(NULL, result, size, user_data) PyDataMem_FREE(ptr) -> (*hook)(ptr, NULL, 0, user_data) result = PyDataMem_RENEW(ptr, size) -> (*hook)(ptr, result, size, user_data)

System Message: WARNING/2 (<string>, line 10); backlink Inline emphasis start-string without end-string.
System Message: WARNING/2 (<string>, line 10); backlink Inline emphasis start-string without end-string.
System Message: WARNING/2 (<string>, line 10); backlink Inline emphasis start-string without end-string.

When the hook is called, the GIL will be held by the calling thread. The hook should be written to be reentrant, if it performs operations that might cause new allocation events (such as the creation/destruction numpy objects, or creating/destroying Python objects which might cause a gc)


Variable Documentation