Delay checkpoint start in RecordTransactionAbortPrepared() ROLLBACK PREPARED flushes its abort record and then updates pg_xact. Nothing prevented a checkpoint from setting its redo pointer between these two steps. A crash before the removal of the 2PC state file would then cause recovery to begin after the abort record and would restore the transaction as prepared, even though its rollback has been aknowledged. Standbys could for example replay the abort record, and a follow-up COMMIT PREPARED on a primary could make them flip a transaction from aborted to committed.
Losing an abort is harmless for a regular transaction, but not for a prepared transaction whose 2PC state file is still on disk. This issue is fixed by setting DELAY_CHKPT_START (delayChkpt in v14) around the abort record and the pg_xact update, as done for COMMIT PREPARED. This issue exists since the introduction of 2PC, since d0a89683a3a4. Author: Shihao Zhong <[email protected]> Discussion: https://postgr.es/m/CAGRkXqRhpq=fd8qf_-ki1ow7b1il+o3yuhihqhlw5rujy2j...@mail.gmail.com Backpatch-through: 14 Branch ------ REL_17_STABLE Details ------- https://git.postgresql.org/pg/commitdiff/56e831ea2227b701548899db40a49af17a7ec79c Modified Files -------------- src/backend/access/transam/twophase.c | 21 +++++++++++++++++---- 1 file changed, 17 insertions(+), 4 deletions(-)
