Improve the efficiency of _bt_killitems.

From: feichanghong <feichanghong(at)qq(dot)com>
To: pgsql-hackers(at)lists(dot)postgresql(dot)org
Cc: hu_yajun(at)qq(dot)com
Subject: Improve the efficiency of _bt_killitems.
Date: 2024-11-01 07:19:59
Message-ID: tencent_E183B533F143CC2486E31F414DE9E3DD2305@qq.com
Views: Raw Message | Whole Thread | Download mbox | Resend email
Thread:
Lists: pgsql-hackers

Hi hackers,

In the _bt_killitems function, the following logic is present: we search to the
right for an index item that matches the heap TID and attempt to mark it as
dead. If that index item has already been marked as dead by other concurrent
processes, we will continue searching. However, there should not be any more
matching index items on the current page.

```
while (offnum <= maxoff)
{
...
/*
* Mark index item as dead, if it isn't already. Since this
* happens while holding a buffer lock possibly in shared mode,
* it's possible that multiple processes attempt to do this
* simultaneously, leading to multiple full-page images being sent
* to WAL (if wal_log_hints or data checksums are enabled), which
* is undesirable.
*/
if (killtuple && !ItemIdIsDead(iid))
{
/* found the item/all posting list items */
ItemIdMarkDead(iid);
killedsomething = true;
break; /* out of inner search loop */
}
offnum = OffsetNumberNext(offnum);
}
```

Perhaps we should exit the current loop immediately when the killtuple is set,
stopping the search to the right. This could improve efficiency, especially
when the index item to be killed is the first one on the current page:

```
diff --git a/src/backend/access/nbtree/nbtutils.c b/src/backend/access/nbtree/nbtutils.c
index b4ba51357a5..529a3083165 100644
--- a/src/backend/access/nbtree/nbtutils.c
+++ b/src/backend/access/nbtree/nbtutils.c
@@ -4298,11 +4298,14 @@ _bt_killitems(IndexScanDesc scan)
* 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;
+ if (!ItemIdIsDead(iid))
+ {
+ /* found the item/all posting list items */
+ ItemIdMarkDead(iid);
+ killedsomething = true;
+ }
break; /* out of inner search loop */
}
offnum = OffsetNumberNext(offnum);
```

Best Regards,
Fei Changhong

Responses

Browse pgsql-hackers by date

  From Date Subject
Next Message David Rowley 2024-11-01 07:21:50 Re: define pg_structiszero(addr, s, r)
Previous Message David Rowley 2024-11-01 07:19:39 Re: define pg_structiszero(addr, s, r)