Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
Skip to content

Commit 6312c08

Browse files
nbtree: Use raw PageAddItem() for retail inserts.
Only internal page splits need to call _bt_pgaddtup() instead of PageAddItem(), and only for data items, one of which will end up at the first offset (or first offset after the high key offset) on the new right page. This data item alone will need to be truncated in _bt_pgaddtup(). Since there is no reason why retail inserts ever need to truncate the incoming item, use a raw PageAddItem() call there instead. Even _bt_split() uses raw PageAddItem() calls for left page and right page high keys. Clearly the _bt_pgaddtup() shim function wasn't really encapsulating anything. _bt_pgaddtup() should now be thought of as a _bt_split() helper function. Note that the assertions from commit d1e241c verify that retail inserts never insert an item at an internal page's negative infinity offset. This invariant could only ever be violated as a result of a basic logic error in nbtinsert.c.
1 parent d41202f commit 6312c08

File tree

1 file changed

+19
-7
lines changed

1 file changed

+19
-7
lines changed

src/backend/access/nbtree/nbtinsert.c

Lines changed: 19 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1249,7 +1249,8 @@ _bt_insertonpg(Relation rel,
12491249
if (postingoff != 0)
12501250
memcpy(oposting, nposting, MAXALIGN(IndexTupleSize(nposting)));
12511251

1252-
if (!_bt_pgaddtup(page, itemsz, itup, newitemoff))
1252+
if (PageAddItem(page, (Item) itup, itemsz, newitemoff, false,
1253+
false) == InvalidOffsetNumber)
12531254
elog(PANIC, "failed to add new item to block %u in index \"%s\"",
12541255
BufferGetBlockNumber(buf), RelationGetRelationName(rel));
12551256

@@ -2528,19 +2529,30 @@ _bt_newroot(Relation rel, Buffer lbuf, Buffer rbuf)
25282529
}
25292530

25302531
/*
2531-
* _bt_pgaddtup() -- add a tuple to a particular page in the index.
2532+
* _bt_pgaddtup() -- add a data item to a particular page during split.
25322533
*
25332534
* This routine adds the tuple to the page as requested. It does
25342535
* not affect pin/lock status, but you'd better have a write lock
25352536
* and pin on the target buffer! Don't forget to write and release
25362537
* the buffer afterwards, either.
25372538
*
2538-
* The main difference between this routine and a bare PageAddItem call
2539-
* is that this code knows that the leftmost index tuple on a non-leaf
2539+
* The difference between this routine and a bare PageAddItem call is
2540+
* that this code knows that the leftmost data item on an internal
25402541
* btree page has a key that must be treated as minus infinity.
2541-
* Therefore, it truncates away all attributes. CAUTION: this works
2542-
* ONLY if we insert the tuples in order, so that the given itup_off
2543-
* does represent the final position of the tuple!
2542+
* Therefore, it truncates away all attributes. This extra step is
2543+
* only needed during internal page splits.
2544+
*
2545+
* Truncation of an internal page data item can be thought of as one
2546+
* of the steps used to "move" a boundary separator key during an
2547+
* internal page split. Conceptually, _bt_split() caller splits
2548+
* internal pages "inside" the firstright data item: firstright's
2549+
* separator key is used as the high key for the left page, while its
2550+
* downlink is used within the first data item (also the negative
2551+
* infinity item) for the right page. Each distinct separator key
2552+
* should appear no more than once per level of the tree.
2553+
*
2554+
* CAUTION: this works ONLY if we insert the tuples in order, so that
2555+
* the given itup_off does represent the final position of the tuple!
25442556
*/
25452557
static bool
25462558
_bt_pgaddtup(Page page,

0 commit comments

Comments
 (0)