postmaster: Don't repeatedly transition to crashing state
authorAndres Freund <andres@anarazel.de>
Fri, 24 Jan 2025 22:00:10 +0000 (17:00 -0500)
committerAndres Freund <andres@anarazel.de>
Fri, 24 Jan 2025 22:00:10 +0000 (17:00 -0500)
Previously HandleChildCrash() skipped logging and signalling child exits if
already in an immediate shutdown or in FatalError state, but still
transitioned server state in response to a crash. That's redundant.

In the other place we transition to FatalError, we do take care to not do so
when already in FatalError state.

To make it easier to combine different paths for entering FatalError state,
only do so once in HandleChildCrash().

Reviewed-by: Bertrand Drouvot <bertranddrouvot.pg@gmail.com>
Discussion: https://postgr.es/m/kgng5nrvnlv335evmsuvpnh354rw7qyazl73kdysev2cr2v5zu@m3cfzxicm5kp

src/backend/postmaster/postmaster.c

index ea92fb56c80a2739b1173f7380de6b31ea86bbd1..a24c0385fe6fb6d49e41c4c943b139aff586b0a4 100644 (file)
@@ -2685,8 +2685,6 @@ CleanupBackend(PMChild *bp,
 static void
 HandleChildCrash(int pid, int exitstatus, const char *procname)
 {
-   bool        take_action;
-
    /*
     * We only log messages and send signals if this is the first process
     * crash and we're not doing an immediate shutdown; otherwise, we're only
@@ -2694,15 +2692,13 @@ HandleChildCrash(int pid, int exitstatus, const char *procname)
     * signaled children, nonzero exit status is to be expected, so don't
     * clutter log.
     */
-   take_action = !FatalError && Shutdown != ImmediateShutdown;
+   if (FatalError || Shutdown == ImmediateShutdown)
+       return;
 
-   if (take_action)
-   {
-       LogChildExit(LOG, procname, pid, exitstatus);
-       ereport(LOG,
-               (errmsg("terminating any other active server processes")));
-       SetQuitSignalReason(PMQUIT_FOR_CRASH);
-   }
+   LogChildExit(LOG, procname, pid, exitstatus);
+   ereport(LOG,
+           (errmsg("terminating any other active server processes")));
+   SetQuitSignalReason(PMQUIT_FOR_CRASH);
 
    /*
     * Signal all other child processes to exit.  The crashed process has
@@ -2711,11 +2707,9 @@ HandleChildCrash(int pid, int exitstatus, const char *procname)
     * We could exclude dead-end children here, but at least when sending
     * SIGABRT it seems better to include them.
     */
-   if (take_action)
-       TerminateChildren(send_abort_for_crash ? SIGABRT : SIGQUIT);
+   TerminateChildren(send_abort_for_crash ? SIGABRT : SIGQUIT);
 
-   if (Shutdown != ImmediateShutdown)
-       FatalError = true;
+   FatalError = true;
 
    /* We now transit into a state of waiting for children to die */
    if (pmState == PM_RECOVERY ||