aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorMichael Paquier <michael@paquier.xyz>2021-08-23 11:09:33 +0900
committerMichael Paquier <michael@paquier.xyz>2021-08-23 11:09:33 +0900
commita3fcbcda7505e9079cec95e7209cde4f5d5c8bd8 (patch)
treef4015c672d1d0a87a7c454bc4e8c15197b3b4247 /src
parentc818c25f448d0085e1bb2be402463a4b28bc20c4 (diff)
downloadpostgresql-a3fcbcda7505e9079cec95e7209cde4f5d5c8bd8.tar.gz
postgresql-a3fcbcda7505e9079cec95e7209cde4f5d5c8bd8.zip
Fix backup manifests to generate correct WAL-Ranges across timelines
In a backup manifest, WAL-Ranges stores the range of WAL that is required for the backup to be valid. pg_verifybackup would then internally use pg_waldump for the checks based on this data. When the timeline where the backup started was more than 1 with a history file looked at for the manifest data generation, the calculation of the WAL range for the first timeline to check was incorrect. The previous logic used as start LSN the start position of the first timeline, but it needs to use the start LSN of the backup. This would cause failures with pg_verifybackup, or any tools making use of the backup manifests. This commit adds a test based on a logic using a self-promoted node, making it rather cheap. Author: Kyotaro Horiguchi Discussion: https://postgr.es/m/20210818.143031.1867083699202617521.horikyota.ntt@gmail.com Backpatch-through: 13
Diffstat (limited to 'src')
-rw-r--r--src/backend/replication/backup_manifest.c15
-rw-r--r--src/bin/pg_verifybackup/t/007_wal.pl19
2 files changed, 29 insertions, 5 deletions
diff --git a/src/backend/replication/backup_manifest.c b/src/backend/replication/backup_manifest.c
index 921de47a6c2..04ca455ace8 100644
--- a/src/backend/replication/backup_manifest.c
+++ b/src/backend/replication/backup_manifest.c
@@ -251,11 +251,18 @@ AddWALInfoToBackupManifest(backup_manifest_info *manifest, XLogRecPtr startptr,
errmsg("expected end timeline %u but found timeline %u",
starttli, entry->tli));
- if (!XLogRecPtrIsInvalid(entry->begin))
- tl_beginptr = entry->begin;
+ /*
+ * If this timeline entry matches with the timeline on which the
+ * backup started, WAL needs to be checked from the start LSN of the
+ * backup. If this entry refers to a newer timeline, WAL needs to be
+ * checked since the beginning of this timeline, so use the LSN where
+ * the timeline began.
+ */
+ if (starttli == entry->tli)
+ tl_beginptr = startptr;
else
{
- tl_beginptr = startptr;
+ tl_beginptr = entry->begin;
/*
* If we reach a TLI that has no valid beginning LSN, there can't
@@ -263,7 +270,7 @@ AddWALInfoToBackupManifest(backup_manifest_info *manifest, XLogRecPtr startptr,
* better have arrived at the expected starting TLI. If not,
* something's gone horribly wrong.
*/
- if (starttli != entry->tli)
+ if (XLogRecPtrIsInvalid(entry->begin))
ereport(ERROR,
errmsg("expected start timeline %u but found timeline %u",
starttli, entry->tli));
diff --git a/src/bin/pg_verifybackup/t/007_wal.pl b/src/bin/pg_verifybackup/t/007_wal.pl
index adf60fb7556..29b8a070d74 100644
--- a/src/bin/pg_verifybackup/t/007_wal.pl
+++ b/src/bin/pg_verifybackup/t/007_wal.pl
@@ -10,7 +10,7 @@ use Config;
use File::Path qw(rmtree);
use PostgresNode;
use TestLib;
-use Test::More tests => 7;
+use Test::More tests => 9;
# Start up the server and take a backup.
my $primary = PostgresNode->new('primary');
@@ -59,3 +59,20 @@ command_fails_like(
[ 'pg_verifybackup', $backup_path ],
qr/WAL parsing failed for timeline 1/,
'corrupt WAL file causes failure');
+
+# Check that WAL-Ranges has correct values with a history file and
+# a timeline > 1. Rather than plugging in a new standby, do a
+# self-promotion of this node.
+$primary->stop;
+$primary->append_conf('standby.signal');
+$primary->start;
+$primary->promote;
+$primary->safe_psql('postgres', 'SELECT pg_switch_wal()');
+my $backup_path2 = $primary->backup_dir . '/test_tli';
+# The base backup run below does a checkpoint, that removes the first segment
+# of the current timeline.
+$primary->command_ok([ 'pg_basebackup', '-D', $backup_path2, '--no-sync' ],
+ "base backup 2 ok");
+command_ok(
+ [ 'pg_verifybackup', $backup_path2 ],
+ 'valid base backup with timeline > 1');