You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
postgres/src/backend/storage/ipc/ipci.c

176 lines
4.2 KiB

/*-------------------------------------------------------------------------
*
* ipci.c
* POSTGRES inter-process communication initialization code.
*
* Portions Copyright (c) 1996-2004, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/storage/ipc/ipci.c,v 1.71 2004/08/29 05:06:48 momjian Exp $
*
*-------------------------------------------------------------------------
*/
#include "postgres.h"
#include "access/clog.h"
#include "access/subtrans.h"
#include "access/xlog.h"
#include "miscadmin.h"
#include "postmaster/bgwriter.h"
27 years ago
#include "storage/bufmgr.h"
#include "storage/freespace.h"
#include "storage/ipc.h"
#include "storage/lmgr.h"
#include "storage/lwlock.h"
#include "storage/pg_sema.h"
#include "storage/pg_shmem.h"
#include "storage/pmsignal.h"
#include "storage/proc.h"
27 years ago
#include "storage/sinval.h"
#include "storage/spin.h"
/*
* CreateSharedMemoryAndSemaphores
* Creates and initializes shared memory and semaphores.
*
* This is called by the postmaster or by a standalone backend.
* It is also called by a backend forked from the postmaster under
* the EXEC_BACKEND case. (In the non EXEC_BACKEND case, backends
* start life already attached to shared memory.) The initialization
* functions are set up to simply "attach" to pre-existing shared memory
* structures in the latter case. We have to do that in order to
* initialize pointers in local memory that reference the shared structures.
* (In the non EXEC_BACKEND case, these pointer values are inherited via
* fork() from the postmaster.)
*
* If "makePrivate" is true then we only need private memory, not shared
* memory. This is true for a standalone backend, false for a postmaster.
*/
void
CreateSharedMemoryAndSemaphores(bool makePrivate,
int maxBackends,
int port)
{
PGShmemHeader *seghdr = NULL;
if (!IsUnderPostmaster)
{
int size;
int numSemas;
/*
* Size of the Postgres shared-memory block is estimated via
* moderately-accurate estimates for the big hogs, plus 100K for
* the stuff that's too small to bother with estimating.
*/
size = hash_estimate_size(SHMEM_INDEX_SIZE, sizeof(ShmemIndexEnt));
size += BufferShmemSize();
size += LockShmemSize(maxBackends);
size += XLOGShmemSize();
size += CLOGShmemSize();
size += SUBTRANSShmemSize();
size += LWLockShmemSize();
size += SInvalShmemSize(maxBackends);
size += FreeSpaceShmemSize();
size += BgWriterShmemSize();
#ifdef EXEC_BACKEND
size += ShmemBackendArraySize();
#endif
size += 100000;
/* might as well round it off to a multiple of a typical page size */
size += 8192 - (size % 8192);
elog(DEBUG3, "invoking IpcMemoryCreate(size=%d)", size);
/*
* Create the shmem segment
*/
seghdr = PGSharedMemoryCreate(size, makePrivate, port);
/*
* Create semaphores
*/
numSemas = ProcGlobalSemas(maxBackends);
numSemas += SpinlockSemas();
PGReserveSemaphores(numSemas, port);
}
else
{
/*
* Attach to the shmem segment. (this should only ever be reached
* by EXEC_BACKEND code, and only then with makePrivate == false)
*/
#ifdef EXEC_BACKEND
Assert(!makePrivate);
seghdr = PGSharedMemoryCreate(-1, makePrivate, 0);
#else
Assert(false);
#endif
}
/*
* Set up shared memory allocation mechanism
*/
InitShmemAllocation(seghdr, !IsUnderPostmaster);
/*
* Now initialize LWLocks, which do shared memory allocation and are
* needed for InitShmemIndex.
*/
if (!IsUnderPostmaster)
CreateLWLocks();
/*
* Set up shmem.c index hashtable
*/
InitShmemIndex();
/*
* Set up xlog, clog, and buffers
*/
XLOGShmemInit();
CLOGShmemInit();
SUBTRANSShmemInit();
InitBufferPool();
/*
* Set up lock manager
*/
InitLocks();
Try to reduce confusion about what is a lock method identifier, a lock method control structure, or a table of control structures. . Use type LOCKMASK where an int is not a counter. . Get rid of INVALID_TABLEID, use INVALID_LOCKMETHOD instead. . Use INVALID_LOCKMETHOD instead of (LOCKMETHOD) NULL, because LOCKMETHOD is not a pointer. . Define and use macro LockMethodIsValid. . Rename LOCKMETHOD to LOCKMETHODID. . Remove global variable LongTermTableId in lmgr.c, because it is never used. . Make LockTableId static in lmgr.c, because it is used nowhere else. Why not remove it and use DEFAULT_LOCKMETHOD? . Rename the lock method control structure from LOCKMETHODTABLE to LockMethodData. Introduce a pointer type named LockMethod. . Remove elog(FATAL) after InitLockTable() call in CreateSharedMemoryAndSemaphores(), because if something goes wrong, there is elog(FATAL) in LockMethodTableInit(), and if this doesn't help, an elog(ERROR) in InitLockTable() is promoted to FATAL. . Make InitLockTable() void, because its only caller does not use its return value any more. . Rename variables in lock.c to avoid statements like LockMethodTable[NumLockMethods] = lockMethodTable; lockMethodTable = LockMethodTable[lockmethod]; . Change LOCKMETHODID type to uint16 to fit into struct LOCKTAG. . Remove static variables BITS_OFF and BITS_ON from lock.c, because I agree to this doubt: * XXX is a fetch from a static array really faster than a shift? . Define and use macros LOCKBIT_ON/OFF. Manfred Koizar
22 years ago
InitLockTable(maxBackends);
/*
* Set up process table
*/
InitProcGlobal(maxBackends);
/*
* Set up shared-inval messaging
*/
CreateSharedInvalidationState(maxBackends);
/*
* Set up free-space map
*/
InitFreeSpaceMap();
/*
* Set up interprocess signaling mechanisms
*/
PMSignalInit();
BgWriterShmemInit();
#ifdef EXEC_BACKEND
/*
* Alloc the win32 shared backend array
*/
if (!IsUnderPostmaster)
ShmemBackendArrayAllocation();
#endif
}