14#ifndef SPGIST_PRIVATE_H
15#define SPGIST_PRIVATE_H
19#include "catalog/pg_am_d.h"
32#define SpGistGetFillFactor(relation) \
33 (AssertMacro(relation->rd_rel->relkind == RELKIND_INDEX && \
34 relation->rd_rel->relam == SPGIST_AM_OID), \
35 (relation)->rd_options ? \
36 ((SpGistOptions *) (relation)->rd_options)->fillfactor : \
37 SPGIST_DEFAULT_FILLFACTOR)
38#define SpGistGetTargetPageFreeSpace(relation) \
39 (BLCKSZ * (100 - SpGistGetFillFactor(relation)) / 100)
44#define spgFirstIncludeColumn 1
47#define SPGIST_METAPAGE_BLKNO (0)
48#define SPGIST_ROOT_BLKNO (1)
49#define SPGIST_NULL_BLKNO (2)
50#define SPGIST_LAST_FIXED_BLKNO SPGIST_NULL_BLKNO
52#define SpGistBlockIsRoot(blkno) \
53 ((blkno) == SPGIST_ROOT_BLKNO || (blkno) == SPGIST_NULL_BLKNO)
54#define SpGistBlockIsFixed(blkno) \
55 ((BlockNumber) (blkno) <= (BlockNumber) SPGIST_LAST_FIXED_BLKNO)
72#define SPGIST_META (1<<0)
73#define SPGIST_DELETED (1<<1)
75#define SPGIST_LEAF (1<<2)
76#define SPGIST_NULLS (1<<3)
78#define SpGistPageGetOpaque(page) ((SpGistPageOpaque) PageGetSpecialPointer(page))
79#define SpGistPageIsMeta(page) (SpGistPageGetOpaque(page)->flags & SPGIST_META)
80#define SpGistPageIsDeleted(page) (SpGistPageGetOpaque(page)->flags & SPGIST_DELETED)
81#define SpGistPageIsLeaf(page) (SpGistPageGetOpaque(page)->flags & SPGIST_LEAF)
82#define SpGistPageStoresNulls(page) (SpGistPageGetOpaque(page)->flags & SPGIST_NULLS)
92#define SPGIST_PAGE_ID 0xFF82
106#define SPGIST_CACHED_PAGES 8
122#define SPGIST_MAGIC_NUMBER (0xBA0BABEE)
124#define SpGistPageGetMeta(p) \
125 ((SpGistMetaPageData *) PageGetContents(p))
183#define SizeOfSpGistSearchItem(n_distances) \
184 (offsetof(SpGistSearchItem, distances) + sizeof(double) * (n_distances))
273#define SPGIST_REDIRECT 1
275#define SPGIST_PLACEHOLDER 3
309#define SGITMAXNNODES 0x1FFF
310#define SGITMAXPREFIXSIZE 0xFFFF
311#define SGITMAXSIZE 0xFFFF
313#define SGITHDRSZ MAXALIGN(sizeof(SpGistInnerTupleData))
314#define _SGITDATA(x) (((char *) (x)) + SGITHDRSZ)
315#define SGITDATAPTR(x) ((x)->prefixSize ? _SGITDATA(x) : NULL)
316#define SGITDATUM(x, s) ((x)->prefixSize ? \
317 ((s)->attPrefixType.attbyval ? \
318 *(Datum *) _SGITDATA(x) : \
319 PointerGetDatum(_SGITDATA(x))) \
321#define SGITNODEPTR(x) ((SpGistNodeTuple) (_SGITDATA(x) + (x)->prefixSize))
324#define SGITITERATE(x, i, nt) \
325 for ((i) = 0, (nt) = SGITNODEPTR(x); \
327 (i)++, (nt) = (SpGistNodeTuple) (((char *) (nt)) + IndexTupleSize(nt)))
342#define SGNTHDRSZ MAXALIGN(sizeof(SpGistNodeTupleData))
343#define SGNTDATAPTR(x) (((char *) (x)) + SGNTHDRSZ)
344#define SGNTDATUM(x, s) ((s)->attLabelType.attbyval ? \
345 *(Datum *) SGNTDATAPTR(x) : \
346 PointerGetDatum(SGNTDATAPTR(x)))
397#define SGLT_GET_NEXTOFFSET(spgLeafTuple) \
398 ((spgLeafTuple)->t_info & 0x3FFF)
399#define SGLT_GET_HASNULLMASK(spgLeafTuple) \
400 (((spgLeafTuple)->t_info & 0x8000) ? true : false)
401#define SGLT_SET_NEXTOFFSET(spgLeafTuple, offsetNumber) \
402 ((spgLeafTuple)->t_info = \
403 ((spgLeafTuple)->t_info & 0xC000) | ((offsetNumber) & 0x3FFF))
404#define SGLT_SET_HASNULLMASK(spgLeafTuple, hasnulls) \
405 ((spgLeafTuple)->t_info = \
406 ((spgLeafTuple)->t_info & 0x7FFF) | ((hasnulls) ? 0x8000 : 0))
408#define SGLTHDRSZ(hasnulls) \
409 ((hasnulls) ? MAXALIGN(sizeof(SpGistLeafTupleData) + \
410 sizeof(IndexAttributeBitMapData)) : \
411 MAXALIGN(sizeof(SpGistLeafTupleData)))
412#define SGLTDATAPTR(x) (((char *) (x)) + SGLTHDRSZ(SGLT_GET_HASNULLMASK(x)))
413#define SGLTDATUM(x, s) fetch_att(SGLTDATAPTR(x), \
414 (s)->attLeafType.attbyval, \
415 (s)->attLeafType.attlen)
440#define SGDTSIZE MAXALIGN(sizeof(SpGistDeadTupleData))
450#define SPGIST_PAGE_CAPACITY \
451 MAXALIGN_DOWN(BLCKSZ - \
452 SizeOfPageHeaderData - \
453 MAXALIGN(sizeof(SpGistPageOpaqueData)))
459#define SpGistPageGetFreeSpace(p, n) \
460 (PageGetExactFreeSpace(p) + \
461 Min(SpGistPageGetOpaque(p)->nPlaceholder, n) * \
462 (SGDTSIZE + sizeof(ItemIdData)))
468#define STORE_STATE(s, d) \
470 (d).redirectXid = (s)->redirectXid; \
471 (d).isBuild = (s)->isBuild; \
485#define GBUF_LEAF 0x03
486#define GBUF_INNER_PARITY(x) ((x) % 3)
487#define GBUF_NULLS 0x04
489#define GBUF_PARITY_MASK 0x03
490#define GBUF_REQ_LEAF(flags) (((flags) & GBUF_PARITY_MASK) == GBUF_LEAF)
491#define GBUF_REQ_NULLS(flags) ((flags) & GBUF_NULLS)
496#define SPGIST_MIN_FILLFACTOR 10
497#define SPGIST_DEFAULT_FILLFACTOR 80
505 int needSpace,
bool *isNew);
512 const Datum *datums,
const bool *isnulls);
515 const Datum *datums,
const bool *isnulls);
519 bool hasPrefix,
Datum prefix,
524 Datum *datums,
bool *isnulls,
525 bool keyColumnIsNull);
529 const void *item,
Size size,
534 bool *res,
bool *isnull);
541 int firststate,
int reststate,
548 ScanKey orderbys,
int norderbys);
#define FLEXIBLE_ARRAY_MEMBER
#define MaxIndexTuplesPerPage
OffsetNumber SpGistPageAddNewItem(SpGistState *state, Page page, const void *item, Size size, OffsetNumber *startOffset, bool errorOK)
BOX * box_copy(BOX *orig)
SpGistDeadTupleData * SpGistDeadTuple
Datum * spgExtractNodeLabels(SpGistState *state, SpGistInnerTuple innerTuple)
void initSpGistState(SpGistState *state, Relation index)
struct SpGistPageOpaqueData SpGistPageOpaqueData
void SpGistUpdateMetaPage(Relation index)
SpGistPageOpaqueData * SpGistPageOpaque
TupleDesc getSpGistTupleDesc(Relation index, SpGistTypeDesc *keyType)
Buffer SpGistNewBuffer(Relation index)
SpGistInnerTupleData * SpGistInnerTuple
SpGistLeafTuple spgFormLeafTuple(SpGistState *state, const ItemPointerData *heapPtr, const Datum *datums, const bool *isnulls)
struct SpGistDeadTupleData SpGistDeadTupleData
SpGistInnerTuple spgFormInnerTuple(SpGistState *state, bool hasPrefix, Datum prefix, int nNodes, SpGistNodeTuple *nodes)
SpGistCache * spgGetCache(Relation index)
void spgPageIndexMultiDelete(SpGistState *state, Page page, OffsetNumber *itemnos, int nitems, int firststate, int reststate, BlockNumber blkno, OffsetNumber offnum)
bool spgdoinsert(Relation index, SpGistState *state, const ItemPointerData *heapPtr, const Datum *datums, const bool *isnulls)
struct SpGistState SpGistState
void spgDeformLeafTuple(SpGistLeafTuple tup, TupleDesc tupleDescriptor, Datum *datums, bool *isnulls, bool keyColumnIsNull)
SpGistDeadTuple spgFormDeadTuple(SpGistState *state, int tupstate, BlockNumber blkno, OffsetNumber offnum)
IndexTupleData SpGistNodeTupleData
SpGistScanOpaqueData * SpGistScanOpaque
struct SpGistInnerTupleData SpGistInnerTupleData
unsigned int SpGistGetInnerTypeSize(SpGistTypeDesc *att, Datum datum)
struct SpGistOptions SpGistOptions
struct SpGistCache SpGistCache
void SpGistInitBuffer(Buffer b, uint16 f)
void spgUpdateNodeLink(SpGistInnerTuple tup, int nodeN, BlockNumber blkno, OffsetNumber offset)
double * spg_key_orderbys_distances(Datum key, bool isLeaf, ScanKey orderbys, int norderbys)
SpGistNodeTupleData * SpGistNodeTuple
struct SpGistMetaPageData SpGistMetaPageData
struct SpGistLastUsedPage SpGistLastUsedPage
Buffer SpGistGetBuffer(Relation index, int flags, int needSpace, bool *isNew)
struct SpGistLeafTupleData * SpGistLeafTuple
#define SPGIST_CACHED_PAGES
bool spgproperty(Oid index_oid, int attno, IndexAMProperty prop, const char *propname, bool *res, bool *isnull)
void SpGistSetLastUsedPage(Relation index, Buffer buffer)
struct SpGistScanOpaqueData SpGistScanOpaqueData
struct SpGistTypeDesc SpGistTypeDesc
struct SpGistSearchItem SpGistSearchItem
Size SpGistGetLeafTupleSize(TupleDesc tupleDescriptor, const Datum *datums, const bool *isnulls)
void SpGistInitPage(Page page, uint16 f)
struct SpGistLeafTupleData SpGistLeafTupleData
SpGistNodeTuple spgFormNodeTuple(SpGistState *state, Datum label, bool isnull)
void SpGistInitMetapage(Page page)
struct SpGistLUPCache SpGistLUPCache
SpGistTypeDesc attPrefixType
SpGistTypeDesc attLeafType
SpGistLUPCache lastUsedPages
SpGistTypeDesc attLabelType
SpGistLastUsedPage cachedPage[SPGIST_CACHED_PAGES]
SpGistLUPCache lastUsedPages
HeapTuple reconTups[MaxIndexTuplesPerPage]
ItemPointerData heapPtrs[MaxIndexTuplesPerPage]
MemoryContext traversalCxt
int * nonNullOrderByOffsets
int numberOfNonNullOrderBys
bool recheckDistances[MaxIndexTuplesPerPage]
FmgrInfo leafConsistentFn
IndexOrderByDistance * distances[MaxIndexTuplesPerPage]
bool recheck[MaxIndexTuplesPerPage]
FmgrInfo innerConsistentFn
SpGistLeafTuple leafTuple
double distances[FLEXIBLE_ARRAY_MEMBER]
SpGistTypeDesc attPrefixType
TransactionId redirectXid
SpGistTypeDesc attLabelType
SpGistTypeDesc attLeafType