aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorPeter Eisentraut <peter@eisentraut.org>2021-03-10 15:19:37 +0100
committerPeter Eisentraut <peter@eisentraut.org>2021-03-10 15:19:37 +0100
commitbbaf315309ed1194d451326cc8f4f59a45906408 (patch)
tree086b59d6168704bc646bc5901422b31dd29fd487 /src
parentc427de427ac411039d5efd5d0dcc8a4e0c6da68d (diff)
downloadpostgresql-bbaf315309ed1194d451326cc8f4f59a45906408.tar.gz
postgresql-bbaf315309ed1194d451326cc8f4f59a45906408.zip
Add bound check before bsearch() for performance
In the current lazy vacuum implementation, some index AMs such as btree indexes call lazy_tid_reaped() for each index tuple during ambulkdelete to check if the index tuple points to the (collected) garbage tuple. In that function, we simply call bsearch(), but we should be able to know the result without bsearch() if the index tuple points to the heap tuple that is out of range of the collected garbage tuples. Therefore, add a simple bound check before resorting to bsearch(). Testing has shown that this can give significant performance benefits. Author: Masahiko Sawada <masahiko.sawada@2ndquadrant.com> Discussion: https://www.postgresql.org/message-id/flat/CA+fd4k76j8jKzJzcx8UqEugvayaMSnQz0iLUt_XgBp-_-bd22A@mail.gmail.com
Diffstat (limited to 'src')
-rw-r--r--src/backend/access/heap/vacuumlazy.c17
1 files changed, 17 insertions, 0 deletions
diff --git a/src/backend/access/heap/vacuumlazy.c b/src/backend/access/heap/vacuumlazy.c
index d8f847b0e66..4b65205cd13 100644
--- a/src/backend/access/heap/vacuumlazy.c
+++ b/src/backend/access/heap/vacuumlazy.c
@@ -61,6 +61,7 @@
#include "access/visibilitymap.h"
#include "access/xact.h"
#include "access/xlog.h"
+#include "catalog/index.h"
#include "catalog/storage.h"
#include "commands/dbcommands.h"
#include "commands/progress.h"
@@ -2923,8 +2924,24 @@ static bool
lazy_tid_reaped(ItemPointer itemptr, void *state)
{
LVDeadTuples *dead_tuples = (LVDeadTuples *) state;
+ int64 litem,
+ ritem,
+ item;
ItemPointer res;
+ litem = itemptr_encode(&dead_tuples->itemptrs[0]);
+ ritem = itemptr_encode(&dead_tuples->itemptrs[dead_tuples->num_tuples - 1]);
+ item = itemptr_encode(itemptr);
+
+ /*
+ * Doing a simple bound check before bsearch() is useful to avoid the
+ * extra cost of bsearch(), especially if dead tuples on the heap are
+ * concentrated in a certain range. Since this function is called for
+ * every index tuple, it pays to be really fast.
+ */
+ if (item < litem || item > ritem)
+ return false;
+
res = (ItemPointer) bsearch((void *) itemptr,
(void *) dead_tuples->itemptrs,
dead_tuples->num_tuples,