PostgreSQL Source Code git master
Loading...
Searching...
No Matches
shmem.h File Reference
#include "storage/spin.h"
#include "utils/hsearch.h"
Include dependency graph for shmem.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Data Structures

struct  ShmemIndexEnt
 

Macros

#define SHMEM_INDEX_KEYSIZE   (48)
 
#define SHMEM_INDEX_SIZE   (64)
 

Typedefs

typedef struct PGShmemHeader PGShmemHeader
 

Functions

void InitShmemAllocator (PGShmemHeader *seghdr)
 
voidShmemAlloc (Size size)
 
voidShmemAllocNoError (Size size)
 
bool ShmemAddrIsValid (const void *addr)
 
void InitShmemIndex (void)
 
HTABShmemInitHash (const char *name, int64 init_size, int64 max_size, HASHCTL *infoP, int hash_flags)
 
voidShmemInitStruct (const char *name, Size size, bool *foundPtr)
 
Size add_size (Size s1, Size s2)
 
Size mul_size (Size s1, Size s2)
 
PGDLLIMPORT Size pg_get_shmem_pagesize (void)
 
void RequestAddinShmemSpace (Size size)
 

Variables

PGDLLIMPORT slock_tShmemLock
 

Macro Definition Documentation

◆ SHMEM_INDEX_KEYSIZE

#define SHMEM_INDEX_KEYSIZE   (48)

Definition at line 50 of file shmem.h.

◆ SHMEM_INDEX_SIZE

#define SHMEM_INDEX_SIZE   (64)

Definition at line 52 of file shmem.h.

Typedef Documentation

◆ PGShmemHeader

Definition at line 30 of file shmem.h.

Function Documentation

◆ add_size()

Size add_size ( Size  s1,
Size  s2 
)
extern

Definition at line 482 of file shmem.c.

483{
484 Size result;
485
486 if (pg_add_size_overflow(s1, s2, &result))
489 errmsg("requested shared memory size overflows size_t")));
490 return result;
491}
size_t Size
Definition c.h:619
int errcode(int sqlerrcode)
Definition elog.c:863
int errmsg(const char *fmt,...)
Definition elog.c:1080
#define ERROR
Definition elog.h:39
#define ereport(elevel,...)
Definition elog.h:150
static bool pg_add_size_overflow(size_t a, size_t b, size_t *result)
Definition int.h:608
static int fb(int x)
char * s1
char * s2

References ereport, errcode(), errmsg(), ERROR, fb(), pg_add_size_overflow(), s1, and s2.

Referenced by _brin_parallel_estimate_shared(), _bt_parallel_estimate_shared(), _gin_parallel_estimate_shared(), AioShmemSize(), ApplyLauncherShmemSize(), AsyncShmemInit(), AsyncShmemSize(), AutoVacuumShmemSize(), BackendStatusShmemSize(), BackgroundWorkerShmemSize(), btestimateparallelscan(), BTreeShmemSize(), BufferManagerShmemSize(), CalculateShmemSize(), CheckpointerShmemSize(), CreateAnonymousSegment(), estimate_variable_size(), EstimateClientConnectionInfoSpace(), EstimateComboCIDStateSpace(), EstimateGUCStateSpace(), EstimateLibraryStateSpace(), EstimateParamExecSpace(), EstimateParamListSpace(), EstimateSnapshotSpace(), EstimateTransactionStateSpace(), ExecAggEstimate(), ExecAppendEstimate(), ExecBitmapHeapEstimate(), ExecBitmapHeapInitializeDSM(), ExecHashEstimate(), ExecIncrementalSortEstimate(), ExecMemoizeEstimate(), ExecSortEstimate(), expand_planner_arrays(), FastPathLockShmemSize(), hash_estimate_size(), index_parallelscan_estimate(), index_parallelscan_initialize(), InitializeShmemGUCs(), InjectionPointShmemSize(), LockManagerShmemSize(), LWLockShmemSize(), MultiXactShmemSize(), pgaio_worker_shmem_size(), PgArchShmemSize(), PGProcShmemSize(), pgss_memsize(), PMSignalShmemSize(), PredicateLockShmemInit(), PredicateLockShmemSize(), ProcArrayShmemInit(), ProcArrayShmemSize(), ProcGlobalShmemSize(), ProcSignalShmemSize(), ReplicationOriginShmemSize(), ReplicationSlotsShmemSize(), RequestAddinShmemSpace(), SerializeTransactionState(), SharedInvalShmemSize(), shm_toc_estimate(), StatsShmemSize(), StrategyShmemSize(), table_parallelscan_estimate(), tuplesort_estimate_shared(), TwoPhaseShmemSize(), WaitEventCustomShmemSize(), WaitLSNShmemSize(), WalRcvShmemSize(), WalSndShmemSize(), and XLOGShmemSize().

◆ InitShmemAllocator()

void InitShmemAllocator ( PGShmemHeader seghdr)
extern

Definition at line 122 of file shmem.c.

123{
124 Assert(seghdr != NULL);
125
126 /*
127 * We assume the pointer and offset are MAXALIGN. Not a hard requirement,
128 * but it's true today and keeps the math below simpler.
129 */
130 Assert(seghdr == (void *) MAXALIGN(seghdr));
131 Assert(seghdr->content_offset == MAXALIGN(seghdr->content_offset));
132
135 ShmemEnd = (char *) ShmemBase + seghdr->totalsize;
136
137#ifndef EXEC_BACKEND
139#endif
141 {
143
144 ShmemAllocator = (ShmemAllocatorData *) ((char *) shmhdr + shmhdr->content_offset);
146 }
147 else
148 {
149 Size offset;
150
151 /*
152 * Allocations after this point should go through ShmemAlloc, which
153 * expects to allocate everything on cache line boundaries. Make sure
154 * the first allocation begins on a cache line boundary.
155 */
156 offset = CACHELINEALIGN(seghdr->content_offset + sizeof(ShmemAllocatorData));
157 if (offset > seghdr->totalsize)
160 errmsg("out of shared memory (%zu bytes requested)",
161 offset)));
162
163 ShmemAllocator = (ShmemAllocatorData *) ((char *) seghdr + seghdr->content_offset);
164
167 ShmemAllocator->free_offset = offset;
168 /* ShmemIndex can't be set up yet (need LWLocks first) */
170 ShmemIndex = (HTAB *) NULL;
171 }
172}
#define CACHELINEALIGN(LEN)
Definition c.h:829
#define MAXALIGN(LEN)
Definition c.h:826
#define Assert(condition)
Definition c.h:873
bool IsUnderPostmaster
Definition globals.c:120
static void * ShmemBase
Definition shmem.c:101
static void * ShmemEnd
Definition shmem.c:102
slock_t * ShmemLock
Definition shmem.c:105
static PGShmemHeader * ShmemSegHdr
Definition shmem.c:100
static HTAB * ShmemIndex
Definition shmem.c:106
static ShmemAllocatorData * ShmemAllocator
Definition shmem.c:104
#define SpinLockInit(lock)
Definition spin.h:57
Size totalsize
Definition pg_shmem.h:34
slock_t shmem_lock
Definition shmem.c:93

References Assert, CACHELINEALIGN, ereport, errcode(), errmsg(), ERROR, fb(), ShmemAllocatorData::free_offset, ShmemAllocatorData::index, IsUnderPostmaster, MAXALIGN, ShmemAllocatorData::shmem_lock, ShmemAllocator, ShmemBase, ShmemEnd, ShmemIndex, ShmemLock, ShmemSegHdr, SpinLockInit, and PGShmemHeader::totalsize.

Referenced by CreateSharedMemoryAndSemaphores().

◆ InitShmemIndex()

void InitShmemIndex ( void  )
extern

Definition at line 274 of file shmem.c.

275{
276 HASHCTL info;
277
278 /*
279 * Create the shared memory shmem index.
280 *
281 * Since ShmemInitHash calls ShmemInitStruct, which expects the ShmemIndex
282 * hashtable to exist already, we have a bit of a circularity problem in
283 * initializing the ShmemIndex itself. The special "ShmemIndex" hash
284 * table name will tell ShmemInitStruct to fake it.
285 */
287 info.entrysize = sizeof(ShmemIndexEnt);
288
289 ShmemIndex = ShmemInitHash("ShmemIndex",
291 &info,
293}
#define HASH_STRINGS
Definition hsearch.h:96
#define HASH_ELEM
Definition hsearch.h:95
HTAB * ShmemInitHash(const char *name, int64 init_size, int64 max_size, HASHCTL *infoP, int hash_flags)
Definition shmem.c:323
#define SHMEM_INDEX_SIZE
Definition shmem.h:52
#define SHMEM_INDEX_KEYSIZE
Definition shmem.h:50
Size keysize
Definition hsearch.h:75
Size entrysize
Definition hsearch.h:76

References HASHCTL::entrysize, HASH_ELEM, HASH_STRINGS, HASHCTL::keysize, SHMEM_INDEX_KEYSIZE, SHMEM_INDEX_SIZE, ShmemIndex, and ShmemInitHash().

Referenced by CreateOrAttachShmemStructs().

◆ mul_size()

Size mul_size ( Size  s1,
Size  s2 
)
extern

Definition at line 497 of file shmem.c.

498{
499 Size result;
500
501 if (pg_mul_size_overflow(s1, s2, &result))
504 errmsg("requested shared memory size overflows size_t")));
505 return result;
506}
static bool pg_mul_size_overflow(size_t a, size_t b, size_t *result)
Definition int.h:642

References ereport, errcode(), errmsg(), ERROR, fb(), pg_mul_size_overflow(), s1, and s2.

Referenced by _brin_begin_parallel(), _bt_begin_parallel(), _gin_begin_parallel(), AioBackendShmemSize(), AioHandleDataShmemSize(), AioHandleIOVShmemSize(), AioHandleShmemSize(), ApplyLauncherShmemSize(), AsyncShmemInit(), AsyncShmemSize(), AutoVacuumShmemSize(), BackendStatusShmemInit(), BackendStatusShmemSize(), BackgroundWorkerShmemSize(), BTreeShmemSize(), BufferManagerShmemSize(), CheckpointerShmemSize(), EstimateComboCIDStateSpace(), EstimatePendingSyncsSpace(), EstimateReindexStateSpace(), EstimateSnapshotSpace(), EstimateTransactionStateSpace(), ExecAggEstimate(), ExecBitmapHeapEstimate(), ExecBitmapHeapInitializeDSM(), ExecHashEstimate(), ExecIncrementalSortEstimate(), ExecInitParallelPlan(), ExecMemoizeEstimate(), ExecParallelRetrieveInstrumentation(), ExecParallelRetrieveJitInstrumentation(), ExecParallelSetupTupleQueues(), ExecSortEstimate(), FastPathLockShmemSize(), hash_estimate_size(), InitializeParallelDSM(), LWLockShmemSize(), parallel_vacuum_init(), PGProcShmemSize(), PGSemaphoreShmemSize(), PMSignalShmemSize(), PredicateLockShmemInit(), PredicateLockShmemSize(), ProcArrayShmemInit(), ProcArrayShmemSize(), ProcSignalShmemSize(), ReplicationOriginShmemSize(), ReplicationSlotsShmemSize(), SharedInvalShmemSize(), shm_toc_estimate(), tuplesort_estimate_shared(), TwoPhaseShmemSize(), WaitLSNShmemSize(), WalSndShmemSize(), and XLOGShmemSize().

◆ pg_get_shmem_pagesize()

PGDLLIMPORT Size pg_get_shmem_pagesize ( void  )
extern

Definition at line 738 of file shmem.c.

739{
741#ifdef WIN32
743
745 os_page_size = sysinfo.dwPageSize;
746#else
748#endif
749
752
755
756 return os_page_size;
757}
int huge_pages_status
Definition guc_tables.c:591
@ HUGE_PAGES_UNKNOWN
Definition pg_shmem.h:56
@ HUGE_PAGES_ON
Definition pg_shmem.h:54
void GetHugePageSize(Size *hugepagesize, int *mmap_flags)
Definition sysv_shmem.c:480

References Assert, fb(), GetHugePageSize(), HUGE_PAGES_ON, huge_pages_status, HUGE_PAGES_UNKNOWN, and IsUnderPostmaster.

Referenced by pg_buffercache_os_pages_internal(), and pg_get_shmem_allocations_numa().

◆ RequestAddinShmemSpace()

void RequestAddinShmemSpace ( Size  size)
extern

Definition at line 75 of file ipci.c.

76{
78 elog(FATAL, "cannot request additional shared memory outside shmem_request_hook");
80}
#define FATAL
Definition elog.h:41
#define elog(elevel,...)
Definition elog.h:226
static Size total_addin_request
Definition ipci.c:61
bool process_shmem_requests_in_progress
Definition miscinit.c:1790
Size add_size(Size s1, Size s2)
Definition shmem.c:482

References add_size(), elog, FATAL, process_shmem_requests_in_progress, and total_addin_request.

Referenced by injection_shmem_request(), pgss_shmem_request(), test_aio_shmem_request(), and test_slru_shmem_request().

◆ ShmemAddrIsValid()

bool ShmemAddrIsValid ( const void addr)
extern

Definition at line 265 of file shmem.c.

266{
267 return (addr >= ShmemBase) && (addr < ShmemEnd);
268}

References ShmemBase, and ShmemEnd.

Referenced by ReleasePredXact(), and ShmemInitStruct().

◆ ShmemAlloc()

void * ShmemAlloc ( Size  size)
extern

Definition at line 182 of file shmem.c.

183{
184 void *newSpace;
185 Size allocated_size;
186
187 newSpace = ShmemAllocRaw(size, &allocated_size);
188 if (!newSpace)
191 errmsg("out of shared memory (%zu bytes requested)",
192 size)));
193 return newSpace;
194}
static void * ShmemAllocRaw(Size size, Size *allocated_size)
Definition shmem.c:216

References ereport, errcode(), errmsg(), ERROR, fb(), and ShmemAllocRaw().

Referenced by CreateLWLocks(), PGReserveSemaphores(), ShmemInitStruct(), and StatsShmemInit().

◆ ShmemAllocNoError()

void * ShmemAllocNoError ( Size  size)
extern

Definition at line 202 of file shmem.c.

203{
204 Size allocated_size;
205
206 return ShmemAllocRaw(size, &allocated_size);
207}

References ShmemAllocRaw().

Referenced by ShmemInitHash().

◆ ShmemInitHash()

HTAB * ShmemInitHash ( const char name,
int64  init_size,
int64  max_size,
HASHCTL infoP,
int  hash_flags 
)
extern

Definition at line 323 of file shmem.c.

328{
329 bool found;
330 void *location;
331
332 /*
333 * Hash tables allocated in shared memory have a fixed directory; it can't
334 * grow or other backends wouldn't be able to find it. So, make sure we
335 * make it big enough to start with.
336 *
337 * The shared memory allocator must be specified too.
338 */
339 infoP->dsize = infoP->max_dsize = hash_select_dirsize(max_size);
340 infoP->alloc = ShmemAllocNoError;
342
343 /* look it up in the shmem index */
344 location = ShmemInitStruct(name,
346 &found);
347
348 /*
349 * if it already exists, attach to it rather than allocate and initialize
350 * new space
351 */
352 if (found)
354
355 /* Pass location of hashtable header to hash_create */
356 infoP->hctl = (HASHHDR *) location;
357
359}
HTAB * hash_create(const char *tabname, int64 nelem, const HASHCTL *info, int flags)
Definition dynahash.c:358
Size hash_get_shared_size(HASHCTL *info, int flags)
Definition dynahash.c:854
int64 hash_select_dirsize(int64 num_entries)
Definition dynahash.c:830
#define HASH_ALLOC
Definition hsearch.h:101
#define HASH_DIRSIZE
Definition hsearch.h:94
#define HASH_ATTACH
Definition hsearch.h:104
#define HASH_SHARED_MEM
Definition hsearch.h:103
void * ShmemAllocNoError(Size size)
Definition shmem.c:202
void * ShmemInitStruct(const char *name, Size size, bool *foundPtr)
Definition shmem.c:378
const char * name

References fb(), HASH_ALLOC, HASH_ATTACH, hash_create(), HASH_DIRSIZE, hash_get_shared_size(), hash_select_dirsize(), HASH_SHARED_MEM, name, ShmemAllocNoError(), and ShmemInitStruct().

Referenced by InitBufTable(), InitShmemIndex(), LockManagerShmemInit(), pgss_shmem_startup(), PredicateLockShmemInit(), and WaitEventCustomShmemInit().

◆ ShmemInitStruct()

void * ShmemInitStruct ( const char name,
Size  size,
bool foundPtr 
)
extern

Definition at line 378 of file shmem.c.

379{
380 ShmemIndexEnt *result;
381 void *structPtr;
382
384
385 if (!ShmemIndex)
386 {
387 /* Must be trying to create/attach to ShmemIndex itself */
388 Assert(strcmp(name, "ShmemIndex") == 0);
389
391 {
392 /* Must be initializing a (non-standalone) backend */
395 *foundPtr = true;
396 }
397 else
398 {
399 /*
400 * If the shmem index doesn't exist, we are bootstrapping: we must
401 * be trying to init the shmem index itself.
402 *
403 * Notice that the ShmemIndexLock is released before the shmem
404 * index has been initialized. This should be OK because no other
405 * process can be accessing shared memory yet.
406 */
408 structPtr = ShmemAlloc(size);
410 *foundPtr = false;
411 }
413 return structPtr;
414 }
415
416 /* look it up in the shmem index */
417 result = (ShmemIndexEnt *)
419
420 if (!result)
421 {
425 errmsg("could not create ShmemIndex entry for data structure \"%s\"",
426 name)));
427 }
428
429 if (*foundPtr)
430 {
431 /*
432 * Structure is in the shmem index so someone else has allocated it
433 * already. The size better be the same as the size we are trying to
434 * initialize to, or there is a name conflict (or worse).
435 */
436 if (result->size != size)
437 {
440 (errmsg("ShmemIndex entry size is wrong for data structure"
441 " \"%s\": expected %zu, actual %zu",
442 name, size, result->size)));
443 }
444 structPtr = result->location;
445 }
446 else
447 {
448 Size allocated_size;
449
450 /* It isn't in the table yet. allocate and initialize it */
451 structPtr = ShmemAllocRaw(size, &allocated_size);
452 if (structPtr == NULL)
453 {
454 /* out of memory; remove the failed ShmemIndex entry */
459 errmsg("not enough shared memory for data structure"
460 " \"%s\" (%zu bytes requested)",
461 name, size)));
462 }
463 result->size = size;
464 result->allocated_size = allocated_size;
465 result->location = structPtr;
466 }
467
469
471
473
474 return structPtr;
475}
void * hash_search(HTAB *hashp, const void *keyPtr, HASHACTION action, bool *foundPtr)
Definition dynahash.c:952
@ HASH_REMOVE
Definition hsearch.h:115
@ HASH_ENTER_NULL
Definition hsearch.h:116
bool LWLockAcquire(LWLock *lock, LWLockMode mode)
Definition lwlock.c:1176
void LWLockRelease(LWLock *lock)
Definition lwlock.c:1793
@ LW_EXCLUSIVE
Definition lwlock.h:112
bool ShmemAddrIsValid(const void *addr)
Definition shmem.c:265
void * ShmemAlloc(Size size)
Definition shmem.c:182
void * location
Definition shmem.h:58
Size size
Definition shmem.h:59
Size allocated_size
Definition shmem.h:60

References ShmemIndexEnt::allocated_size, Assert, CACHELINEALIGN, ereport, errcode(), errmsg(), ERROR, fb(), HASH_ENTER_NULL, HASH_REMOVE, hash_search(), ShmemAllocatorData::index, IsUnderPostmaster, ShmemIndexEnt::location, LW_EXCLUSIVE, LWLockAcquire(), LWLockRelease(), name, ShmemAddrIsValid(), ShmemAlloc(), ShmemAllocator, ShmemAllocRaw(), ShmemIndex, and ShmemIndexEnt::size.

Referenced by AioShmemInit(), ApplyLauncherShmemInit(), AsyncShmemInit(), AutoVacuumShmemInit(), BackendStatusShmemInit(), BackgroundWorkerShmemInit(), BTreeShmemInit(), BufferManagerShmemInit(), CheckpointerShmemInit(), CommitTsShmemInit(), dsm_shmem_init(), DSMRegistryShmemInit(), InitProcGlobal(), injection_shmem_startup(), InjectionPointShmemInit(), LockManagerShmemInit(), LogicalDecodingCtlShmemInit(), MultiXactShmemInit(), pgaio_worker_shmem_init(), PgArchShmemInit(), pgss_shmem_startup(), PMSignalShmemInit(), PredicateLockShmemInit(), ProcArrayShmemInit(), ProcSignalShmemInit(), ReplicationOriginShmemInit(), ReplicationSlotsShmemInit(), SerialInit(), SharedInvalShmemInit(), ShmemInitHash(), SimpleLruInit(), SlotSyncShmemInit(), StatsShmemInit(), StrategyInitialize(), SyncScanShmemInit(), test_aio_shmem_startup(), TwoPhaseShmemInit(), VarsupShmemInit(), WaitEventCustomShmemInit(), WaitLSNShmemInit(), WalRcvShmemInit(), WalSndShmemInit(), WalSummarizerShmemInit(), XLogPrefetchShmemInit(), XLogRecoveryShmemInit(), and XLOGShmemInit().

Variable Documentation

◆ ShmemLock

PGDLLIMPORT slock_t* ShmemLock
extern

Definition at line 105 of file shmem.c.

Referenced by GetLWTrancheName(), InitShmemAllocator(), LWLockNewTrancheId(), and ShmemAllocRaw().