diff --git a/src/backend/access/nbtree/nbtutils.c b/src/backend/access/nbtree/nbtutils.c index 1429ac8b63..ee7e8edf58 100644 --- a/src/backend/access/nbtree/nbtutils.c +++ b/src/backend/access/nbtree/nbtutils.c @@ -1776,6 +1776,7 @@ _bt_killitems(IndexScanDesc scan) int itemIndex = so->killedItems[i]; BTScanPosItem *kitem = &so->currPos.items[itemIndex]; OffsetNumber offnum = kitem->indexOffset; + OffsetNumber current_offnum PG_USED_FOR_ASSERTS_ONLY; Assert(itemIndex >= so->currPos.firstItem && itemIndex <= so->currPos.lastItem); @@ -1784,9 +1785,19 @@ _bt_killitems(IndexScanDesc scan) while (offnum <= maxoff) { ItemId iid = PageGetItemId(page, offnum); - IndexTuple ituple = (IndexTuple) PageGetItem(page, iid); - bool killtuple = false; + IndexTuple ituple; + bool killtuple; + + /* Save current offnum and advance to the next, avoiding call twice OffsetNumberNext */ + current_offnum = offnum; + offnum = OffsetNumberNext(offnum); + + /* Item already as dead, goes to next */ + if (ItemIdIsDead(iid)) + continue; + killtuple = false; + ituple = (IndexTuple) PageGetItem(page, iid); if (BTreeTupleIsPosting(ituple)) { int pi = i + 1; @@ -1819,7 +1830,7 @@ _bt_killitems(IndexScanDesc scan) * though only in the common case where the page can't * have been concurrently modified */ - Assert(kitem->indexOffset == offnum || !droppedpin); + Assert(kitem->indexOffset == current_offnum || !droppedpin); /* * Read-ahead to later kitems here. @@ -1862,14 +1873,13 @@ _bt_killitems(IndexScanDesc scan) * set to WAL (if wal_log_hints or data checksums are enabled), * which is undesirable. */ - if (killtuple && !ItemIdIsDead(iid)) + if (killtuple) { /* found the item/all posting list items */ ItemIdMarkDead(iid); killedsomething = true; break; /* out of inner search loop */ } - offnum = OffsetNumberNext(offnum); } }