Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
Report syncscan position at end of scan.
authorHeikki Linnakangas <heikki.linnakangas@iki.fi>
Thu, 31 Aug 2023 10:02:15 +0000 (13:02 +0300)
committerHeikki Linnakangas <heikki.linnakangas@iki.fi>
Thu, 31 Aug 2023 10:02:37 +0000 (13:02 +0300)
The comment in heapgettup_advance_block() says that it reports the
scan position before checking for end of scan, but that didn't match
the code. The code was refactored in commit 7ae0ab0ad9, which
inadvertently changed the order of the check and reporting. Change it
back.

This caused a few regression test failures with a small shared_buffers
setting like 10 MB. The 'portals' and 'cluster' tests perform seqscans
that are large enough that sync seqscans kick in. When the sync scan
position is not updated at end of scan, the next seq scan doesn't
start at the beginning of the table, and the test queries are
sensitive to that.

Reviewed-by: Melanie Plageman, David Rowley
Discussion: https://www.postgresql.org/message-id/6f991389-ae22-d844-a9d8-9aceb7c01a9a@iki.fi
Backpatch-through: 16

src/backend/access/heap/heapam.c

index 6a66214a58041ef5850af0064f8af47159c088d8..dc3c4074ed63852b257fbc2f6276189834cc909e 100644 (file)
@@ -647,17 +647,6 @@ heapgettup_advance_block(HeapScanDesc scan, BlockNumber block, ScanDirection dir
            if (block >= scan->rs_nblocks)
                block = 0;
 
-           /* we're done if we're back at where we started */
-           if (block == scan->rs_startblock)
-               return InvalidBlockNumber;
-
-           /* check if the limit imposed by heap_setscanlimits() is met */
-           if (scan->rs_numblocks != InvalidBlockNumber)
-           {
-               if (--scan->rs_numblocks == 0)
-                   return InvalidBlockNumber;
-           }
-
            /*
             * Report our new scan position for synchronization purposes. We
             * don't do that when moving backwards, however. That would just
@@ -673,6 +662,17 @@ heapgettup_advance_block(HeapScanDesc scan, BlockNumber block, ScanDirection dir
            if (scan->rs_base.rs_flags & SO_ALLOW_SYNC)
                ss_report_location(scan->rs_base.rs_rd, block);
 
+           /* we're done if we're back at where we started */
+           if (block == scan->rs_startblock)
+               return InvalidBlockNumber;
+
+           /* check if the limit imposed by heap_setscanlimits() is met */
+           if (scan->rs_numblocks != InvalidBlockNumber)
+           {
+               if (--scan->rs_numblocks == 0)
+                   return InvalidBlockNumber;
+           }
+
            return block;
        }
        else