Skip to content

Commit 61dd418

Browse files
committed
Keep rs_startblock the same during heap_rescan, so that a rescan of a SeqScan
node starts from the same place as the first scan did. This avoids surprising behavior of scrollable and WITH HOLD cursors, as seen in Mark Kirkwood's bug report of yesterday. It's not entirely clear whether a rescan should be forced to drop out of the syncscan mode, but for the moment I left the code behaving the same on that point. Any change there would only be a performance and not a correctness issue, anyway. Back-patch to 8.3, since the unstable behavior was created by the syncscan patch.
1 parent 2ef8c1a commit 61dd418

File tree

1 file changed

+14
-5
lines changed

1 file changed

+14
-5
lines changed

src/backend/access/heap/heapam.c

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
*
99
*
1010
* IDENTIFICATION
11-
* $PostgreSQL: pgsql/src/backend/access/heap/heapam.c,v 1.275 2009/05/12 16:43:32 tgl Exp $
11+
* $PostgreSQL: pgsql/src/backend/access/heap/heapam.c,v 1.276 2009/06/10 18:54:16 tgl Exp $
1212
*
1313
*
1414
* INTERFACE ROUTINES
@@ -93,7 +93,7 @@ static bool HeapSatisfiesHOTUpdate(Relation relation, Bitmapset *hot_attrs,
9393
* ----------------
9494
*/
9595
static void
96-
initscan(HeapScanDesc scan, ScanKey key)
96+
initscan(HeapScanDesc scan, ScanKey key, bool is_rescan)
9797
{
9898
bool allow_strat;
9999
bool allow_sync;
@@ -143,7 +143,16 @@ initscan(HeapScanDesc scan, ScanKey key)
143143
scan->rs_strategy = NULL;
144144
}
145145

146-
if (allow_sync && synchronize_seqscans)
146+
if (is_rescan)
147+
{
148+
/*
149+
* If rescan, keep the previous startblock setting so that rewinding
150+
* a cursor doesn't generate surprising results. Reset the syncscan
151+
* setting, though.
152+
*/
153+
scan->rs_syncscan = (allow_sync && synchronize_seqscans);
154+
}
155+
else if (allow_sync && synchronize_seqscans)
147156
{
148157
scan->rs_syncscan = true;
149158
scan->rs_startblock = ss_get_location(scan->rs_rd, scan->rs_nblocks);
@@ -1218,7 +1227,7 @@ heap_beginscan_internal(Relation relation, Snapshot snapshot,
12181227
else
12191228
scan->rs_key = NULL;
12201229

1221-
initscan(scan, key);
1230+
initscan(scan, key, false);
12221231

12231232
return scan;
12241233
}
@@ -1240,7 +1249,7 @@ heap_rescan(HeapScanDesc scan,
12401249
/*
12411250
* reinitialize scan descriptor
12421251
*/
1243-
initscan(scan, key);
1252+
initscan(scan, key, true);
12441253
}
12451254

12461255
/* ----------------

0 commit comments

Comments
 (0)