diff --git a/src/backend/access/heap/heapam_handler.c b/src/backend/access/heap/heapam_handler.c index 6ecd7631489..f35ccabb4ff 100644 --- a/src/backend/access/heap/heapam_handler.c +++ b/src/backend/access/heap/heapam_handler.c @@ -895,8 +895,17 @@ heapam_relation_copy_for_cluster(Relation OldHeap, Relation NewHeap, Assert(BlockNumberIsValid(range_end)); - /* End of the current range or wraparound? */ - if (blkno >= range_end || blkno < range_start) + /* + * End of the current range or wraparound? + * + * range_start is where the scan started and it never changes. + * Once the scan has wrapped around, range_end is not above it and + * the blocks before range_end are in the range too, like in + * is_block_in_range(). + */ + if (range_start < range_end ? + (blkno >= range_end || blkno < range_start) : + (blkno >= range_end && blkno < range_start)) snapshot = finalize_block_range(chgcxt, blkno, range_start, &range_end); @@ -1111,6 +1120,13 @@ finalize_block_range(ChangeContext *chgcxt, BlockNumber cur, * block number could have wrapped around. */ end = cur + repack_pages_per_snapshot - (cur % repack_pages_per_snapshot); + + /* + * After wraparound the scan ends right before 'start'. If the range went + * beyond that, it would look like a range that has not wrapped around. + */ + if (cur < start && end > start) + end = start; *end_p = end; /*