Re: avoid multiple hard links to same WAL file after a crash
Michael Paquier <michael@paquier.xyz>
On Wed, Apr 27, 2022 at 11:42:04AM -0700, Nathan Bossart wrote: > Here is a new patch set with these assertions added. I think at least the > xlog.c change ought to be back-patched. The problem may be unlikely, but > AFAICT the possible consequences include WAL corruption. Okay, so I have applied this stuff this morning to see what the buildfarm had to say, and we have finished with a set of failures in various buildfarm members: https://buildfarm.postgresql.org/cgi-bin/show_log.pl?nm=kestrel&dt=2022-04-28%2002%3A13%3A27 https://buildfarm.postgresql.org/cgi-bin/show_log.pl?nm=rorqual&dt=2022-04-28%2002%3A14%3A08 https://buildfarm.postgresql.org/cgi-bin/show_log.pl?nm=calliphoridae&dt=2022-04-28%2002%3A59%3A26 All of them did not like the part where we assume that a TLI history file written by a WAL receiver should not exist beforehand, but as 025_stuck_on_old_timeline.pl is showing, a standby may attempt to retrieve a TLI history file after getting it from the archives. I was analyzing the whole thing, and it looks like a race condition. Per the the buildfarm logs, we have less than 5ms between the moment the startup process retrieves the history file of TLI 2 from the archives and the moment the WAL receiver decides to check if this TLI file exists. If it does not exist, it would then retrieve it from the primary via streaming. So I guess that the sequence of events is that: - In WalRcvFetchTimeLineHistoryFiles(), the WAL receiver checks the existence of the history file for TLI 2, does not find it. - The startup process retrieves the file from the archives. - The WAL receiver goes through the internal loop of WalRcvFetchTimeLineHistoryFiles(), retrieves the history file from the primary's stream. Switching from durable_rename_excl() to durable_rename() would mean that we'd overwrite the TLI file received from the primary stream over what's been retrieved from the archives. That does not strike me as an issue in itself and that should be safe, so the comment is misleading, and we can live without the assertion in writeTimeLineHistoryFile() called by the WAL receiver. Now, I think that we'd better keep some belts in writeTimeLineHistory() called by the startup process at the end-of-recovery as I should never ever have a TLI file generated when selecting a new timeline. Perhaps this should be a elog(ERROR) at least, with a check on the file existence before calling durable_rename()? Anyway, my time is constrained next week due to the upcoming Japanese Golden Week and the buildfarm has to be stable, so I have reverted the change for now. -- Michael
Commits
-
Test restartpoints in archive recovery.
- 4399d1055627 13.21 landed
- 41ffd9d6a724 14.18 landed
- e297ddcfb7d3 17.5 landed
- 91168a9ae38d 15.13 landed
- 4664de1826a8 16.9 landed
- 714bd9e3a733 18.0 landed
-
Reset InstallXLogFileSegmentActive after walreceiver self-initiated exit.
- 69a498eb6465 13.21 landed
- 3635a0a35aaf 14.18 landed
-
Skip WAL recycling and preallocation during archive recovery.
- a5b0c06daae9 13.21 landed
- 014a508009df 14.18 landed
- cc2c7d65fc27 15.0 cited
-
Don't ERROR on PreallocXlogFiles() race condition.
- cbed472a9341 13.21 landed
- 675b771ca5f2 14.18 landed
-
Revert "Add HINT for restartpoint race with KeepFileRestoredFromArchive()."
- e77d9cd4f52e 13.21 landed
- 47d2d2982729 14.18 landed
-
Remove XLogFileInit() ability to unlink a pre-existing file.
- d0b6acaf04a2 13.21 landed
- b494640e8297 14.18 landed
-
In XLogFileInit(), fix *use_existent postcondition to suit callers.
- 20e5ef3ca70c 13.21 landed
- 8967dddf086e 14.18 landed
-
Remove XLogFileInit() ability to skip ControlFileLock.
- df8ec9634ccd 13.21 landed
- 6b168c1299c5 14.18 landed
-
Replace durable_rename_excl() by durable_rename(), take two
- 26a79cbbdace 13.19 landed
- 1f95181b44c8 14.16 landed
- c1c9df3159cf 15.11 landed
- dac1ff30906b 16.0 landed
-
Add HINT for restartpoint race with KeepFileRestoredFromArchive().
- 8ad6c5dbbe5a 14.5 cited
-
Remove durable_rename_excl()
- eb64ceac7ec3 16.0 landed
- 2c902bbf1911 15.0 landed
-
Replace existing durable_rename_excl() calls with durable_rename()
- ccfbd9287d70 15.0 landed