From eee68a884d848eaf7e97e36a04192a594f88e3ad Mon Sep 17 00:00:00 2001 From: Shihao Date: Tue, 29 Sep 2026 21:27:11 -0600 Subject: [PATCH v1 2/2] Forget a statement timeout that fires after the statement is done A statement timeout can fire after the statement's last CHECK_FOR_INTERRUPTS(), for example while interrupts are held in dsm_detach() during parallel query cleanup. disable_statement_timeout() then does nothing because the timer is no longer active, so the fired indicator and the cancel request it queued stay set. The next statement fails on its first CHECK_FOR_INTERRUPTS(), even if it is a COMMIT. Clear both when the timer has fired but was not serviced. --- src/backend/tcop/postgres.c | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/src/backend/tcop/postgres.c b/src/backend/tcop/postgres.c index b6bdfe213fe..c7b0b972954 100644 --- a/src/backend/tcop/postgres.c +++ b/src/backend/tcop/postgres.c @@ -5407,4 +5407,14 @@ disable_statement_timeout(void) { if (get_timeout_active(STATEMENT_TIMEOUT)) disable_timeout(STATEMENT_TIMEOUT, false); + else if (get_timeout_indicator(STATEMENT_TIMEOUT, true)) + { + /* + * The timeout fired after the statement's last + * CHECK_FOR_INTERRUPTS(), for instance while interrupts were held + * during cleanup. The statement is over, so drop the cancel request + * it queued rather than let the next statement fail on it. + */ + QueryCancelPending = false; + } } -- 2.37.1 (Apple Git-137.1)