1
0
mirror of https://github.com/postgres/postgres.git synced 2025-11-06 07:49:08 +03:00

More cleanups of the include files

- centralizing to simplify the -I's required to compile
This commit is contained in:
Marc G. Fournier
1996-08-28 01:59:28 +00:00
parent ca405ae4bf
commit 1054097464
107 changed files with 13489 additions and 3 deletions

View File

@@ -0,0 +1,32 @@
/*-------------------------------------------------------------------------
*
* backendid.h--
* POSTGRES backend id communication definitions
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: backendid.h,v 1.1 1996/08/28 01:57:54 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef BACKENDID_H
#define BACKENDID_H
/* ----------------
* pulled out of sinval.h to temporarily reduce #include nesting.
* -cim 8/17/90
* ----------------
*/
typedef int16 BackendId; /* unique currently active backend identifier */
#define InvalidBackendId (-1)
typedef int32 BackendTag; /* unique backend identifier */
#define InvalidBackendTag (-1)
extern BackendId MyBackendId; /* backend id of this backend */
extern BackendTag MyBackendTag; /* backend tag of this backend */
#endif /* BACKENDID_H */

114
src/include/storage/block.h Normal file
View File

@@ -0,0 +1,114 @@
/*-------------------------------------------------------------------------
*
* block.h--
* POSTGRES disk block definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: block.h,v 1.1 1996/08/28 01:57:55 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef BLOCK_H
#define BLOCK_H
#include "c.h"
/*
* BlockNumber:
*
* each data file (heap or index) is divided into postgres disk blocks
* (which may be thought of as the unit of i/o -- a postgres buffer
* contains exactly one disk block). the blocks are numbered
* sequentially, 0 to 0xFFFFFFFE.
*
* InvalidBlockNumber is the same thing as P_NEW in buf.h.
*
* the access methods, the buffer manager and the storage manager are
* more or less the only pieces of code that should be accessing disk
* blocks directly.
*/
typedef uint32 BlockNumber;
#define InvalidBlockNumber ((BlockNumber) 0xFFFFFFFF)
/*
* BlockId:
*
* this is a storage type for BlockNumber. in other words, this type
* is used for on-disk structures (e.g., in HeapTupleData) whereas
* BlockNumber is the type on which calculations are performed (e.g.,
* in access method code).
*
* there doesn't appear to be any reason to have separate types except
* for the fact that BlockIds can be SHORTALIGN'd (and therefore any
* structures that contains them, such as ItemPointerData, can also be
* SHORTALIGN'd). this is an important consideration for reducing the
* space requirements of the line pointer (ItemIdData) array on each
* page and the header of each heap or index tuple, so it doesn't seem
* wise to change this without good reason.
*/
typedef struct BlockIdData {
uint16 bi_hi;
uint16 bi_lo;
} BlockIdData;
typedef BlockIdData *BlockId; /* block identifier */
/* ----------------
* support macros
* ----------------
*/
/*
* BlockNumberIsValid --
* True iff blockNumber is valid.
*/
#define BlockNumberIsValid(blockNumber) \
((bool) ((int32) (blockNumber) != InvalidBlockNumber))
/*
* BlockIdIsValid --
* True iff the block identifier is valid.
*/
#define BlockIdIsValid(blockId) \
((bool) PointerIsValid(blockId))
/*
* BlockIdSet --
* Sets a block identifier to the specified value.
*/
#define BlockIdSet(blockId, blockNumber) \
Assert(PointerIsValid(blockId)); \
(blockId)->bi_hi = (blockNumber) >> 16; \
(blockId)->bi_lo = (blockNumber) & 0xffff
/*
* BlockIdCopy --
* Copy a block identifier.
*/
#define BlockIdCopy(toBlockId, fromBlockId) \
Assert(PointerIsValid(toBlockId)); \
Assert(PointerIsValid(fromBlockId)); \
(toBlockId)->bi_hi = (fromBlockId)->bi_hi; \
(toBlockId)->bi_lo = (fromBlockId)->bi_lo
/*
* BlockIdEquals --
* Check for block number equality.
*/
#define BlockIdEquals(blockId1, blockId2) \
((blockId1)->bi_hi == (blockId2)->bi_hi && \
(blockId1)->bi_lo == (blockId2)->bi_lo)
/*
* BlockIdGetBlockNumber --
* Retrieve the block number from a block identifier.
*/
#define BlockIdGetBlockNumber(blockId) \
(AssertMacro(BlockIdIsValid(blockId)) ? \
(BlockNumber) (((blockId)->bi_hi << 16) | ((uint16) (blockId)->bi_lo)) : \
(BlockNumber) InvalidBlockNumber)
#endif /* BLOCK_H */

47
src/include/storage/buf.h Normal file
View File

@@ -0,0 +1,47 @@
/*-------------------------------------------------------------------------
*
* buf.h--
* Basic buffer manager data types.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: buf.h,v 1.1 1996/08/28 01:57:57 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef BUF_H
#define BUF_H
#define InvalidBuffer (0)
#define UnknownBuffer (-99999)
typedef long Buffer;
/*
* BufferIsInvalid --
* True iff the buffer is invalid.
*/
#define BufferIsInvalid(buffer) ((buffer) == InvalidBuffer)
/*
* BufferIsUnknown --
* True iff the buffer is unknown.
*/
#define BufferIsUnknown(buffer) ((buffer) == UnknownBuffer)
/*
* BufferIsLocal --
* True iff the buffer is local (not visible to other servers).
*/
#define BufferIsLocal(buffer) ((buffer) < 0)
/*
* If NO_BUFFERISVALID is defined, all error checking using BufferIsValid()
* are suppressed. Decision-making using BufferIsValid is not affected.
* This should be set only if one is sure there will be no errors.
* - plai 9/10/90
*/
#undef NO_BUFFERISVALID
#endif /* BUF_H */

View File

@@ -0,0 +1,244 @@
/*-------------------------------------------------------------------------
*
* buf_internals.h--
* Internal definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: buf_internals.h,v 1.1 1996/08/28 01:58:00 scrappy Exp $
*
* NOTE
* If BUFFERPAGE0 is defined, then 0 will be used as a
* valid buffer page number.
*
*-------------------------------------------------------------------------
*/
#ifndef BUFMGR_INTERNALS_H
#define BUFMGR_INTERNALS_H
#include "postgres.h"
#include "storage/buf.h"
#include "storage/ipc.h"
#include "storage/shmem.h"
#include "miscadmin.h"
#include "storage/lmgr.h"
#include "utils/rel.h"
#include "utils/relcache.h"
/* Buf Mgr constants */
/* in bufmgr.c */
extern int NBuffers;
extern int Data_Descriptors;
extern int Free_List_Descriptor;
extern int Lookup_List_Descriptor;
extern int Num_Descriptors;
/*
* Flags for buffer descriptors
*/
#define BM_DIRTY (1 << 0)
#define BM_PRIVATE (1 << 1)
#define BM_VALID (1 << 2)
#define BM_DELETED (1 << 3)
#define BM_FREE (1 << 4)
#define BM_IO_IN_PROGRESS (1 << 5)
#define BM_IO_ERROR (1 << 6)
typedef bits16 BufFlags;
typedef struct sbufdesc BufferDesc;
typedef struct sbufdesc BufferHdr;
typedef struct buftag BufferTag;
/* long * so alignment will be correct */
typedef long **BufferBlock;
struct buftag{
LRelId relId;
BlockNumber blockNum; /* blknum relative to begin of reln */
};
#define CLEAR_BUFFERTAG(a)\
(a)->relId.dbId = InvalidOid; \
(a)->relId.relId = InvalidOid; \
(a)->blockNum = InvalidBlockNumber
#define INIT_BUFFERTAG(a,xx_reln,xx_blockNum) \
{ \
(a)->blockNum = xx_blockNum;\
(a)->relId = RelationGetLRelId(xx_reln); \
}
#define COPY_BUFFERTAG(a,b)\
{ \
(a)->blockNum = (b)->blockNum;\
LRelIdAssign(*(a),*(b));\
}
#define EQUAL_BUFFERTAG(a,b) \
(((a)->blockNum == (b)->blockNum) &&\
(OID_Equal((a)->relId.relId,(b)->relId.relId)))
#define BAD_BUFFER_ID(bid) ((bid<1) || (bid>(NBuffers)))
#define INVALID_DESCRIPTOR (-3)
/*
* bletch hack -- anyplace that we declare space for relation or
* database names, we just use '16', not a symbolic constant, to
* specify their lengths. BM_NAMESIZE is the length of these names,
* and is used in the buffer manager code. somebody with lots of
* spare time should do this for all the other modules, too.
*/
#define BM_NAMESIZE 16
/*
* struct sbufdesc -- shared buffer cache metadata for a single
* shared buffer descriptor.
*
* We keep the name of the database and relation in which this
* buffer appears in order to avoid a catalog lookup on cache
* flush if we don't have the reldesc in the cache. It is also
* possible that the relation to which this buffer belongs is
* not visible to all backends at the time that it gets flushed.
* Dbname, relname, dbid, and relid are enough to determine where
* to put the buffer, for all storage managers.
*/
struct sbufdesc {
Buffer freeNext; /* link for freelist chain */
Buffer freePrev;
SHMEM_OFFSET data; /* pointer to data in buf pool */
/* tag and id must be together for table lookup to work */
BufferTag tag; /* file/block identifier */
int buf_id; /* maps global desc to local desc */
BufFlags flags; /* described below */
int16 bufsmgr; /* storage manager id for buffer */
unsigned refcount; /* # of times buffer is pinned */
char sb_dbname[NAMEDATALEN+1]; /* name of db in which buf belongs */
char sb_relname[NAMEDATALEN+1]; /* name of reln */
#ifdef HAS_TEST_AND_SET
/* can afford a dedicated lock if test-and-set locks are available */
slock_t io_in_progress_lock;
#endif /* HAS_TEST_AND_SET */
/*
* I padded this structure to a power of 2 (128 bytes on a MIPS) because
* BufferDescriptorGetBuffer is called a billion times and it does an
* C pointer subtraction (i.e., "x - y" -> array index of x relative
* to y, which is calculated using division by struct size). Integer
* ".div" hits you for 35 cycles, as opposed to a 1-cycle "sra" ...
* this hack cut 10% off of the time to create the Wisconsin database!
* It eats up more shared memory, of course, but we're (allegedly)
* going to make some of these types bigger soon anyway... -pma 1/2/93
*/
/* NO spinlock */
#if defined(PORTNAME_ultrix4)
char sb_pad[60]; /* no slock_t */
#endif /* mips */
/* HAS_TEST_AND_SET -- platform dependent size */
#if defined(PORTNAME_aix)
char sb_pad[44]; /* typedef unsigned int slock_t; */
#endif /* aix */
#if defined(PORTNAME_alpha)
char sb_pad[40]; /* typedef msemaphore slock_t; */
#endif /* alpha */
#if defined(PORTNAME_hpux)
char sb_pad[44]; /* typedef struct { int sem[4]; } slock_t; */
#endif /* hpux */
#if defined(PORTNAME_irix5)
char sb_pad[44]; /* typedef abilock_t slock_t; */
#endif /* irix5 */
#if defined(PORTNAME_next)
char sb_pad[56]; /* typedef struct mutex slock_t; */
#endif /* next */
/* HAS_TEST_AND_SET -- default 1 byte spinlock */
#if defined(PORTNAME_BSD44_derived) || \
defined(PORTNAME_bsdi) || \
defined(PORTNAME_bsdi_2_1) || \
defined(PORTNAME_i386_solaris) || \
defined(PORTNAME_linux) || \
defined(PORTNAME_sparc) || \
defined(PORTNAME_sparc_solaris)
char sb_pad[56]; /* has slock_t */
#endif /* 1 byte slock_t */
};
/*
* mao tracing buffer allocation
*/
/*#define BMTRACE*/
#ifdef BMTRACE
typedef struct _bmtrace {
int bmt_pid;
long bmt_buf;
long bmt_dbid;
long bmt_relid;
int bmt_blkno;
int bmt_op;
#define BMT_NOTUSED 0
#define BMT_ALLOCFND 1
#define BMT_ALLOCNOTFND 2
#define BMT_DEALLOC 3
} bmtrace;
#endif /* BMTRACE */
/*
* Bufmgr Interface:
*/
/* Internal routines: only called by buf.c */
/*freelist.c*/
extern void AddBufferToFreelist(BufferDesc *bf);
extern void PinBuffer(BufferDesc *buf);
extern void PinBuffer_Debug(char *file, int line, BufferDesc *buf);
extern void UnpinBuffer(BufferDesc *buf);
extern void UnpinBuffer_Debug(char *file, int line, BufferDesc *buf);
extern BufferDesc *GetFreeBuffer(void);
extern void InitFreeList(bool init);
extern void DBG_FreeListCheck(int nfree);
/* buf_table.c */
extern void InitBufTable(void);
extern BufferDesc *BufTableLookup(BufferTag *tagPtr);
extern bool BufTableDelete(BufferDesc *buf);
extern bool BufTableInsert(BufferDesc *buf);
extern void DBG_LookupListCheck(int nlookup);
/* bufmgr.c */
extern BufferDesc *BufferDescriptors;
extern BufferBlock BufferBlocks;
extern long *PrivateRefCount;
extern long *LastRefCount;
extern SPINLOCK BufMgrLock;
/* localbuf.c */
extern long *LocalRefCount;
extern BufferDesc *LocalBufferDescriptors;
extern int NLocBuffer;
extern BufferDesc *LocalBufferAlloc(Relation reln, BlockNumber blockNum,
bool *foundPtr);
extern int WriteLocalBuffer(Buffer buffer, bool release);
extern int FlushLocalBuffer(Buffer buffer);
extern void InitLocalBuffer();
extern void LocalBufferSync();
extern void ResetLocalBufferPool();
#endif /* BUFMGR_INTERNALS_H */

View File

@@ -0,0 +1,112 @@
/*-------------------------------------------------------------------------
*
* bufmgr.h--
* POSTGRES buffer manager definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: bufmgr.h,v 1.1 1996/08/28 01:58:01 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef BUFMGR_H
#define BUFMGR_H
#include "c.h"
#include "machine.h" /* for BLCKSZ */
#include "utils/rel.h"
#include "storage/buf_internals.h" /* UGLY! -- ay */
/*
* the maximum size of a disk block for any possible installation.
*
* in theory this could be anything, but in practice this is actually
* limited to 2^13 bytes because we have limited ItemIdData.lp_off and
* ItemIdData.lp_len to 13 bits (see itemid.h).
*/
#define MAXBLCKSZ 8192
typedef void *Block;
/* special pageno for bget */
#define P_NEW InvalidBlockNumber /* grow the file to get a new page */
typedef bits16 BufferLock;
/**********************************************************************
the rest is function defns in the bufmgr that are externally callable
**********************************************************************/
/*
* These routines are beaten on quite heavily, hence the macroization.
* See buf_internals.h for a related comment.
*/
#define BufferDescriptorGetBuffer(bdesc) ((bdesc)->buf_id + 1)
/*
* BufferIsPinned --
* True iff the buffer is pinned (and therefore valid)
*
* Note:
* Smenatics are identical to BufferIsValid
* XXX - need to remove either one eventually.
*/
#define BufferIsPinned BufferIsValid
extern int ShowPinTrace;
/*
* prototypes for functions in bufmgr.c
*/
extern Buffer RelationGetBufferWithBuffer(Relation relation,
BlockNumber blockNumber, Buffer buffer);
extern Buffer ReadBuffer(Relation reln, BlockNumber blockNum);
extern Buffer ReadBuffer_Debug(char *file, int line, Relation reln,
BlockNumber blockNum);
extern int WriteBuffer(Buffer buffer);
extern void WriteBuffer_Debug(char *file, int line, Buffer buffer);
extern void DirtyBufferCopy(Oid dbid, Oid relid, BlockNumber blkno,
char *dest);
extern int WriteNoReleaseBuffer(Buffer buffer);
extern Buffer ReleaseAndReadBuffer(Buffer buffer, Relation relation,
BlockNumber blockNum);
extern void InitBufferPool(IPCKey key);
extern void PrintBufferUsage(FILE *statfp);
extern void ResetBufferUsage(void);
extern void ResetBufferPool(void);
extern int BufferPoolCheckLeak(void);
extern void FlushBufferPool(int StableMainMemoryFlag);
extern bool BufferIsValid(Buffer bufnum);
extern BlockNumber BufferGetBlockNumber(Buffer buffer);
extern Relation BufferGetRelation(Buffer buffer);
extern BlockNumber RelationGetNumberOfBlocks(Relation relation);
extern Block BufferGetBlock(Buffer buffer);
extern void ReleaseTmpRelBuffers(Relation tempreldesc);
extern void DropBuffers(Oid dbid);
extern void PrintBufferDescs(void);
extern void PrintPinnedBufs(void);
extern int BufferShmemSize(void);
extern void BufferPoolBlowaway(void);
extern void IncrBufferRefCount(Buffer buffer);
extern int ReleaseBuffer(Buffer buffer);
extern void IncrBufferRefCount_Debug(char *file, int line, Buffer buffer);
extern void ReleaseBuffer_Debug(char *file, int line, Buffer buffer);
extern int ReleaseAndReadBuffer_Debug(char *file,
int line,
Buffer buffer,
Relation relation,
BlockNumber blockNum);
extern void BufferRefCountReset(int *refcountsave);
extern void BufferRefCountRestore(int *refcountsave);
#endif /* !defined(BufMgrIncluded) */

View File

@@ -0,0 +1,256 @@
/*-------------------------------------------------------------------------
*
* bufpage.h--
* Standard POSTGRES buffer page definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: bufpage.h,v 1.1 1996/08/28 01:58:03 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef BUFPAGE_H
#define BUFPAGE_H
#include "c.h"
#include "machine.h" /* for BLCKSZ */
#include "storage/buf.h"
#include "storage/item.h"
#include "storage/itemid.h"
#include "storage/itemptr.h"
/*
* a postgres disk page is an abstraction layered on top of a postgres
* disk block (which is simply a unit of i/o, see block.h).
*
* specifically, while a disk block can be unformatted, a postgres
* disk page is always a slotted page of the form:
*
* +----------------+---------------------------------+
* | PageHeaderData | linp0 linp1 linp2 ... |
* +-----------+----+---------------------------------+
* | ... linpN | |
* +-----------+--------------------------------------+
* | ^ pd_lower |
* | |
* | v pd_upper |
* +-------------+------------------------------------+
* | | tupleN ... |
* +-------------+------------------+-----------------+
* | ... tuple2 tuple1 tuple0 | "special space" |
* +--------------------------------+-----------------+
* ^ pd_special
*
* a page is full when nothing can be added between pd_lower and
* pd_upper.
*
* all blocks written out by an access method must be disk pages.
*
* EXCEPTIONS:
*
* obviously, a page is not formatted before it is initialized with by
* a call to PageInit.
*
* the contents of the special pg_variable/pg_time/pg_log tables are
* raw disk blocks with special formats. these are the only "access
* methods" that need not write disk pages.
*
* NOTES:
*
* linp0..N form an ItemId array. ItemPointers point into this array
* rather than pointing directly to a tuple.
*
* tuple0..N are added "backwards" on the page. because a tuple's
* ItemPointer points to its ItemId entry rather than its actual
* byte-offset position, tuples can be physically shuffled on a page
* whenever the need arises.
*
* AM-generic per-page information is kept in the pd_opaque field of
* the PageHeaderData. (this is currently only the page size.)
* AM-specific per-page data is kept in the area marked "special
* space"; each AM has an "opaque" structure defined somewhere that is
* stored as the page trailer. an access method should always
* initialize its pages with PageInit and then set its own opaque
* fields.
*/
typedef Pointer Page;
/*
* PageIsValid --
* True iff page is valid.
*/
#define PageIsValid(page) PointerIsValid(page)
/*
* location (byte offset) within a page.
*
* note that this is actually limited to 2^13 because we have limited
* ItemIdData.lp_off and ItemIdData.lp_len to 13 bits (see itemid.h).
*/
typedef uint16 LocationIndex;
/*
* space management information generic to any page
*
* od_pagesize - size in bytes.
* in reality, we need at least 64B to fit the
* page header, opaque space and a minimal tuple;
* on the high end, we can only support pages up
* to 8KB because lp_off/lp_len are 13 bits.
*/
typedef struct OpaqueData {
uint16 od_pagesize;
} OpaqueData;
typedef OpaqueData *Opaque;
/*
* disk page organization
*/
typedef struct PageHeaderData {
LocationIndex pd_lower; /* offset to start of free space */
LocationIndex pd_upper; /* offset to end of free space */
LocationIndex pd_special; /* offset to start of special space */
OpaqueData pd_opaque; /* AM-generic information */
ItemIdData pd_linp[1]; /* line pointers */
} PageHeaderData;
typedef PageHeaderData *PageHeader;
typedef enum {
ShufflePageManagerMode,
OverwritePageManagerMode
} PageManagerMode;
/* ----------------
* misc support macros
* ----------------
*/
/*
* XXX this is wrong -- ignores padding/alignment, variable page size,
* AM-specific opaque space at the end of the page (as in btrees), ...
* however, it at least serves as an upper bound for heap pages.
*/
#define MAXTUPLEN (BLCKSZ - sizeof (PageHeaderData))
/* ----------------------------------------------------------------
* page support macros
* ----------------------------------------------------------------
*/
/*
* PageIsValid -- This is defined in page.h.
*/
/*
* PageIsUsed --
* True iff the page size is used.
*
* Note:
* Assumes page is valid.
*/
#define PageIsUsed(page) \
(AssertMacro(PageIsValid(page)) ? \
((bool) (((PageHeader) (page))->pd_lower != 0)) : false)
/*
* PageIsEmpty --
* returns true iff no itemid has been allocated on the page
*/
#define PageIsEmpty(page) \
(((PageHeader) (page))->pd_lower == \
(sizeof(PageHeaderData) - sizeof(ItemIdData)) ? true : false)
/*
* PageGetItemId --
* Returns an item identifier of a page.
*/
#define PageGetItemId(page, offsetNumber) \
((ItemId) (&((PageHeader) (page))->pd_linp[(-1) + (offsetNumber)]))
/* ----------------
* macros to access opaque space
* ----------------
*/
/*
* PageSizeIsValid --
* True iff the page size is valid.
*
* XXX currently all page sizes are "valid" but we only actually
* use BLCKSZ.
*/
#define PageSizeIsValid(pageSize) 1
/*
* PageGetPageSize --
* Returns the page size of a page.
*
* this can only be called on a formatted page (unlike
* BufferGetPageSize, which can be called on an unformatted page).
* however, it can be called on a page for which there is no buffer.
*/
#define PageGetPageSize(page) \
((Size) ((PageHeader) (page))->pd_opaque.od_pagesize)
/*
* PageSetPageSize --
* Sets the page size of a page.
*/
#define PageSetPageSize(page, size) \
((PageHeader) (page))->pd_opaque.od_pagesize = (size)
/* ----------------
* page special data macros
* ----------------
*/
/*
* PageGetSpecialSize --
* Returns size of special space on a page.
*
* Note:
* Assumes page is locked.
*/
#define PageGetSpecialSize(page) \
((uint16) (PageGetPageSize(page) - ((PageHeader)page)->pd_special))
/*
* PageGetSpecialPointer --
* Returns pointer to special space on a page.
*
* Note:
* Assumes page is locked.
*/
#define PageGetSpecialPointer(page) \
(AssertMacro(PageIsValid(page)) ? \
(char *) ((char *) (page) + ((PageHeader) (page))->pd_special) \
: (char *) 0)
/* ----------------------------------------------------------------
* extern declarations
* ----------------------------------------------------------------
*/
extern Size BufferGetPageSize(Buffer buffer);
extern Page BufferGetPage(Buffer buffer);
extern void PageInit(Page page, Size pageSize, Size specialSize);
extern Item PageGetItem(Page page, ItemId itemId);
extern OffsetNumber PageAddItem(Page page, Item item, Size size,
OffsetNumber offsetNumber, ItemIdFlags flags);
extern Page PageGetTempPage(Page page, Size specialSize);
extern void PageRestoreTempPage(Page tempPage, Page oldPage);
extern OffsetNumber PageGetMaxOffsetNumber(Page page);
extern void PageRepairFragmentation(Page page);
extern Size PageGetFreeSpace(Page page);
extern void PageManagerModeSet(PageManagerMode mode);
extern void PageIndexTupleDelete(Page page, OffsetNumber offset);
extern void PageIndexTupleDeleteAdjustLinePointers(PageHeader phdr,
char *location, Size size);
#endif /* BUFPAGE_H */

96
src/include/storage/fd.h Normal file
View File

@@ -0,0 +1,96 @@
/*-------------------------------------------------------------------------
*
* fd.h--
* Virtual file descriptor definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: fd.h,v 1.1 1996/08/28 01:58:04 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
/*
* calls:
*
* File {Close, Read, Write, Seek, Tell, Sync}
* {File Name Open, Allocate, Free} File
*
* These are NOT JUST RENAMINGS OF THE UNIX ROUTINES.
* use them for all file activity...
*
* fd = FilePathOpenFile("foo", O_RDONLY);
* File fd;
*
* use AllocateFile if you need a file descriptor in some other context.
* it will make sure that there is a file descriptor free
*
* use FreeFile to let the virtual file descriptor package know that
* there is now a free fd (when you are done with it)
*
* AllocateFile();
* FreeFile();
*/
#ifndef FD_H
#define FD_H
/*
* FileOpen uses the standard UNIX open(2) flags.
*/
#include <fcntl.h> /* for O_ on most */
#ifndef O_RDONLY
#include <sys/file.h> /* for O_ on the rest */
#endif /* O_RDONLY */
/*
* FileSeek uses the standard UNIX lseek(2) flags.
*/
#ifndef WIN32
#include <unistd.h> /* for SEEK_ on most */
#else
#ifndef SEEK_SET
#include <stdio.h> /* for SEEK_ on the rest */
#endif /* SEEK_SET */
#endif /* WIN32 */
#include "c.h"
#include "storage/block.h"
typedef char *FileName;
typedef int File;
/* originally in libpq-fs.h */
struct pgstat { /* just the fields we need from stat structure */
int st_ino;
int st_mode;
unsigned int st_size;
unsigned int st_sizehigh; /* high order bits */
/* 2^64 == 1.8 x 10^20 bytes */
int st_uid;
int st_atime_s; /* just the seconds */
int st_mtime_s; /* since SysV and the new BSD both have */
int st_ctime_s; /* usec fields.. */
};
/*
* prototypes for functions in fd.c
*/
extern void FileInvalidate(File file);
extern File FileNameOpenFile(FileName fileName, int fileFlags, int fileMode);
extern File PathNameOpenFile(FileName fileName, int fileFlags, int fileMode);
extern void FileClose(File file);
extern void FileUnlink(File file);
extern int FileRead(File file, char *buffer, int amount);
extern int FileWrite(File file, char *buffer, int amount);
extern long FileSeek(File file, long offset, int whence);
extern long FileTell(File file);
extern int FileTruncate(File file, int offset);
extern int FileSync(File file);
extern int FileNameUnlink(char *filename);
extern void AllocateFile(void);
extern void FreeFile(void);
extern void closeAllVfds(void);
extern void closeOneVfd(void);
#endif /* FD_H */

302
src/include/storage/ipc.h Normal file
View File

@@ -0,0 +1,302 @@
/*-------------------------------------------------------------------------
*
* ipc.h--
* POSTGRES inter-process communication definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: ipc.h,v 1.1 1996/08/28 01:58:05 scrappy Exp $
*
* NOTES
* This file is very architecture-specific. This stuff should actually
* be factored into the port/ directories.
*
*-------------------------------------------------------------------------
*/
#ifndef IPC_H
#define IPC_H
#include <sys/types.h>
#ifndef _IPC_
#define _IPC_
#include <sys/ipc.h>
#endif
#include "c.h"
/*
* Many architectures have support for user-level spinlocks (i.e., an
* atomic test-and-set instruction). However, we have only written
* spinlock code for the architectures listed.
*/
#if defined(PORTNAME_aix) || \
defined(PORTNAME_alpha) || \
defined(PORTNAME_BSD44_derived) || \
defined(PORTNAME_bsdi) || \
defined(PORTNAME_bsdi_2_1) || \
defined(PORTNAME_hpux) || \
defined(PORTNAME_i386_solaris) || \
defined(PORTNAME_irix5) || \
defined(PORTNAME_linux) || \
defined(PORTNAME_next) || \
defined(PORTNAME_sparc) || \
defined(PORTNAME_sparc_solaris)
#define HAS_TEST_AND_SET
#endif
#if defined(HAS_TEST_AND_SET)
#if defined(PORTNAME_aix)
/*
* The AIX C library has the cs(3) builtin for compare-and-set that
* operates on ints.
*/
typedef unsigned int slock_t;
#else /* aix */
#if defined(PORTNAME_alpha)
#include <sys/mman.h>
typedef msemaphore slock_t;
#else /* alpha */
#if defined(PORTNAME_hpux)
/*
* The PA-RISC "semaphore" for the LDWCX instruction is 4 bytes aligned
* to a 16-byte boundary.
*/
typedef struct { int sem[4]; } slock_t;
#else /* hpux */
#if defined(PORTNAME_irix5)
#include <abi_mutex.h>
typedef abilock_t slock_t;
#else /* irix5 */
#if defined(PORTNAME_next)
/*
* Use Mach mutex routines since these are, in effect, test-and-set
* spinlocks.
*/
#undef NEVER /* definition in cthreads.h conflicts with parse.h */
#include <mach/cthreads.h>
typedef struct mutex slock_t;
#else /* next */
/*
* On all other architectures spinlocks are a single byte.
*/
typedef unsigned char slock_t;
#endif /* next */
#endif /* irix5 */
#endif /* hpux */
#endif /* alpha */
#endif /* aix */
extern void S_LOCK(slock_t *lock);
extern void S_UNLOCK(slock_t *lock);
extern void S_INIT_LOCK(slock_t *lock);
#if defined(PORTNAME_alpha) || \
defined(PORTNAME_hpux) || \
defined(PORTNAME_irix5) || \
defined(PORTNAME_next)
extern int S_LOCK_FREE(slock_t *lock);
#else
#define S_LOCK_FREE(lock) ((*lock) == 0)
#endif
#endif /* HAS_TEST_AND_SET */
/*
* On architectures for which we have not implemented spinlocks (or
* cannot do so), we use System V semaphores. We also use them for
* long locks. For some reason union semun is never defined in the
* System V header files so we must do it ourselves.
*
* bsdi_2_1 does not need this
*/
#if defined(sequent) || \
defined(PORTNAME_aix) || \
defined(PORTNAME_alpha) || \
defined(PORTNAME_bsdi) || \
defined(PORTNAME_hpux) || \
defined(PORTNAME_i386_solaris) || \
defined(PORTNAME_sparc_solaris) || \
defined(PORTNAME_ultrix4) || \
defined(PORTNAME_svr4) || \
defined(WIN32)
union semun {
int val;
struct semid_ds *buf;
unsigned short *array;
};
#endif
typedef uint16 SystemPortAddress;
/* semaphore definitions */
#define IPCProtection (0600) /* access/modify by user only */
#define IPC_NMAXSEM 25 /* maximum number of semaphores */
#define IpcSemaphoreDefaultStartValue 255
#define IpcSharedLock (-1)
#define IpcExclusiveLock (-255)
#define IpcUnknownStatus (-1)
#define IpcInvalidArgument (-2)
#define IpcSemIdExist (-3)
#define IpcSemIdNotExist (-4)
typedef uint32 IpcSemaphoreKey; /* semaphore key */
typedef int IpcSemaphoreId;
/* shared memory definitions */
#define IpcMemCreationFailed (-1)
#define IpcMemIdGetFailed (-2)
#define IpcMemAttachFailed 0
typedef uint32 IPCKey;
#define PrivateIPCKey IPC_PRIVATE
#define DefaultIPCKey 17317
typedef uint32 IpcMemoryKey; /* shared memory key */
typedef int IpcMemoryId;
/* ipc.c */
extern void exitpg(int code);
extern void quasi_exitpg(void);
extern on_exitpg(void (*function)(), caddr_t arg);
extern IpcSemaphoreId IpcSemaphoreCreate(IpcSemaphoreKey semKey,
int semNum, int permission, int semStartValue,
int removeOnExit, int *status);
extern void IpcSemaphoreSet(int semId, int semno, int value);
extern void IpcSemaphoreKill(IpcSemaphoreKey key);
extern void IpcSemaphoreLock(IpcSemaphoreId semId, int sem, int lock);
extern void IpcSemaphoreUnlock(IpcSemaphoreId semId, int sem, int lock);
extern int IpcSemaphoreGetCount(IpcSemaphoreId semId, int sem);
extern int IpcSemaphoreGetValue(IpcSemaphoreId semId, int sem);
extern IpcMemoryId IpcMemoryCreate(IpcMemoryKey memKey, uint32 size,
int permission);
extern IpcMemoryId IpcMemoryIdGet(IpcMemoryKey memKey, uint32 size);
extern void IpcMemoryDetach(int status, char *shmaddr);
extern char *IpcMemoryAttach(IpcMemoryId memId);
extern void IpcMemoryKill(IpcMemoryKey memKey);
extern void CreateAndInitSLockMemory(IPCKey key);
extern void AttachSLockMemory(IPCKey key);
#ifdef HAS_TEST_AND_SET
#define NSLOCKS 2048
#define NOLOCK 0
#define SHAREDLOCK 1
#define EXCLUSIVELOCK 2
typedef enum _LockId_ {
BUFMGRLOCKID,
LOCKLOCKID,
OIDGENLOCKID,
SHMEMLOCKID,
BINDINGLOCKID,
LOCKMGRLOCKID,
SINVALLOCKID,
#ifdef MAIN_MEMORY
MMCACHELOCKID,
#endif /* MAIN_MEMORY */
PROCSTRUCTLOCKID,
FIRSTFREELOCKID
} _LockId_;
#define MAX_SPINS FIRSTFREELOCKID
typedef struct slock {
slock_t locklock;
unsigned char flag;
short nshlocks;
slock_t shlock;
slock_t exlock;
slock_t comlock;
struct slock *next;
} SLock;
extern void ExclusiveLock(int lockid);
extern void ExclusiveUnlock(int lockid);
extern bool LockIsFree(int lockid);
#else /* HAS_TEST_AND_SET */
typedef enum _LockId_ {
SHMEMLOCKID,
BINDINGLOCKID,
BUFMGRLOCKID,
LOCKMGRLOCKID,
SINVALLOCKID,
#ifdef MAIN_MEMORY
MMCACHELOCKID,
#endif /* MAIN_MEMORY */
PROCSTRUCTLOCKID,
OIDGENLOCKID,
FIRSTFREELOCKID
} _LockId_;
#define MAX_SPINS FIRSTFREELOCKID
#endif /* HAS_TEST_AND_SET */
/*
* the following are originally in ipci.h but the prototypes have circular
* dependencies and most files include both ipci.h and ipc.h anyway, hence
* combined.
*
*/
/*
* Note:
* These must not hash to DefaultIPCKey or PrivateIPCKey.
*/
#define SystemPortAddressGetIPCKey(address) \
(28597 * (address) + 17491)
/*
* these keys are originally numbered from 1 to 12 consecutively but not
* all are used. The unused ones are removed. - ay 4/95.
*/
#define IPCKeyGetBufferMemoryKey(key) \
((key == PrivateIPCKey) ? key : 1 + (key))
#define IPCKeyGetSIBufferMemoryBlock(key) \
((key == PrivateIPCKey) ? key : 7 + (key))
#define IPCKeyGetSLockSharedMemoryKey(key) \
((key == PrivateIPCKey) ? key : 10 + (key))
#define IPCKeyGetSpinLockSemaphoreKey(key) \
((key == PrivateIPCKey) ? key : 11 + (key))
#define IPCKeyGetWaitIOSemaphoreKey(key) \
((key == PrivateIPCKey) ? key : 12 + (key))
/* --------------------------
* NOTE: This macro must always give the highest numbered key as every backend
* process forked off by the postmaster will be trying to acquire a semaphore
* with a unique key value starting at key+14 and incrementing up. Each
* backend uses the current key value then increments it by one.
* --------------------------
*/
#define IPCGetProcessSemaphoreInitKey(key) \
((key == PrivateIPCKey) ? key : 14 + (key))
/* ipci.c */
extern IPCKey SystemPortAddressCreateIPCKey(SystemPortAddress address);
extern void CreateSharedMemoryAndSemaphores(IPCKey key);
extern void AttachSharedMemoryAndSemaphores(IPCKey key);
#endif /* IPC_H */

View File

@@ -0,0 +1,20 @@
/*-------------------------------------------------------------------------
*
* item.h--
* POSTGRES disk item definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: item.h,v 1.1 1996/08/28 01:58:06 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef ITEM_H
#define ITEM_H
#include "c.h"
typedef Pointer Item;
#endif /* ITEM_H */

View File

@@ -0,0 +1,75 @@
/*-------------------------------------------------------------------------
*
* itemid.h--
* Standard POSTGRES buffer page item identifier definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: itemid.h,v 1.1 1996/08/28 01:58:08 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef ITEMID_H
#define ITEMID_H
typedef uint16 ItemOffset;
typedef uint16 ItemLength;
typedef bits16 ItemIdFlags;
typedef struct ItemIdData { /* line pointers */
unsigned lp_off:13, /* offset to find tup */
/* can be reduced by 2 if necc. */
lp_flags:6, /* flags on tuple */
lp_len:13; /* length of tuple */
} ItemIdData;
typedef struct ItemIdData *ItemId;
#ifndef LP_USED
#define LP_USED 0x01 /* this line pointer is being used */
#endif
/* ----------------
* support macros
* ----------------
*/
/*
* ItemIdGetLength
*/
#define ItemIdGetLength(itemId) \
((itemId)->lp_len)
/*
* ItemIdGetOffset
*/
#define ItemIdGetOffset(itemId) \
((itemId)->lp_off)
/*
* ItemIdGetFlags
*/
#define ItemIdGetFlags(itemId) \
((itemId)->lp_flags)
/*
* ItemIdIsValid --
* True iff disk item identifier is valid.
*/
#define ItemIdIsValid(itemId) PointerIsValid(itemId)
/*
* ItemIdIsUsed --
* True iff disk item identifier is in use.
*
* Note:
* Assumes disk item identifier is valid.
*/
#define ItemIdIsUsed(itemId) \
(AssertMacro(ItemIdIsValid(itemId)) ? \
(bool) (((itemId)->lp_flags & LP_USED) != 0) : false)
#endif /* ITEMID_H */

View File

@@ -0,0 +1,44 @@
/*-------------------------------------------------------------------------
*
* itempos.h--
* Standard POSTGRES buffer page long item subposition definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: itempos.h,v 1.1 1996/08/28 01:58:09 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef ITEMPOS_H
#define ITEMPOS_H
#include "c.h"
#include "storage/buf.h"
#include "storage/itemid.h"
typedef struct ItemSubpositionData {
Buffer op_db;
ItemId op_lpp;
char *op_cp; /* XXX */
uint32 op_len;
} ItemSubpositionData;
typedef ItemSubpositionData *ItemSubposition;
/*
* PNOBREAK(OBJP, LEN)
* struct objpos *OBJP;
* unsigned LEN;
*/
#define PNOBREAK(OBJP, LEN) ((OBJP)->op_len >= LEN)
/*
* PSKIP(OBJP, LEN)
* struct objpos *OBJP;
* unsigned LEN;
*/
#define PSKIP(OBJP, LEN)\
{ (OBJP)->op_cp += (LEN); (OBJP)->op_len -= (LEN); }
#endif /* ITEMPOS_H */

View File

@@ -0,0 +1,115 @@
/*-------------------------------------------------------------------------
*
* itemptr.h--
* POSTGRES disk item pointer definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: itemptr.h,v 1.1 1996/08/28 01:58:11 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef ITEMPTR_H
#define ITEMPTR_H
#include "c.h"
#include "storage/block.h"
#include "storage/off.h"
#include "storage/itemid.h"
/*
* ItemPointer:
*
* this is a pointer to an item on another disk page in the same file.
* blkid tells us which block, posid tells us which entry in the linp
* (ItemIdData) array we want.
*/
typedef struct ItemPointerData {
BlockIdData ip_blkid;
OffsetNumber ip_posid;
} ItemPointerData;
typedef ItemPointerData *ItemPointer;
/* ----------------
* support macros
* ----------------
*/
/*
* ItemPointerIsValid --
* True iff the disk item pointer is not NULL.
*/
#define ItemPointerIsValid(pointer) \
((bool) (PointerIsValid(pointer) && ((pointer)->ip_posid != 0)))
/*
* ItemPointerGetBlockNumber --
* Returns the block number of a disk item pointer.
*/
#define ItemPointerGetBlockNumber(pointer) \
(AssertMacro(ItemPointerIsValid(pointer)) ? \
BlockIdGetBlockNumber(&(pointer)->ip_blkid) : (BlockNumber) 0)
/*
* ItemPointerGetOffsetNumber --
* Returns the offset number of a disk item pointer.
*/
#define ItemPointerGetOffsetNumber(pointer) \
(AssertMacro(ItemPointerIsValid(pointer)) ? \
(pointer)->ip_posid : \
InvalidOffsetNumber)
/*
* ItemPointerSet --
* Sets a disk item pointer to the specified block and offset.
*/
#define ItemPointerSet(pointer, blockNumber, offNum) \
Assert(PointerIsValid(pointer)); \
BlockIdSet(&((pointer)->ip_blkid), blockNumber); \
(pointer)->ip_posid = offNum
/*
* ItemPointerSetBlockNumber --
* Sets a disk item pointer to the specified block.
*/
#define ItemPointerSetBlockNumber(pointer, blockNumber) \
Assert(PointerIsValid(pointer)); \
BlockIdSet(&((pointer)->ip_blkid), blockNumber)
/*
* ItemPointerSetOffsetNumber --
* Sets a disk item pointer to the specified offset.
*/
#define ItemPointerSetOffsetNumber(pointer, offsetNumber) \
AssertMacro(PointerIsValid(pointer)); \
(pointer)->ip_posid = (offsetNumber)
/*
* ItemPointerCopy --
* Copies the contents of one disk item pointer to another.
*/
#define ItemPointerCopy(fromPointer, toPointer) \
Assert(PointerIsValid(toPointer)); \
Assert(PointerIsValid(fromPointer)); \
*(toPointer) = *(fromPointer)
/*
* ItemPointerSetInvalid --
* Sets a disk item pointer to be invalid.
*/
#define ItemPointerSetInvalid(pointer) \
Assert(PointerIsValid(pointer)); \
BlockIdSet(&((pointer)->ip_blkid), InvalidBlockNumber); \
(pointer)->ip_posid = InvalidOffsetNumber
/* ----------------
* externs
* ----------------
*/
extern bool ItemPointerEquals(ItemPointer pointer1, ItemPointer pointer2);
#endif /* ITEMPTR_H */

View File

@@ -0,0 +1,58 @@
/*-------------------------------------------------------------------------
*
* large_object.h--
* file of info for Postgres large objects. POSTGRES 4.2 supports
* zillions of large objects (internal, external, jaquith, inversion).
* Now we only support inversion.
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: large_object.h,v 1.1 1996/08/28 01:58:12 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef LARGE_OBJECT_H
#define LARGE_OBJECT_H
#include "c.h"
#include "utils/rel.h"
#include "access/relscan.h"
/*
* This structure will eventually have lots more stuff associated with it.
*/
typedef struct LargeObjectDesc
{
Relation heap_r; /* heap relation */
Relation index_r; /* index relation on seqno attribute */
IndexScanDesc iscan; /* index scan we're using */
TupleDesc hdesc; /* heap relation tuple desc */
TupleDesc idesc; /* index relation tuple desc */
uint32 lowbyte; /* low byte on the current page */
uint32 highbyte; /* high byte on the current page */
uint32 offset; /* current seek pointer */
ItemPointerData htid; /* tid of current heap tuple */
#define IFS_RDLOCK (1 << 0)
#define IFS_WRLOCK (1 << 1)
#define IFS_ATEOF (1 << 2)
u_long flags; /* locking info, etc */
} LargeObjectDesc;
/*
* Function definitions...
*/
/* inversion stuff in inv_api.c */
extern LargeObjectDesc *inv_create(int flags);
extern LargeObjectDesc *inv_open(Oid lobjId, int flags);
extern void inv_close(LargeObjectDesc *obj_desc);
extern int inv_destroy(Oid lobjId);
extern int inv_stat(LargeObjectDesc *obj_desc, struct pgstat *stbuf);
extern int inv_seek(LargeObjectDesc *obj_desc, int offset, int whence);
extern int inv_tell(LargeObjectDesc *obj_desc);
extern int inv_read(LargeObjectDesc *obj_desc, char *buf, int nbytes);
extern int inv_write(LargeObjectDesc *obj_desc, char *buf, int nbytes);
#endif /* LARGE_OBJECT_H */

View File

@@ -0,0 +1,84 @@
/*-------------------------------------------------------------------------
*
* lmgr.h--
* POSTGRES lock manager definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: lmgr.h,v 1.1 1996/08/28 01:58:13 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef LMGR_H
#define LMGR_H
#include "postgres.h"
#include "storage/itemptr.h"
#include "storage/lock.h"
#include "utils/rel.h"
/*
* This was moved from pladt.h for the new lock manager. Want to obsolete
* all of the old code.
*/
typedef struct LRelId {
Oid relId; /* a relation identifier */
Oid dbId; /* a database identifier */
} LRelId;
typedef struct LockInfoData {
bool initialized;
LRelId lRelId;
TransactionId transactionIdData;
uint16 flags;
} LockInfoData;
typedef LockInfoData *LockInfo;
#define LockInfoIsValid(linfo) \
((PointerIsValid(linfo)) && ((LockInfo) linfo)->initialized)
extern LRelId RelationGetLRelId(Relation relation);
extern Oid LRelIdGetDatabaseId(LRelId lRelId);
extern Oid LRelIdGetRelationId(LRelId lRelId);
extern bool DatabaseIdIsMyDatabaseId(Oid databaseId);
extern bool LRelIdContainsMyDatabaseId(LRelId lRelId);
extern void RelationInitLockInfo(Relation relation);
extern void RelationDiscardLockInfo(Relation relation);
extern void RelationSetLockForDescriptorOpen(Relation relation);
extern void RelationSetLockForRead(Relation relation);
extern void RelationUnsetLockForRead(Relation relation);
extern void RelationSetLockForWrite(Relation relation);
extern void RelationUnsetLockForWrite(Relation relation);
extern void RelationSetLockForTupleRead(Relation relation,
ItemPointer itemPointer);
/* used in vaccum.c */
extern void RelationSetLockForWritePage(Relation relation,
ItemPointer itemPointer);
/* used in nbtpage.c, hashpage.c */
extern void RelationSetSingleWLockPage(Relation relation,
ItemPointer itemPointer);
extern void RelationUnsetSingleWLockPage(Relation relation,
ItemPointer itemPointer);
extern void RelationSetSingleRLockPage(Relation relation,
ItemPointer itemPointer);
extern void RelationUnsetSingleRLockPage(Relation relation,
ItemPointer itemPointer);
extern void RelationSetRIntentLock(Relation relation);
extern void RelationUnsetRIntentLock(Relation relation);
extern void RelationSetWIntentLock(Relation relation);
extern void RelationUnsetWIntentLock(Relation relation);
extern void RelationSetLockForExtend(Relation relation);
extern void RelationUnsetLockForExtend(Relation relation);
extern void LRelIdAssign(LRelId *lRelId, Oid dbId, Oid relId);
/* single.c */
extern bool SingleLockReln(LockInfo linfo, LOCKT lockt, int action);
extern bool SingleLockPage(LockInfo linfo, ItemPointer tidPtr,
LOCKT lockt, int action);
#endif /* LMGR_H */

218
src/include/storage/lock.h Normal file
View File

@@ -0,0 +1,218 @@
/*-------------------------------------------------------------------------
*
* lock.h--
*
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: lock.h,v 1.1 1996/08/28 01:58:15 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef LOCK_H_
#define LOCK_H_
#include "postgres.h"
#include "storage/itemptr.h"
#include "storage/shmem.h"
#include "storage/spin.h"
#include "storage/backendid.h"
#include "utils/hsearch.h"
extern SPINLOCK LockMgrLock;
typedef int MASK;
#define INIT_TABLE_SIZE 100
#define MAX_TABLE_SIZE 1000
/* ----------------------
* The following defines are used to estimate how much shared
* memory the lock manager is going to require.
*
* NBACKENDS - The number of concurrently running backends
* NLOCKS_PER_XACT - The number of unique locks acquired in a transaction
* NLOCKENTS - The maximum number of lock entries in the lock table.
* ----------------------
*/
#define NBACKENDS 50
#define NLOCKS_PER_XACT 40
#define NLOCKENTS NLOCKS_PER_XACT*NBACKENDS
typedef int LOCK_TYPE;
typedef int LOCKT;
typedef int LockTableId;
/* MAX_LOCKTYPES cannot be larger than the bits in MASK */
#define MAX_LOCKTYPES 6
/*
* MAX_TABLES corresponds to the number of spin locks allocated in
* CreateSpinLocks() or the number of shared memory locations allocated
* for lock table spin locks in the case of machines with TAS instructions.
*/
#define MAX_TABLES 2
#define INVALID_TABLEID 0
/*typedef struct LOCK LOCK; */
typedef struct ltag {
Oid relId;
Oid dbId;
ItemPointerData tupleId;
} LOCKTAG;
#define TAGSIZE (sizeof(LOCKTAG))
/* This is the control structure for a lock table. It
* lives in shared memory:
*
* tableID -- the handle used by the lock table's clients to
* refer to the table.
*
* nLockTypes -- number of lock types (READ,WRITE,etc) that
* are defined on this lock table
*
* conflictTab -- this is an array of bitmasks showing lock
* type conflicts. conflictTab[i] is a mask with the j-th bit
* turned on if lock types i and j conflict.
*
* prio -- each locktype has a priority, so, for example, waiting
* writers can be given priority over readers (to avoid
* starvation).
*
* masterlock -- synchronizes access to the table
*
*/
typedef struct lockctl {
LockTableId tableId;
int nLockTypes;
int conflictTab[MAX_LOCKTYPES];
int prio[MAX_LOCKTYPES];
SPINLOCK masterLock;
} LOCKCTL;
/*
* lockHash -- hash table on lock Ids,
* xidHash -- hash on xid and lockId in case
* multiple processes are holding the lock
* ctl - control structure described above.
*/
typedef struct ltable {
HTAB *lockHash;
HTAB *xidHash;
LOCKCTL *ctl;
} LOCKTAB;
/* -----------------------
* A transaction never conflicts with its own locks. Hence, if
* multiple transactions hold non-conflicting locks on the same
* data, private per-transaction information must be stored in the
* XID table. The tag is XID + shared memory lock address so that
* all locks can use the same XID table. The private information
* we store is the number of locks of each type (holders) and the
* total number of locks (nHolding) held by the transaction.
*
* NOTE: --
* There were some problems with the fact that currently TransactionIdData
* is a 5 byte entity and compilers long word aligning of structure fields.
* If the 3 byte padding is put in front of the actual xid data then the
* hash function (which uses XID_TAGSIZE when deciding how many bytes of a
* struct to look at for the key) might only see the last two bytes of the xid.
*
* Clearly this is not good since its likely that these bytes will be the
* same for many transactions and hence they will share the same entry in
* hash table causing the entry to be corrupted. For this long-winded
* reason I have put the tag in a struct of its own to ensure that the
* XID_TAGSIZE is computed correctly. It used to be sizeof (SHMEM_OFFSET) +
* sizeof(TransactionIdData) which != sizeof(XIDTAG).
*
* Finally since the hash function will now look at all 12 bytes of the tag
* the padding bytes MUST be zero'd before use in hash_search() as they
* will have random values otherwise. Jeff 22 July 1991.
* -----------------------
*/
typedef struct XIDTAG {
SHMEM_OFFSET lock;
int pid;
TransactionId xid;
} XIDTAG;
typedef struct XIDLookupEnt {
/* tag */
XIDTAG tag;
/* data */
int holders[MAX_LOCKTYPES];
int nHolding;
SHM_QUEUE queue;
} XIDLookupEnt;
#define XID_TAGSIZE (sizeof(XIDTAG))
/* originally in procq.h */
typedef struct procQueue {
SHM_QUEUE links;
int size;
} PROC_QUEUE;
/*
* lock information:
*
* tag -- uniquely identifies the object being locked
* mask -- union of the conflict masks of all lock types
* currently held on this object.
* waitProcs -- queue of processes waiting for this lock
* holders -- count of each lock type currently held on the
* lock.
* nHolding -- total locks of all types.
*/
typedef struct Lock {
/* hash key */
LOCKTAG tag;
/* data */
int mask;
PROC_QUEUE waitProcs;
int holders[MAX_LOCKTYPES];
int nHolding;
int activeHolders[MAX_LOCKTYPES];
int nActive;
} LOCK;
#define LockGetLock_nHolders(l) l->nHolders
#define LockDecrWaitHolders(lock, lockt) \
lock->nHolding--; \
lock->holders[lockt]--
#define LockLockTable() SpinAcquire(LockMgrLock);
#define UnlockLockTable() SpinRelease(LockMgrLock);
extern SPINLOCK LockMgrLock;
/*
* function prototypes
*/
extern void InitLocks(void);
extern void LockDisable(int status);
extern LockTableId LockTabInit(char *tabName, MASK *conflictsP, int *prioP,
int ntypes);
extern LockTableId LockTabRename(LockTableId tableId);
extern bool LockAcquire(LockTableId tableId, LOCKTAG *lockName, LOCKT lockt);
extern int LockResolveConflicts(LOCKTAB *ltable, LOCK *lock, LOCKT lockt,
TransactionId xid);
extern int WaitOnLock(LOCKTAB *ltable, LockTableId tableId, LOCK *lock,
LOCKT lockt);
extern bool LockRelease(LockTableId tableId, LOCKTAG *lockName, LOCKT lockt);
extern void GrantLock(LOCK *lock, LOCKT lockt);
extern bool LockReleaseAll(LockTableId tableId, SHM_QUEUE *lockQueue);
extern int LockShmemSize(void);
extern bool LockingDisabled(void);
#endif /* LOCK_H */

View File

@@ -0,0 +1,64 @@
/*-------------------------------------------------------------------------
*
* multilev.h--
* multi level lock table consts/defs for single.c and multi.c and their
* clients
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: multilev.h,v 1.1 1996/08/28 01:58:17 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef MULTILEV_H
#define MULTILEV_H
#include "storage/lock.h"
#include "storage/lmgr.h"
#define READ_LOCK 2
#define WRITE_LOCK 1
/* any time a small granularity READ/WRITE lock is set.
* Higher granularity READ_INTENT/WRITE_INTENT locks must
* also be set. A read intent lock is has value READ+INTENT.
* in this implementation.
*/
#define NO_LOCK 0
#define INTENT 2
#define READ_INTENT (READ_LOCK+INTENT)
#define WRITE_INTENT (WRITE_LOCK+INTENT)
#define EXTEND_LOCK 5
#define SHORT_TERM 1
#define LONG_TERM 2
#define UNLOCK 0
#define N_LEVELS 3
#define RELN_LEVEL 0
#define PAGE_LEVEL 1
#define TUPLE_LEVEL 2
typedef int LOCK_LEVEL;
/* multi.c */
extern LockTableId MultiTableId;
extern LockTableId ShortTermTableId;
/*
* function prototypes
*/
extern LockTableId InitMultiLevelLockm(void);
extern bool MultiLockReln(LockInfo linfo, LOCKT lockt);
extern bool MultiLockTuple(LockInfo linfo, ItemPointer tidPtr, LOCKT lockt);
extern bool MultiLockPage(LockInfo linfo, ItemPointer tidPtr, LOCKT lockt);
extern bool MultiAcquire(LockTableId tableId, LOCKTAG *tag, LOCKT lockt,
LOCK_LEVEL level);
extern bool MultiReleasePage(LockInfo linfo, ItemPointer tidPtr, LOCKT lockt);
extern bool MultiReleaseReln(LockInfo linfo, LOCKT lockt);
extern bool MultiRelease(LockTableId tableId, LOCKTAG *tag, LOCKT lockt,
LOCK_LEVEL level);
#endif /* MULTILEV_H */

60
src/include/storage/off.h Normal file
View File

@@ -0,0 +1,60 @@
/*-------------------------------------------------------------------------
*
* off.h--
* POSTGRES disk "offset" definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: off.h,v 1.1 1996/08/28 01:58:18 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef OFF_H
#define OFF_H
#include "c.h"
#include "machine.h" /* for BLCKSZ */
#include "storage/itemid.h"
/*
* OffsetNumber:
*
* this is a 1-based index into the linp (ItemIdData) array in the
* header of each disk page.
*/
typedef uint16 OffsetNumber;
#define InvalidOffsetNumber ((OffsetNumber) 0)
#define FirstOffsetNumber ((OffsetNumber) 1)
#define MaxOffsetNumber ((OffsetNumber) (BLCKSZ / sizeof(ItemIdData)))
#define OffsetNumberMask (0xffff) /* valid uint16 bits */
/* ----------------
* support macros
* ----------------
*/
/*
* OffsetNumberIsValid --
* True iff the offset number is valid.
*/
#define OffsetNumberIsValid(offsetNumber) \
((bool) ((offsetNumber != InvalidOffsetNumber) && \
(offsetNumber <= MaxOffsetNumber)))
/*
* OffsetNumberNext --
* OffsetNumberPrev --
* Increments/decrements the argument. These macros look pointless
* but they help us disambiguate the different manipulations on
* OffsetNumbers (e.g., sometimes we substract one from an
* OffsetNumber to move back, and sometimes we do so to form a
* real C array index).
*/
#define OffsetNumberNext(offsetNumber) \
((OffsetNumber) (1 + (offsetNumber)))
#define OffsetNumberPrev(offsetNumber) \
((OffsetNumber) (-1 + (offsetNumber)))
#endif /* OFF_H */

View File

@@ -0,0 +1,26 @@
/*-------------------------------------------------------------------------
*
* page.h--
* POSTGRES buffer page abstraction definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: page.h,v 1.1 1996/08/28 01:58:20 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef PAGE_H
#define PAGE_H
#include "c.h"
typedef Pointer Page;
/*
* PageIsValid --
* True iff page is valid.
*/
#define PageIsValid(page) PointerIsValid(page)
#endif /* PAGE_H */

View File

@@ -0,0 +1,33 @@
/*-------------------------------------------------------------------------
*
* pagenum.h--
* POSTGRES page number definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: pagenum.h,v 1.1 1996/08/28 01:58:21 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef PAGENUM_H
#define PAGENUM_H
#include "c.h"
#include "storage/page.h"
typedef uint16 PageNumber;
typedef uint32 LogicalPageNumber;
#define InvalidLogicalPageNumber 0
/*
* LogicalPageNumberIsValid --
* True iff the logical page number is valid.
*/
#define LogicalPageNumberIsValid(pageNumber) \
((bool)((pageNumber) != InvalidLogicalPageNumber))
#endif /* PAGENUM_H */

64
src/include/storage/pos.h Normal file
View File

@@ -0,0 +1,64 @@
/*-------------------------------------------------------------------------
*
* pos.h--
* POSTGRES "position" definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: pos.h,v 1.1 1996/08/28 01:58:22 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef POS_H
#define POS_H
#include "c.h"
/*
* a 'position' used to be <pagenumber, offset> in postgres. this has
* been changed to just <offset> as the notion of having multiple pages
* within a block has been removed.
*
* the 'offset' abstraction is somewhat confusing. it is NOT a byte
* offset within the page; instead, it is an offset into the line
* pointer array contained on every page that store (heap or index)
* tuples.
*/
typedef bits16 PositionIdData;
typedef PositionIdData *PositionId;
/* ----------------
* support macros
* ----------------
*/
/*
* PositionIdIsValid --
* True iff the position identifier is valid.
*/
#define PositionIdIsValid(positionId) \
PointerIsValid(positionId)
/*
* PositionIdSetInvalid --
* Make an invalid position.
*/
#define PositionIdSetInvalid(positionId) \
*(positionId) = (bits16) 0
/*
* PositionIdSet --
* Sets a position identifier to the specified value.
*/
#define PositionIdSet(positionId, offsetNumber) \
*(positionId) = (offsetNumber)
/*
* PositionIdGetOffsetNumber --
* Retrieve the offset number from a position identifier.
*/
#define PositionIdGetOffsetNumber(positionId) \
((OffsetNumber) *(positionId))
#endif /* POS_H */

123
src/include/storage/proc.h Normal file
View File

@@ -0,0 +1,123 @@
/*-------------------------------------------------------------------------
*
* proc.h--
*
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: proc.h,v 1.1 1996/08/28 01:58:24 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef _PROC_H_
#define _PROC_H_
#include "storage/ipc.h"
#include "storage/lock.h"
#ifndef WIN32
#include <sys/sem.h>
#else
/* This is because WIN32 already defines PROC */
#define PROC PGL_PROC
#endif /* WIN32 */
#include "storage/shmem.h"
typedef struct {
int sleeplock;
int semNum;
IpcSemaphoreId semId;
IpcSemaphoreKey semKey;
} SEMA;
/*
* Each backend has:
*/
typedef struct proc {
/* proc->links MUST BE THE FIRST ELEMENT OF STRUCT (see ProcWakeup()) */
SHM_QUEUE links; /* proc can be waiting for one event(lock) */
SEMA sem; /* ONE semaphore to sleep on */
int errType; /* error code tells why we woke up */
int procId; /* unique number for this structure
* NOT unique per backend, these things
* are reused after the backend dies.
*/
int critSects; /* If critSects > 0, we are in sensitive
* routines that cannot be recovered when
* the process fails.
*/
int prio; /* priority for sleep queue */
TransactionId xid; /* transaction currently being executed
* by this proc
*/
LOCK * waitLock; /* Lock we're sleeping on */
int token; /* info for proc wakeup routines */
int pid; /* This procs process id */
short sLocks[MAX_SPINS]; /* Spin lock stats */
SHM_QUEUE lockQueue; /* locks associated with current transaction */
} PROC;
/*
* MAX_PROC_SEMS is the maximum number of per-process semaphores (those used
* by the lock mgr) we can keep track of. PROC_NSEMS_PER_SET is the number
* of semaphores in each (sys-V) semaphore set allocated. (Be careful not
* to set it to greater 32. Otherwise, the bitmap will overflow.)
*/
#define MAX_PROC_SEMS 128
#define PROC_NSEMS_PER_SET 16
typedef struct procglobal {
SHMEM_OFFSET freeProcs;
int numProcs;
IPCKey currKey;
int32 freeSemMap[MAX_PROC_SEMS/PROC_NSEMS_PER_SET];
} PROC_HDR;
extern PROC *MyProc;
#define PROC_INCR_SLOCK(lock) if (MyProc) (MyProc->sLocks[(lock)])++
#define PROC_DECR_SLOCK(lock) if (MyProc) (MyProc->sLocks[(lock)])--
/*
* flags explaining why process woke up
*/
#define NO_ERROR 0
#define ERR_TIMEOUT 1
#define ERR_BUFFER_IO 2
#define MAX_PRIO 50
#define MIN_PRIO (-1)
extern SPINLOCK ProcStructLock;
/*
* Function Prototypes
*/
extern void InitProcess(IPCKey key);
extern void ProcReleaseLocks(void);
extern bool ProcRemove(int pid);
/* extern bool ProcKill(int exitStatus, int pid); */
/* make static in storage/lmgr/proc.c -- jolly */
extern PROC_QUEUE *ProcQueueAlloc(char *name);
extern void ProcQueueInit(PROC_QUEUE *queue);
extern int ProcSleep(PROC_QUEUE *queue, SPINLOCK spinlock, int token,
int prio, LOCK *lock);
extern PROC *ProcWakeup(PROC *proc, int errType);
extern int ProcGetId(void);
extern int ProcLockWakeup(PROC_QUEUE *queue, char * ltable, char * lock);
extern void ProcAddLock(SHM_QUEUE *elem);
extern void HandleDeadLock(int sig);
extern void ProcReleaseSpins(PROC *proc);
extern void ProcFreeAllSemaphores(void);
#endif /* PROC_H */

104
src/include/storage/shmem.h Normal file
View File

@@ -0,0 +1,104 @@
/*-------------------------------------------------------------------------
*
* shmem.h--
* shared memory management structures
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: shmem.h,v 1.1 1996/08/28 01:58:26 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef SHMEM_H
#define SHMEM_H
#include "storage/spin.h" /* for SPINLOCK */
#include "utils/hsearch.h" /* for HTAB */
/* The shared memory region can start at a different address
* in every process. Shared memory "pointers" are actually
* offsets relative to the start of the shared memory region(s).
*/
typedef unsigned long SHMEM_OFFSET;
#define INVALID_OFFSET (-1)
#define BAD_LOCATION (-1)
/* start of the lowest shared memory region. For now, assume that
* there is only one shared memory region
*/
extern SHMEM_OFFSET ShmemBase;
/* coerce an offset into a pointer in this process's address space */
#define MAKE_PTR(xx_offs)\
(ShmemBase+((unsigned long)(xx_offs)))
/* coerce a pointer into a shmem offset */
#define MAKE_OFFSET(xx_ptr)\
(SHMEM_OFFSET) (((unsigned long)(xx_ptr))-ShmemBase)
#define SHM_PTR_VALID(xx_ptr)\
(((unsigned long)xx_ptr) > ShmemBase)
/* cannot have an offset to ShmemFreeStart (offset 0) */
#define SHM_OFFSET_VALID(xx_offs)\
((xx_offs != 0) && (xx_offs != INVALID_OFFSET))
extern SPINLOCK ShmemLock;
extern SPINLOCK BindingLock;
/* shmemqueue.c */
typedef struct SHM_QUEUE {
SHMEM_OFFSET prev;
SHMEM_OFFSET next;
} SHM_QUEUE;
/* shmem.c */
extern void ShmemBindingTabReset();
extern void ShmemCreate(unsigned int key, unsigned int size);
extern int InitShmem(unsigned int key, unsigned int size);
extern long *ShmemAlloc(unsigned long size);
extern int ShmemIsValid(unsigned long addr);
extern HTAB *ShmemInitHash(char *name, long init_size, long max_size,
HASHCTL *infoP, int hash_flags);
extern bool ShmemPIDLookup(int pid, SHMEM_OFFSET* locationPtr);
extern SHMEM_OFFSET ShmemPIDDestroy(int pid);
extern long *ShmemInitStruct(char *name, unsigned long size,
bool *foundPtr);
typedef int TableID;
/* size constants for the binding table */
/* max size of data structure string name */
#define BTABLE_KEYSIZE (50)
/* data in binding table hash bucket */
#define BTABLE_DATASIZE (sizeof(BindingEnt) - BTABLE_KEYSIZE)
/* maximum size of the binding table */
#define BTABLE_SIZE (100)
/* this is a hash bucket in the binding table */
typedef struct {
char key[BTABLE_KEYSIZE]; /* string name */
unsigned long location; /* location in shared mem */
unsigned long size; /* numbytes allocated for the
* structure
*/
} BindingEnt;
/*
* prototypes for functions in shmqueue.c
*/
extern void SHMQueueInit(SHM_QUEUE *queue);
extern bool SHMQueueIsDetached(SHM_QUEUE *queue);
extern void SHMQueueElemInit(SHM_QUEUE *queue);
extern void SHMQueueDelete(SHM_QUEUE *queue);
extern void SHMQueueInsertHD(SHM_QUEUE *queue, SHM_QUEUE *elem);
extern void SHMQueueInsertTL(SHM_QUEUE *queue, SHM_QUEUE *elem);
extern void SHMQueueFirst(SHM_QUEUE *queue, Pointer *nextPtrPtr,
SHM_QUEUE *nextQueue);
extern bool SHMQueueEmpty(SHM_QUEUE *queue);
#endif /* SHMEM_H */

View File

@@ -0,0 +1,33 @@
/*-------------------------------------------------------------------------
*
* sinval.h--
* POSTGRES shared cache invalidation communication definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: sinval.h,v 1.1 1996/08/28 01:58:28 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef SINVAL_H
#define SINVAL_H
#include "c.h"
#include "storage/spin.h"
#include "storage/ipc.h"
#include "storage/itemptr.h"
#include "storage/backendid.h"
extern SPINLOCK SInvalLock;
extern void CreateSharedInvalidationState(IPCKey key);
extern void AttachSharedInvalidationState(IPCKey key);
extern void InitSharedInvalidationState();
extern void RegisterSharedInvalid(int cacheId, Index hashIndex,
ItemPointer pointer);
extern void InvalidateSharedInvalid(void (*invalFunction)(),
void (*resetFunction)());
#endif /* SINVAL_H */

View File

@@ -0,0 +1,126 @@
/*-------------------------------------------------------------------------
*
* sinvaladt.h--
* POSTGRES shared cache invalidation segment definitions.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: sinvaladt.h,v 1.1 1996/08/28 01:58:29 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef SINVALADT_H
#define SINVALADT_H
#include "postgres.h" /* XXX */
#include "storage/ipc.h"
#include "storage/itemptr.h"
#include "storage/sinval.h"
/*
* The structure of the shared cache invaidation segment
*
*/
/*
A------------- Header info --------------
criticalSectionSemaphoreId
generalSemaphoreId
startEntrySection (offset a)
endEntrySection (offset a + b)
startFreeSpace (offset relative to B)
startEntryChain (offset relatiev to B)
endEntryChain (offset relative to B)
numEntries
maxNumEntries
procState[MaxBackendId] --> limit
resetState (bool)
a tag (POSTID)
B------------- Start entry section -------
SISegEntry --> entryData --> ... (see SharedInvalidData!)
isfree (bool)
next (offset to next entry in chain )
b .... (dynamically growing down)
C----------------End shared segment -------
*/
/* Parameters (configurable) *******************************************/
#define MaxBackendId 32 /* maximum number of backends */
#define MAXNUMMESSAGES 1000 /* maximum number of messages in seg*/
#define InvalidOffset 1000000000 /* a invalid offset (End of chain) */
typedef struct ProcState {
int limit; /* the number of read messages */
bool resetState; /* true, if backend has to reset its state */
int tag; /* special tag, recieved from the postmaster */
} ProcState;
typedef struct SISeg {
IpcSemaphoreId criticalSectionSemaphoreId; /* semaphore id */
IpcSemaphoreId generalSemaphoreId; /* semaphore id */
Offset startEntrySection; /* (offset a) */
Offset endEntrySection; /* (offset a + b) */
Offset startFreeSpace; /* (offset relative to B) */
Offset startEntryChain; /* (offset relative to B) */
Offset endEntryChain; /* (offset relative to B) */
int numEntries;
int maxNumEntries;
ProcState procState[MaxBackendId]; /* reflects the invalidation state */
/* here starts the entry section, controlled by offsets */
} SISeg;
#define SizeSISeg sizeof(SISeg)
typedef struct SharedInvalidData {
int cacheId; /* XXX */
Index hashIndex;
ItemPointerData pointerData;
} SharedInvalidData;
typedef SharedInvalidData *SharedInvalid;
typedef struct SISegEntry {
SharedInvalidData entryData; /* the message data */
bool isfree; /* entry free? */
Offset next; /* offset to next entry*/
} SISegEntry;
#define SizeOfOneSISegEntry sizeof(SISegEntry)
typedef struct SISegOffsets {
Offset startSegment; /* always 0 (for now) */
Offset offsetToFirstEntry; /* A + a = B */
Offset offsetToEndOfSegemnt; /* A + a + b */
} SISegOffsets;
/****************************************************************************/
/* synchronization of the shared buffer access */
/* access to the buffer is synchronized by the lock manager !! */
/****************************************************************************/
#define SI_LockStartValue 255
#define SI_SharedLock (-1)
#define SI_ExclusiveLock (-255)
extern SISeg *shmInvalBuffer;
/*
* prototypes for functions in sinvaladt.c
*/
extern int SIBackendInit(SISeg *segInOutP);
extern int SISegmentInit(bool killExistingSegment, IPCKey key);
extern bool SISetDataEntry(SISeg *segP, SharedInvalidData *data);
extern void SISetProcStateInvalid(SISeg *segP);
extern bool SIDelDataEntry(SISeg *segP);
extern void SIReadEntryData(SISeg *segP, int backendId,
void (*invalFunction)(), void (*resetFunction)());
extern void SIDelExpiredDataEntries(SISeg *segP);
#endif /* SINVALADT_H */

View File

@@ -0,0 +1,84 @@
/*-------------------------------------------------------------------------
*
* smgr.h--
* storage manager switch public interface declarations.
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: smgr.h,v 1.1 1996/08/28 01:58:32 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef SMGR_H
#define SMGR_H
#include "utils/rel.h"
#include "storage/spin.h" /* for SPINLOCK */
#define SM_FAIL 0
#define SM_SUCCESS 1
#define DEFAULT_SMGR 0
extern int smgrinit(void);
extern void smgrshutdown(int dummy);
extern int smgrcreate(int16 which, Relation reln);
extern int smgrunlink(int16 which, Relation reln);
extern int smgrextend(int16 which, Relation reln, char *buffer);
extern int smgropen(int16 which, Relation reln);
extern int smgrclose(int16 which, Relation reln);
extern int smgrread(int16 which, Relation reln, BlockNumber blocknum,
char *buffer);
extern int smgrwrite(int16 which, Relation reln, BlockNumber blocknum,
char *buffer);
extern int smgrflush(int16 which, Relation reln, BlockNumber blocknum,
char *buffer);
extern int smgrblindwrt(int16 which, char *dbname, char *relname, Oid dbid,
Oid relid, BlockNumber blkno, char *buffer);
extern int smgrnblocks(int16 which, Relation reln);
extern int smgrcommit(void);
extern int smgrabort(void);
extern bool smgriswo(int16 smgrno);
/* internals: move me elsewhere -- ay 7/94 */
/* in md.c */
extern int mdinit(void);
extern int mdcreate(Relation reln);
extern int mdunlink(Relation reln);
extern int mdextend(Relation reln, char *buffer);
extern int mdopen(Relation reln);
extern int mdclose(Relation reln);
extern int mdread(Relation reln, BlockNumber blocknum, char *buffer);
extern int mdwrite(Relation reln, BlockNumber blocknum, char *buffer);
extern int mdflush(Relation reln, BlockNumber blocknum, char *buffer);
extern int mdblindwrt(char *dbstr, char *relstr, Oid dbid, Oid relid,
BlockNumber blkno, char *buffer);
extern int mdnblocks(Relation reln);
extern int mdcommit(void);
extern int mdabort(void);
/* mm.c */
extern SPINLOCK MMCacheLock;
extern int mminit(void);
extern int mmshutdown(void);
extern int mmcreate(Relation reln);
extern int mmunlink(Relation reln);
extern int mmextend(Relation reln, char *buffer);
extern int mmopen(Relation reln);
extern int mmclose(Relation reln);
extern int mmread(Relation reln, BlockNumber blocknum, char *buffer);
extern int mmwrite(Relation reln, BlockNumber blocknum, char *buffer);
extern int mmflush(Relation reln, BlockNumber blocknum, char *buffer);
extern int mmblindwrt(char *dbstr, char *relstr, Oid dbid, Oid relid,
BlockNumber blkno, char *buffer);
extern int mmnblocks(Relation reln);
extern int mmcommit(void);
extern int mmabort(void);
extern int MMShmemSize(void);
#endif /* SMGR_H */

View File

@@ -0,0 +1,38 @@
/*-------------------------------------------------------------------------
*
* spin.h--
* synchronization routines
*
*
* Copyright (c) 1994, Regents of the University of California
*
* $Id: spin.h,v 1.1 1996/08/28 01:58:33 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef SPIN_H
#define SPIN_H
#include "ipc.h"
/*
* two implementations of spin locks
*
* sequent, sparc, sun3: real spin locks. uses a TAS instruction; see
* src/storage/ipc/s_lock.c for details.
*
* default: fake spin locks using semaphores. see spin.c
*
*/
typedef int SPINLOCK;
extern bool CreateSpinlocks(IPCKey key);
extern bool AttachSpinLocks(IPCKey key);
extern bool InitSpinLocks(int init, IPCKey key);
extern void SpinAcquire(SPINLOCK lock);
extern void SpinRelease(SPINLOCK lock);
extern bool SpinIsLocked(SPINLOCK lock);
#endif /* SPIN_H */