From 465ef4d1017171f80d320e56cced8539c3e896eb Mon Sep 17 00:00:00 2001
From: Robert Haas <rhaas@postgresql.org>
Date: Thu, 18 Nov 2021 13:32:30 -0500
Subject: [PATCH 1/2] dubious test case

---
 src/test/recovery/t/027_tli_crosscheck.pl | 52 +++++++++++++++++++++++
 1 file changed, 52 insertions(+)
 create mode 100644 src/test/recovery/t/027_tli_crosscheck.pl

diff --git a/src/test/recovery/t/027_tli_crosscheck.pl b/src/test/recovery/t/027_tli_crosscheck.pl
new file mode 100644
index 0000000000..79ca1946fe
--- /dev/null
+++ b/src/test/recovery/t/027_tli_crosscheck.pl
@@ -0,0 +1,52 @@
+# Copyright (c) 2021, PostgreSQL Global Development Group
+
+# Test whether the appearance of a new timeline history file while a
+# standby is busy trying to read the very first checkpoint record is
+# properly handled. In this scenario, the timeline branches off before
+# the replay LSN, so the new timeline should be rejected.
+use strict;
+use warnings;
+use File::Copy;
+use FindBin;
+use PostgreSQL::Test::Cluster;
+use PostgreSQL::Test::Utils;
+use Test::More tests => 1;
+
+# initialize and start a primary node
+my $alpha = PostgreSQL::Test::Cluster->new('alpha');
+$alpha->init(allows_streaming => 1);
+$alpha->start;
+
+# create a standby, start it up, and promote it to make a second primary
+$alpha->backup('bravo_backup');
+my $bravo = PostgreSQL::Test::Cluster->new('bravo');
+$bravo->init_from_backup($alpha, 'bravo_backup', has_streaming => 1,
+						 has_archiving => 1);
+$bravo->start;
+$bravo->promote;
+
+# setup a second standby, this time with no WAL, no primary conninfo,
+# and no restore_command -- but make sure it starts as a standby all the same.
+$alpha->backup('charlie_backup', 'backup_options' => [ '-Xnone' ]);
+my $charlie = PostgreSQL::Test::Cluster->new('charlie');
+$charlie->init_from_backup($alpha, 'charlie_backup');
+$charlie->set_standby_mode();
+
+# XXX. the start() method won't think that the server has started even when it
+# has, so pretend like faillures are ok
+$charlie->start('fail_ok' => 1);
+
+# copy the timeline history file from the wrong primary to the new standby
+my $tlifilepath = '/pg_wal/00000002.history';
+copy($bravo->data_dir . $tlifilepath, $charlie->data_dir . $tlifilepath)
+	|| die "copy: $!";
+
+# XXX. wait for an amount of time that will be excessive on most buildfarm
+# machines and too short on a few, so that we get random test failures that
+# drive everybody crazy while simultaneously driving up the test runtime
+sleep(10);
+
+# check the logfile
+my $logfile = slurp_file($charlie->logfile());
+ok($logfile =~ qr/new timeline 2 forked off current database system timeline 1 before current recovery point/,
+   "timeline 2 rejected");
-- 
2.24.3 (Apple Git-128)

