123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229 |
- /*-------------------------------------------------------------------------
- *
- * memutils.h
- * This file contains declarations for memory allocation utility
- * functions. These are functions that are not quite widely used
- * enough to justify going in utils/palloc.h, but are still part
- * of the API of the memory management subsystem.
- *
- *
- * Portions Copyright (c) 1996-2022, PostgreSQL Global Development Group
- * Portions Copyright (c) 1994, Regents of the University of California
- *
- * src/include/utils/memutils.h
- *
- *-------------------------------------------------------------------------
- */
- #ifndef MEMUTILS_H
- #define MEMUTILS_H
- #include "nodes/memnodes.h"
- /*
- * MaxAllocSize, MaxAllocHugeSize
- * Quasi-arbitrary limits on size of allocations.
- *
- * Note:
- * There is no guarantee that smaller allocations will succeed, but
- * larger requests will be summarily denied.
- *
- * palloc() enforces MaxAllocSize, chosen to correspond to the limiting size
- * of varlena objects under TOAST. See VARSIZE_4B() and related macros in
- * postgres.h. Many datatypes assume that any allocatable size can be
- * represented in a varlena header. This limit also permits a caller to use
- * an "int" variable for an index into or length of an allocation. Callers
- * careful to avoid these hazards can access the higher limit with
- * MemoryContextAllocHuge(). Both limits permit code to assume that it may
- * compute twice an allocation's size without overflow.
- */
- #define MaxAllocSize ((Size) 0x3fffffff) /* 1 gigabyte - 1 */
- #define AllocSizeIsValid(size) ((Size) (size) <= MaxAllocSize)
- #define MaxAllocHugeSize (SIZE_MAX / 2)
- #define AllocHugeSizeIsValid(size) ((Size) (size) <= MaxAllocHugeSize)
- /*
- * Standard top-level memory contexts.
- *
- * Only TopMemoryContext and ErrorContext are initialized by
- * MemoryContextInit() itself.
- */
- extern PGDLLIMPORT MemoryContext TopMemoryContext;
- extern PGDLLIMPORT MemoryContext ErrorContext;
- extern PGDLLIMPORT MemoryContext PostmasterContext;
- extern PGDLLIMPORT MemoryContext CacheMemoryContext;
- extern PGDLLIMPORT MemoryContext MessageContext;
- extern PGDLLIMPORT MemoryContext TopTransactionContext;
- extern PGDLLIMPORT MemoryContext CurTransactionContext;
- /* This is a transient link to the active portal's memory context: */
- extern PGDLLIMPORT MemoryContext PortalContext;
- /* Backwards compatibility macro */
- #define MemoryContextResetAndDeleteChildren(ctx) MemoryContextReset(ctx)
- /*
- * Memory-context-type-independent functions in mcxt.c
- */
- extern void MemoryContextInit(void);
- extern void MemoryContextReset(MemoryContext context);
- extern void MemoryContextDelete(MemoryContext context);
- extern void MemoryContextResetOnly(MemoryContext context);
- extern void MemoryContextResetChildren(MemoryContext context);
- extern void MemoryContextDeleteChildren(MemoryContext context);
- extern void MemoryContextSetIdentifier(MemoryContext context, const char *id);
- extern void MemoryContextSetParent(MemoryContext context,
- MemoryContext new_parent);
- extern Size GetMemoryChunkSpace(void *pointer);
- extern MemoryContext MemoryContextGetParent(MemoryContext context);
- extern bool MemoryContextIsEmpty(MemoryContext context);
- extern Size MemoryContextMemAllocated(MemoryContext context, bool recurse);
- extern void MemoryContextStats(MemoryContext context);
- extern void MemoryContextStatsDetail(MemoryContext context, int max_children,
- bool print_to_stderr);
- extern void MemoryContextAllowInCriticalSection(MemoryContext context,
- bool allow);
- #ifdef MEMORY_CONTEXT_CHECKING
- extern void MemoryContextCheck(MemoryContext context);
- #endif
- extern bool MemoryContextContains(MemoryContext context, void *pointer);
- /* Handy macro for copying and assigning context ID ... but note double eval */
- #define MemoryContextCopyAndSetIdentifier(cxt, id) \
- MemoryContextSetIdentifier(cxt, MemoryContextStrdup(cxt, id))
- /*
- * GetMemoryChunkContext
- * Given a currently-allocated chunk, determine the context
- * it belongs to.
- *
- * All chunks allocated by any memory context manager are required to be
- * preceded by the corresponding MemoryContext stored, without padding, in the
- * preceding sizeof(void*) bytes. A currently-allocated chunk must contain a
- * backpointer to its owning context. The backpointer is used by pfree() and
- * repalloc() to find the context to call.
- */
- #ifndef FRONTEND
- static inline MemoryContext
- GetMemoryChunkContext(void *pointer)
- {
- MemoryContext context;
- /*
- * Try to detect bogus pointers handed to us, poorly though we can.
- * Presumably, a pointer that isn't MAXALIGNED isn't pointing at an
- * allocated chunk.
- */
- Assert(pointer != NULL);
- Assert(pointer == (void *) MAXALIGN(pointer));
- /*
- * OK, it's probably safe to look at the context.
- */
- context = *(MemoryContext *) (((char *) pointer) - sizeof(void *));
- AssertArg(MemoryContextIsValid(context));
- return context;
- }
- #endif
- /*
- * This routine handles the context-type-independent part of memory
- * context creation. It's intended to be called from context-type-
- * specific creation routines, and noplace else.
- */
- extern void MemoryContextCreate(MemoryContext node,
- NodeTag tag,
- const MemoryContextMethods *methods,
- MemoryContext parent,
- const char *name);
- extern void HandleLogMemoryContextInterrupt(void);
- extern void ProcessLogMemoryContextInterrupt(void);
- /*
- * Memory-context-type-specific functions
- */
- /* aset.c */
- extern MemoryContext AllocSetContextCreateInternal(MemoryContext parent,
- const char *name,
- Size minContextSize,
- Size initBlockSize,
- Size maxBlockSize);
- /*
- * This wrapper macro exists to check for non-constant strings used as context
- * names; that's no longer supported. (Use MemoryContextSetIdentifier if you
- * want to provide a variable identifier.)
- */
- #ifdef HAVE__BUILTIN_CONSTANT_P
- #define AllocSetContextCreate(parent, name, ...) \
- (StaticAssertExpr(__builtin_constant_p(name), \
- "memory context names must be constant strings"), \
- AllocSetContextCreateInternal(parent, name, __VA_ARGS__))
- #else
- #define AllocSetContextCreate \
- AllocSetContextCreateInternal
- #endif
- /* slab.c */
- extern MemoryContext SlabContextCreate(MemoryContext parent,
- const char *name,
- Size blockSize,
- Size chunkSize);
- /* generation.c */
- extern MemoryContext GenerationContextCreate(MemoryContext parent,
- const char *name,
- Size minContextSize,
- Size initBlockSize,
- Size maxBlockSize);
- /*
- * Recommended default alloc parameters, suitable for "ordinary" contexts
- * that might hold quite a lot of data.
- */
- #define ALLOCSET_DEFAULT_MINSIZE 0
- #define ALLOCSET_DEFAULT_INITSIZE (8 * 1024)
- #define ALLOCSET_DEFAULT_MAXSIZE (8 * 1024 * 1024)
- #define ALLOCSET_DEFAULT_SIZES \
- ALLOCSET_DEFAULT_MINSIZE, ALLOCSET_DEFAULT_INITSIZE, ALLOCSET_DEFAULT_MAXSIZE
- /*
- * Recommended alloc parameters for "small" contexts that are never expected
- * to contain much data (for example, a context to contain a query plan).
- */
- #define ALLOCSET_SMALL_MINSIZE 0
- #define ALLOCSET_SMALL_INITSIZE (1 * 1024)
- #define ALLOCSET_SMALL_MAXSIZE (8 * 1024)
- #define ALLOCSET_SMALL_SIZES \
- ALLOCSET_SMALL_MINSIZE, ALLOCSET_SMALL_INITSIZE, ALLOCSET_SMALL_MAXSIZE
- /*
- * Recommended alloc parameters for contexts that should start out small,
- * but might sometimes grow big.
- */
- #define ALLOCSET_START_SMALL_SIZES \
- ALLOCSET_SMALL_MINSIZE, ALLOCSET_SMALL_INITSIZE, ALLOCSET_DEFAULT_MAXSIZE
- /*
- * Threshold above which a request in an AllocSet context is certain to be
- * allocated separately (and thereby have constant allocation overhead).
- * Few callers should be interested in this, but tuplesort/tuplestore need
- * to know it.
- */
- #define ALLOCSET_SEPARATE_THRESHOLD 8192
- #define SLAB_DEFAULT_BLOCK_SIZE (8 * 1024)
- #define SLAB_LARGE_BLOCK_SIZE (8 * 1024 * 1024)
- #endif /* MEMUTILS_H */
|