v8-0003-Add-all-visible-FSM-heuristic.patch

application/x-patch

Filename: v8-0003-Add-all-visible-FSM-heuristic.patch
Type: application/x-patch
Part: 0
Message: Re: Removing more vacuumlazy.c special cases, relfrozenxid optimizations

Patch

Format: format-patch
Series: patch v8-0003
Subject: Add all-visible FSM heuristic.
File+
src/backend/access/heap/vacuumlazy.c 21 0
From 41136d2a8af434a095ce3e6dfdfbe4b48b9ec338 Mon Sep 17 00:00:00 2001
From: Peter Geoghegan <pg@bowt.ie>
Date: Sun, 23 Jan 2022 21:10:38 -0800
Subject: [PATCH v8 3/3] Add all-visible FSM heuristic.

When recording free space in all-frozen page, record that the page has
zero free space when it has less than half BLCKSZ worth of space,
according to the traditional definition.  Otherwise record free space as
usual.

Making all-visible pages resistant to change like this can be thought of
as a form of hysteresis.  The page is given an opportunity to "settle"
and permanently stay in the same state when the tuples on the page will
never be updated or deleted.  But when they are updated or deleted, the
page can once again be used to store any tuple.  Over time, most pages
tend to settle permanently in many workloads, perhaps only on the second
or third attempt.
---
 src/backend/access/heap/vacuumlazy.c | 21 +++++++++++++++++++++
 1 file changed, 21 insertions(+)

diff --git a/src/backend/access/heap/vacuumlazy.c b/src/backend/access/heap/vacuumlazy.c
index ea4b75189..95049ed25 100644
--- a/src/backend/access/heap/vacuumlazy.c
+++ b/src/backend/access/heap/vacuumlazy.c
@@ -1231,6 +1231,13 @@ lazy_scan_heap(LVRelState *vacrel, int nworkers)
 				 */
 				freespace = PageGetHeapFreeSpace(page);
 
+				/*
+				 * An all-visible page should not have its free space
+				 * available from FSM unless it's more than half empty
+				 */
+				if (PageIsAllVisible(page) && freespace < BLCKSZ / 2)
+					freespace = 0;
+
 				UnlockReleaseBuffer(buf);
 				RecordPageWithFreeSpace(vacrel->rel, blkno, freespace);
 				continue;
@@ -1368,6 +1375,13 @@ lazy_scan_heap(LVRelState *vacrel, int nworkers)
 		{
 			Size		freespace = PageGetHeapFreeSpace(page);
 
+			/*
+			 * An all-visible page should not have its free space available
+			 * from FSM unless it's more than half empty
+			 */
+			if (PageIsAllVisible(page) && freespace < BLCKSZ / 2)
+				freespace = 0;
+
 			UnlockReleaseBuffer(buf);
 			RecordPageWithFreeSpace(vacrel->rel, blkno, freespace);
 		}
@@ -2537,6 +2551,13 @@ lazy_vacuum_heap_rel(LVRelState *vacrel)
 		page = BufferGetPage(buf);
 		freespace = PageGetHeapFreeSpace(page);
 
+		/*
+		 * An all-visible page should not have its free space available from
+		 * FSM unless it's more than half empty
+		 */
+		if (PageIsAllVisible(page) && freespace < BLCKSZ / 2)
+			freespace = 0;
+
 		UnlockReleaseBuffer(buf);
 		RecordPageWithFreeSpace(vacrel->rel, tblk, freespace);
 		vacuumed_pages++;
-- 
2.30.2