52 #define BUFFERING_MODE_SWITCH_CHECK_STEP 256
60 #define BUFFERING_MODE_TUPLE_SIZE_STATS_TARGET 4096
113 #define GIST_SORTED_BUILD_PAGE_NUM 4
135 bool tupleIsAlive,
void *
state);
194 elog(
ERROR,
"index \"%s\" already contains data",
233 bool hasallsortsupports =
true;
236 for (
int i = 0;
i < keyscount;
i++)
242 hasallsortsupports =
false;
246 if (hasallsortsupports)
323 elog(
DEBUG1,
"all tuples processed, emptying buffers");
382 true, compressed_values);
387 compressed_values, isnull);
407 state->pages_allocated = 1;
414 levelstate->
parent = NULL;
448 memcpy(rootbuf, levelstate->
pages[0], BLCKSZ);
532 dist->
itup = union_tuple;
543 for (; dist != NULL; dist = dist->
next)
566 union_tuple = dist->
itup;
587 blkno =
state->pages_allocated++;
633 double avgIndexTuplesPerPage,
634 maxIndexTuplesPerPage;
658 for (
i = 0;
i <
index->rd_att->natts;
i++)
667 avgIndexTuplesPerPage = pageFreeSpace / itupAvgSize;
668 maxIndexTuplesPerPage = pageFreeSpace / itupMinSize;
721 double maxlowestlevelpages;
725 (1 - pow(avgIndexTuplesPerPage, (
double) (levelStep + 1))) /
726 (1 - avgIndexTuplesPerPage);
729 maxlowestlevelpages = pow(maxIndexTuplesPerPage, (
double) levelStep);
755 elog(
DEBUG1,
"failed to switch to buffered GiST build");
775 elog(
DEBUG1,
"switched to buffered GiST build; level step = %d, pagesPerBuffer = %d",
776 levelStep, pagesPerBuffer);
789 double pagesPerBuffer;
790 double avgIndexTuplesPerPage;
806 avgIndexTuplesPerPage = pageFreeSpace / itupAvgSize;
811 pagesPerBuffer = 2 * pow(avgIndexTuplesPerPage, levelStep);
813 return (
int) rint(pagesPerBuffer);
971 childoffnum =
gistchoose(indexrel, page, itup, giststate);
1000 parentblkno = blkno;
1002 downlinkoffnum = childoffnum;
1034 parentblkno, downlinkoffnum);
1067 itup, ntup, oldoffnum, &placed_to_blk,
1157 foreach(lc, splitinfo)
1192 downlinks, ndownlinks, downlinkoffnum,
1200 return placed_to_blk;
1243 elog(
ERROR,
"no parent buffer provided of child %u", childblkno);
1282 *downlinkoffnum = off;
1287 elog(
ERROR,
"failed to re-find parent for block %u", childblkno);
1416 elog(
DEBUG2,
"emptied all buffers at level %d",
i);
1576 elog(
ERROR,
"could not find parent of block %u in lookup table", child);
#define InvalidBlockNumber
static Datum values[MAXATTR]
BlockNumber BufferGetBlockNumber(Buffer buffer)
void UnlockReleaseBuffer(Buffer buffer)
void MarkBufferDirty(Buffer buffer)
void LockBuffer(Buffer buffer, int mode)
Buffer ReadBuffer(Relation reln, BlockNumber blockNum)
#define RelationGetNumberOfBlocks(reln)
static Page BufferGetPage(Buffer buffer)
Size PageGetFreeSpace(Page page)
static Item PageGetItem(Page page, ItemId itemId)
#define SizeOfPageHeaderData
static ItemId PageGetItemId(Page page, OffsetNumber offsetNumber)
static void PageSetLSN(Page page, XLogRecPtr lsn)
static OffsetNumber PageGetMaxOffsetNumber(Page page)
#define PageAddItem(page, item, size, offsetNumber, overwrite, is_heap)
void smgr_bulk_write(BulkWriteState *bulkstate, BlockNumber blocknum, BulkWriteBuffer buf, bool page_std)
BulkWriteBuffer smgr_bulk_get_buf(BulkWriteState *bulkstate)
void smgr_bulk_finish(BulkWriteState *bulkstate)
BulkWriteState * smgr_bulk_start_rel(Relation rel, ForkNumber forknum)
#define Assert(condition)
#define OidIsValid(objectId)
void * hash_search(HTAB *hashp, const void *keyPtr, HASHACTION action, bool *foundPtr)
HTAB * hash_create(const char *tabname, long nelem, const HASHCTL *info, int flags)
void gistdoinsert(Relation r, IndexTuple itup, Size freespace, GISTSTATE *giststate, Relation heapRel, bool is_build)
bool gistplacetopage(Relation rel, Size freespace, GISTSTATE *giststate, Buffer buffer, IndexTuple *itup, int ntup, OffsetNumber oldoffnum, BlockNumber *newblkno, Buffer leftchildbuf, List **splitinfo, bool markfollowright, Relation heapRel, bool is_build)
GISTSTATE * initGISTstate(Relation index)
MemoryContext createTempGistContext(void)
void freeGISTstate(GISTSTATE *giststate)
SplitPageLayout * gistSplit(Relation r, Page page, IndexTuple *itup, int len, GISTSTATE *giststate)
#define GIST_SORTSUPPORT_PROC
struct GISTPageOpaqueData GISTPageOpaqueData
#define GistPageIsLeaf(page)
#define GistPageGetOpaque(page)
#define LEVEL_HAS_BUFFERS(nlevel, gfbb)
@ GIST_OPTION_BUFFERING_OFF
@ GIST_OPTION_BUFFERING_ON
#define GIST_DEFAULT_FILLFACTOR
#define BUFFER_OVERFLOWED(nodeBuffer, gfbb)
@ GIST_BUFFERING_DISABLED
static BlockNumber gistbufferinginserttuples(GISTBuildState *buildstate, Buffer buffer, int level, IndexTuple *itup, int ntup, OffsetNumber oldoffnum, BlockNumber parentblk, OffsetNumber downlinkoffnum)
static void gistMemorizeAllDownlinks(GISTBuildState *buildstate, Buffer parentbuf)
static bool gistProcessItup(GISTBuildState *buildstate, IndexTuple itup, BlockNumber startblkno, int startlevel)
static void gist_indexsortbuild_levelstate_flush(GISTBuildState *state, GistSortedBuildLevelState *levelstate)
#define BUFFERING_MODE_SWITCH_CHECK_STEP
static Buffer gistBufferingFindCorrectParent(GISTBuildState *buildstate, BlockNumber childblkno, int level, BlockNumber *parentblkno, OffsetNumber *downlinkoffnum)
static int calculatePagesPerBuffer(GISTBuildState *buildstate, int levelStep)
static void gist_indexsortbuild_levelstate_add(GISTBuildState *state, GistSortedBuildLevelState *levelstate, IndexTuple itup)
static void gist_indexsortbuild(GISTBuildState *state)
static void gistInitParentMap(GISTBuildState *buildstate)
static void gistBuildCallback(Relation index, ItemPointer tid, Datum *values, bool *isnull, bool tupleIsAlive, void *state)
static void gistSortedBuildCallback(Relation index, ItemPointer tid, Datum *values, bool *isnull, bool tupleIsAlive, void *state)
static void gistMemorizeParent(GISTBuildState *buildstate, BlockNumber child, BlockNumber parent)
#define GIST_SORTED_BUILD_PAGE_NUM
static void gistEmptyAllBuffers(GISTBuildState *buildstate)
#define BUFFERING_MODE_TUPLE_SIZE_STATS_TARGET
static void gistInitBuffering(GISTBuildState *buildstate)
static void gistBufferingBuildInsert(GISTBuildState *buildstate, IndexTuple itup)
IndexBuildResult * gistbuild(Relation heap, Relation index, IndexInfo *indexInfo)
static BlockNumber gistGetParent(GISTBuildState *buildstate, BlockNumber child)
static int gistGetMaxLevel(Relation index)
struct GistSortedBuildLevelState GistSortedBuildLevelState
static void gistProcessEmptyingQueue(GISTBuildState *buildstate)
void gistPushItupToNodeBuffer(GISTBuildBuffers *gfbb, GISTNodeBuffer *nodeBuffer, IndexTuple itup)
void gistRelocateBuildBuffersOnSplit(GISTBuildBuffers *gfbb, GISTSTATE *giststate, Relation r, int level, Buffer buffer, List *splitinfo)
GISTBuildBuffers * gistInitBuildBuffers(int pagesPerBuffer, int levelStep, int maxLevel)
void gistFreeBuildBuffers(GISTBuildBuffers *gfbb)
GISTNodeBuffer * gistGetNodeBuffer(GISTBuildBuffers *gfbb, GISTSTATE *giststate, BlockNumber nodeBlocknum, int level)
bool gistPopItupFromNodeBuffer(GISTBuildBuffers *gfbb, GISTNodeBuffer *nodeBuffer, IndexTuple *itup)
void gistUnloadNodeBuffers(GISTBuildBuffers *gfbb)
Buffer gistNewBuffer(Relation r, Relation heaprel)
void gistfillbuffer(Page page, IndexTuple *itup, int len, OffsetNumber off)
IndexTuple gistFormTuple(GISTSTATE *giststate, Relation r, const Datum *attdata, const bool *isnull, bool isleaf)
IndexTuple * gistextractpage(Page page, int *len)
IndexTuple gistgetadjusted(Relation r, IndexTuple oldtup, IndexTuple addtup, GISTSTATE *giststate)
OffsetNumber gistchoose(Relation r, Page p, IndexTuple it, GISTSTATE *giststate)
void gistCompressValues(GISTSTATE *giststate, Relation r, const Datum *attdata, const bool *isnull, bool isleaf, Datum *compatt)
IndexTuple * gistjoinvector(IndexTuple *itvec, int *len, IndexTuple *additvec, int addlen)
void gistinitpage(Page page, uint32 f)
IndexTuple gistunion(Relation r, IndexTuple *itvec, int len, GISTSTATE *giststate)
void GISTInitBuffer(Buffer b, uint32 f)
IndexTupleData * gistfillitupvec(IndexTuple *vec, int veclen, int *memlen)
void gistcheckpage(Relation rel, Buffer buf)
RegProcedure index_getprocid(Relation irel, AttrNumber attnum, uint16 procnum)
if(TABLE==NULL||TABLE_index==NULL)
struct ItemIdData ItemIdData
static void ItemPointerSetBlockNumber(ItemPointerData *pointer, BlockNumber blockNumber)
static BlockNumber ItemPointerGetBlockNumber(const ItemPointerData *pointer)
IndexTupleData * IndexTuple
#define IndexTupleSize(itup)
List * list_delete_first(List *list)
List * lcons(void *datum, List *list)
void list_free_deep(List *list)
void MemoryContextReset(MemoryContext context)
void pfree(void *pointer)
void * palloc0(Size size)
MemoryContext CurrentMemoryContext
void MemoryContextDelete(MemoryContext context)
#define START_CRIT_SECTION()
#define CHECK_FOR_INTERRUPTS()
#define END_CRIT_SECTION()
#define InvalidOffsetNumber
#define OffsetNumberNext(offsetNumber)
#define FirstOffsetNumber
static int list_length(const List *l)
MemoryContextSwitchTo(old_ctx)
static SMgrRelation RelationGetSmgr(Relation rel)
#define RelationGetRelationName(relation)
#define RelationNeedsWAL(relation)
#define IndexRelationGetNumberOfKeyAttributes(relation)
BlockNumber smgrnblocks(SMgrRelation reln, ForkNumber forknum)
List * bufferEmptyingQueue
BlockNumber pages_allocated
BulkWriteState * bulkstate
Tuplesortstate * sortstate
Page pages[GIST_SORTED_BUILD_PAGE_NUM]
struct GistSortedBuildLevelState * parent
struct SplitPageLayout * next
static double table_index_build_scan(Relation table_rel, Relation index_rel, struct IndexInfo *index_info, bool allow_sync, bool progress, IndexBuildCallback callback, void *callback_state, TableScanDesc scan)
#define TupleDescAttr(tupdesc, i)
void tuplesort_performsort(Tuplesortstate *state)
void tuplesort_end(Tuplesortstate *state)
IndexTuple tuplesort_getindextuple(Tuplesortstate *state, bool forward)
void tuplesort_putindextuplevalues(Tuplesortstate *state, Relation rel, ItemPointer self, const Datum *values, const bool *isnull)
Tuplesortstate * tuplesort_begin_index_gist(Relation heapRel, Relation indexRel, int workMem, SortCoordinate coordinate, int sortopt)
void log_newpage_range(Relation rel, ForkNumber forknum, BlockNumber startblk, BlockNumber endblk, bool page_std)