From 542ff1da0f42ad21189418f33db68bf618a873e0 Mon Sep 17 00:00:00 2001 From: Rahul Yadav Date: Thu, 1 Oct 2026 07:46:25 +0100 Subject: [PATCH v1 1/2] Report the decoded record's LSN in DecodeXLogRecord() errors DecodeXLogRecord() is passed the LSN of the record it decodes, but its error messages printed state->ReadRecPtr instead. Before 3f1ce97346 added the circular WAL decoding buffer, the two were the same, since XLogReadRecord() set ReadRecPtr before decoding. Now records are decoded ahead of the one the reader last returned, so these messages named an earlier record: in pg_waldump the record just before the failing one, and in crash recovery, which reads further ahead, one several records back. Use the lsn argument instead. The only other caller, the WAL_DEBUG code in XLogInsertRecord(), passes the end of the record it has just inserted, which matches the LSN that code logs for it. Noticed while testing a fix for bug #19599. Author: Rahul Yadav Backpatch-through: 15 --- src/backend/access/transam/xlogreader.c | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7db7c273b0..6573270dab 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1818,7 +1818,7 @@ DecodeXLogRecord(XLogReaderState *state, report_invalid_record(state, "out-of-order block_id %u at %X/%08X", block_id, - LSN_FORMAT_ARGS(state->ReadRecPtr)); + LSN_FORMAT_ARGS(lsn)); goto err; } decoded->max_block_id = block_id; @@ -1841,7 +1841,7 @@ DecodeXLogRecord(XLogReaderState *state, { report_invalid_record(state, "BKPBLOCK_HAS_DATA set, but no data included at %X/%08X", - LSN_FORMAT_ARGS(state->ReadRecPtr)); + LSN_FORMAT_ARGS(lsn)); goto err; } if (!blk->has_data && blk->data_len != 0) @@ -1849,7 +1849,7 @@ DecodeXLogRecord(XLogReaderState *state, report_invalid_record(state, "BKPBLOCK_HAS_DATA not set, but data length is %d at %X/%08X", blk->data_len, - LSN_FORMAT_ARGS(state->ReadRecPtr)); + LSN_FORMAT_ARGS(lsn)); goto err; } datatotal += blk->data_len; @@ -1887,7 +1887,7 @@ DecodeXLogRecord(XLogReaderState *state, blk->hole_offset, blk->hole_length, blk->bimg_len, - LSN_FORMAT_ARGS(state->ReadRecPtr)); + LSN_FORMAT_ARGS(lsn)); goto err; } @@ -1902,7 +1902,7 @@ DecodeXLogRecord(XLogReaderState *state, "BKPIMAGE_HAS_HOLE not set, but hole offset %d length %d at %X/%08X", blk->hole_offset, blk->hole_length, - LSN_FORMAT_ARGS(state->ReadRecPtr)); + LSN_FORMAT_ARGS(lsn)); goto err; } @@ -1915,7 +1915,7 @@ DecodeXLogRecord(XLogReaderState *state, report_invalid_record(state, "BKPIMAGE_COMPRESSED set, but block image length %d at %X/%08X", blk->bimg_len, - LSN_FORMAT_ARGS(state->ReadRecPtr)); + LSN_FORMAT_ARGS(lsn)); goto err; } @@ -1930,7 +1930,7 @@ DecodeXLogRecord(XLogReaderState *state, report_invalid_record(state, "neither BKPIMAGE_HAS_HOLE nor BKPIMAGE_COMPRESSED set, but block image length is %d at %X/%08X", blk->bimg_len, - LSN_FORMAT_ARGS(state->ReadRecPtr)); + LSN_FORMAT_ARGS(lsn)); goto err; } } @@ -1945,7 +1945,7 @@ DecodeXLogRecord(XLogReaderState *state, { report_invalid_record(state, "BKPBLOCK_SAME_REL set but no previous rel at %X/%08X", - LSN_FORMAT_ARGS(state->ReadRecPtr)); + LSN_FORMAT_ARGS(lsn)); goto err; } @@ -1957,7 +1957,7 @@ DecodeXLogRecord(XLogReaderState *state, { report_invalid_record(state, "invalid block_id %u at %X/%08X", - block_id, LSN_FORMAT_ARGS(state->ReadRecPtr)); + block_id, LSN_FORMAT_ARGS(lsn)); goto err; } } @@ -2024,7 +2024,7 @@ DecodeXLogRecord(XLogReaderState *state, shortdata_err: report_invalid_record(state, "record with invalid length at %X/%08X", - LSN_FORMAT_ARGS(state->ReadRecPtr)); + LSN_FORMAT_ARGS(lsn)); err: *errormsg = state->errormsg_buf; -- 2.50.1 (Apple Git-155)