@@ -417,26 +417,12 @@ static void TerminateChildren(int signal);
417417
418418static int CountChildren (int target );
419419static Backend * assign_backendlist_entry (void );
420+ static void LaunchMissingBackgroundProcesses (void );
420421static void maybe_start_bgworkers (void );
421422static bool CreateOptsFile (int argc , char * argv [], char * fullprogname );
422423static pid_t StartChildProcess (BackendType type );
423424static void StartAutovacuumWorker (void );
424- static void MaybeStartWalReceiver (void );
425- static void MaybeStartWalSummarizer (void );
426425static void InitPostmasterDeathWatchHandle (void );
427- static void MaybeStartSlotSyncWorker (void );
428-
429- /*
430- * Archiver is allowed to start up at the current postmaster state?
431- *
432- * If WAL archiving is enabled always, we are allowed to start archiver
433- * even during recovery.
434- */
435- #define PgArchStartupAllowed () \
436- (((XLogArchivingActive() && pmState == PM_RUN) || \
437- (XLogArchivingAlways() && \
438- (pmState == PM_RECOVERY || pmState == PM_HOT_STANDBY))) && \
439- PgArchCanRestart())
440426
441427#ifdef WIN32
442428#define WNOHANG 0 /* ignored, so any integer value will do */
@@ -1670,53 +1656,11 @@ ServerLoop(void)
16701656 }
16711657 }
16721658
1673- /* If we have lost the log collector, try to start a new one */
1674- if (SysLoggerPID == 0 && Logging_collector )
1675- SysLoggerPID = SysLogger_Start ();
1676-
1677- /*
1678- * If no background writer process is running, and we are not in a
1679- * state that prevents it, start one. It doesn't matter if this
1680- * fails, we'll just try again later. Likewise for the checkpointer.
1681- */
1682- if (pmState == PM_RUN || pmState == PM_RECOVERY ||
1683- pmState == PM_HOT_STANDBY || pmState == PM_STARTUP )
1684- {
1685- if (CheckpointerPID == 0 )
1686- CheckpointerPID = StartChildProcess (B_CHECKPOINTER );
1687- if (BgWriterPID == 0 )
1688- BgWriterPID = StartChildProcess (B_BG_WRITER );
1689- }
1690-
16911659 /*
1692- * Likewise, if we have lost the walwriter process, try to start a new
1693- * one. But this is needed only in normal operation (else we cannot
1694- * be writing any new WAL).
1660+ * If we need to launch any background processes after changing state
1661+ * or because some exited, do so now.
16951662 */
1696- if (WalWriterPID == 0 && pmState == PM_RUN )
1697- WalWriterPID = StartChildProcess (B_WAL_WRITER );
1698-
1699- /*
1700- * If we have lost the autovacuum launcher, try to start a new one. We
1701- * don't want autovacuum to run in binary upgrade mode because
1702- * autovacuum might update relfrozenxid for empty tables before the
1703- * physical files are put in place.
1704- */
1705- if (!IsBinaryUpgrade && AutoVacPID == 0 &&
1706- (AutoVacuumingActive () || start_autovac_launcher ) &&
1707- pmState == PM_RUN )
1708- {
1709- AutoVacPID = StartChildProcess (B_AUTOVAC_LAUNCHER );
1710- if (AutoVacPID != 0 )
1711- start_autovac_launcher = false; /* signal processed */
1712- }
1713-
1714- /* If we have lost the archiver, try to start a new one. */
1715- if (PgArchPID == 0 && PgArchStartupAllowed ())
1716- PgArchPID = StartChildProcess (B_ARCHIVER );
1717-
1718- /* If we need to start a slot sync worker, try to do that now */
1719- MaybeStartSlotSyncWorker ();
1663+ LaunchMissingBackgroundProcesses ();
17201664
17211665 /* If we need to signal the autovacuum launcher, do so now */
17221666 if (avlauncher_needs_signal )
@@ -1726,17 +1670,6 @@ ServerLoop(void)
17261670 kill (AutoVacPID , SIGUSR2 );
17271671 }
17281672
1729- /* If we need to start a WAL receiver, try to do that now */
1730- if (WalReceiverRequested )
1731- MaybeStartWalReceiver ();
1732-
1733- /* If we need to start a WAL summarizer, try to do that now */
1734- MaybeStartWalSummarizer ();
1735-
1736- /* Get other worker processes running, if needed */
1737- if (StartWorkerNeeded || HaveCrashedWorker )
1738- maybe_start_bgworkers ();
1739-
17401673#ifdef HAVE_PTHREAD_IS_THREADED_NP
17411674
17421675 /*
@@ -2386,23 +2319,11 @@ process_pm_child_exit(void)
23862319 connsAllowed = true;
23872320
23882321 /*
2389- * Crank up any background tasks that we didn't start earlier
2390- * already. It doesn't matter if any of these fail, we'll just
2391- * try again later .
2322+ * At the next iteration of the postmaster's main loop, we will
2323+ * crank up the background tasks like the autovacuum launcher and
2324+ * background workers that were not started earlier already .
23922325 */
2393- if (CheckpointerPID == 0 )
2394- CheckpointerPID = StartChildProcess (B_CHECKPOINTER );
2395- if (BgWriterPID == 0 )
2396- BgWriterPID = StartChildProcess (B_BG_WRITER );
2397- if (WalWriterPID == 0 )
2398- WalWriterPID = StartChildProcess (B_WAL_WRITER );
2399- MaybeStartWalSummarizer ();
2400- if (!IsBinaryUpgrade && AutoVacuumingActive () && AutoVacPID == 0 )
2401- AutoVacPID = StartChildProcess (B_AUTOVAC_LAUNCHER );
2402- if (PgArchStartupAllowed () && PgArchPID == 0 )
2403- PgArchPID = StartChildProcess (B_ARCHIVER );
2404- MaybeStartSlotSyncWorker ();
2405- maybe_start_bgworkers ();
2326+ StartWorkerNeeded = true;
24062327
24072328 /* at this point we are really open for business */
24082329 ereport (LOG ,
@@ -2541,20 +2462,15 @@ process_pm_child_exit(void)
25412462 /*
25422463 * Was it the archiver? If exit status is zero (normal) or one (FATAL
25432464 * exit), we assume everything is all right just like normal backends
2544- * and just try to restart a new one so that we immediately retry
2545- * archiving remaining files. (If fail, we'll try again in future
2546- * cycles of the postmaster's main loop.) Unless we were waiting for
2547- * it to shut down; don't restart it in that case, and
2548- * PostmasterStateMachine() will advance to the next shutdown step.
2465+ * and just try to start a new one on the next cycle of the
2466+ * postmaster's main loop, to retry archiving remaining files.
25492467 */
25502468 if (pid == PgArchPID )
25512469 {
25522470 PgArchPID = 0 ;
25532471 if (!EXIT_STATUS_0 (exitstatus ) && !EXIT_STATUS_1 (exitstatus ))
25542472 HandleChildCrash (pid , exitstatus ,
25552473 _ ("archiver process" ));
2556- if (PgArchStartupAllowed ())
2557- PgArchPID = StartChildProcess (B_ARCHIVER );
25582474 continue ;
25592475 }
25602476
@@ -3207,6 +3123,118 @@ PostmasterStateMachine(void)
32073123 }
32083124}
32093125
3126+ /*
3127+ * Launch background processes after state change, or relaunch after an
3128+ * existing process has exited.
3129+ *
3130+ * Check the current pmState and the status of any background processes. If
3131+ * there are any background processes missing that should be running in the
3132+ * current state, but are not, launch them.
3133+ */
3134+ static void
3135+ LaunchMissingBackgroundProcesses (void )
3136+ {
3137+ /* Syslogger is active in all states */
3138+ if (SysLoggerPID == 0 && Logging_collector )
3139+ SysLoggerPID = SysLogger_Start ();
3140+
3141+ /*
3142+ * The checkpointer and the background writer are active from the start,
3143+ * until shutdown is initiated.
3144+ *
3145+ * (If the checkpointer is not running when we enter the the PM_SHUTDOWN
3146+ * state, it is launched one more time to perform the shutdown checkpoint.
3147+ * That's done in PostmasterStateMachine(), not here.)
3148+ */
3149+ if (pmState == PM_RUN || pmState == PM_RECOVERY ||
3150+ pmState == PM_HOT_STANDBY || pmState == PM_STARTUP )
3151+ {
3152+ if (CheckpointerPID == 0 )
3153+ CheckpointerPID = StartChildProcess (B_CHECKPOINTER );
3154+ if (BgWriterPID == 0 )
3155+ BgWriterPID = StartChildProcess (B_BG_WRITER );
3156+ }
3157+
3158+ /*
3159+ * WAL writer is needed only in normal operation (else we cannot be
3160+ * writing any new WAL).
3161+ */
3162+ if (WalWriterPID == 0 && pmState == PM_RUN )
3163+ WalWriterPID = StartChildProcess (B_WAL_WRITER );
3164+
3165+ /*
3166+ * We don't want autovacuum to run in binary upgrade mode because
3167+ * autovacuum might update relfrozenxid for empty tables before the
3168+ * physical files are put in place.
3169+ */
3170+ if (!IsBinaryUpgrade && AutoVacPID == 0 &&
3171+ (AutoVacuumingActive () || start_autovac_launcher ) &&
3172+ pmState == PM_RUN )
3173+ {
3174+ AutoVacPID = StartChildProcess (B_AUTOVAC_LAUNCHER );
3175+ if (AutoVacPID != 0 )
3176+ start_autovac_launcher = false; /* signal processed */
3177+ }
3178+
3179+ /*
3180+ * If WAL archiving is enabled always, we are allowed to start archiver
3181+ * even during recovery.
3182+ */
3183+ if (PgArchPID == 0 &&
3184+ ((XLogArchivingActive () && pmState == PM_RUN ) ||
3185+ (XLogArchivingAlways () && (pmState == PM_RECOVERY || pmState == PM_HOT_STANDBY ))) &&
3186+ PgArchCanRestart ())
3187+ PgArchPID = StartChildProcess (B_ARCHIVER );
3188+
3189+ /*
3190+ * If we need to start a slot sync worker, try to do that now
3191+ *
3192+ * We allow to start the slot sync worker when we are on a hot standby,
3193+ * fast or immediate shutdown is not in progress, slot sync parameters are
3194+ * configured correctly, and it is the first time of worker's launch, or
3195+ * enough time has passed since the worker was launched last.
3196+ */
3197+ if (SlotSyncWorkerPID == 0 && pmState == PM_HOT_STANDBY &&
3198+ Shutdown <= SmartShutdown && sync_replication_slots &&
3199+ ValidateSlotSyncParams (LOG ) && SlotSyncWorkerCanRestart ())
3200+ SlotSyncWorkerPID = StartChildProcess (B_SLOTSYNC_WORKER );
3201+
3202+ /*
3203+ * If we need to start a WAL receiver, try to do that now
3204+ *
3205+ * Note: if WalReceiverPID is already nonzero, it might seem that we
3206+ * should clear WalReceiverRequested. However, there's a race condition
3207+ * if the walreceiver terminates and the startup process immediately
3208+ * requests a new one: it's quite possible to get the signal for the
3209+ * request before reaping the dead walreceiver process. Better to risk
3210+ * launching an extra walreceiver than to miss launching one we need. (The
3211+ * walreceiver code has logic to recognize that it should go away if not
3212+ * needed.)
3213+ */
3214+ if (WalReceiverRequested )
3215+ {
3216+ if (WalReceiverPID == 0 &&
3217+ (pmState == PM_STARTUP || pmState == PM_RECOVERY ||
3218+ pmState == PM_HOT_STANDBY ) &&
3219+ Shutdown <= SmartShutdown )
3220+ {
3221+ WalReceiverPID = StartChildProcess (B_WAL_RECEIVER );
3222+ if (WalReceiverPID != 0 )
3223+ WalReceiverRequested = false;
3224+ /* else leave the flag set, so we'll try again later */
3225+ }
3226+ }
3227+
3228+ /* If we need to start a WAL summarizer, try to do that now */
3229+ if (summarize_wal && WalSummarizerPID == 0 &&
3230+ (pmState == PM_RUN || pmState == PM_HOT_STANDBY ) &&
3231+ Shutdown <= SmartShutdown )
3232+ WalSummarizerPID = StartChildProcess (B_WAL_SUMMARIZER );
3233+
3234+ /* Get other worker processes running, if needed */
3235+ if (StartWorkerNeeded || HaveCrashedWorker )
3236+ maybe_start_bgworkers ();
3237+ }
32103238
32113239/*
32123240 * Send a signal to a postmaster child process
@@ -3558,9 +3586,6 @@ process_pm_pmsignal(void)
35583586 StartWorkerNeeded = true;
35593587 }
35603588
3561- if (StartWorkerNeeded || HaveCrashedWorker )
3562- maybe_start_bgworkers ();
3563-
35643589 /* Tell syslogger to rotate logfile if requested */
35653590 if (SysLoggerPID != 0 )
35663591 {
@@ -3600,9 +3625,7 @@ process_pm_pmsignal(void)
36003625 if (CheckPostmasterSignal (PMSIGNAL_START_WALRECEIVER ))
36013626 {
36023627 /* Startup Process wants us to start the walreceiver process. */
3603- /* Start immediately if possible, else remember request for later. */
36043628 WalReceiverRequested = true;
3605- MaybeStartWalReceiver ();
36063629 }
36073630
36083631 /*
@@ -3796,64 +3819,6 @@ StartAutovacuumWorker(void)
37963819 }
37973820}
37983821
3799- /*
3800- * MaybeStartWalReceiver
3801- * Start the WAL receiver process, if not running and our state allows.
3802- *
3803- * Note: if WalReceiverPID is already nonzero, it might seem that we should
3804- * clear WalReceiverRequested. However, there's a race condition if the
3805- * walreceiver terminates and the startup process immediately requests a new
3806- * one: it's quite possible to get the signal for the request before reaping
3807- * the dead walreceiver process. Better to risk launching an extra
3808- * walreceiver than to miss launching one we need. (The walreceiver code
3809- * has logic to recognize that it should go away if not needed.)
3810- */
3811- static void
3812- MaybeStartWalReceiver (void )
3813- {
3814- if (WalReceiverPID == 0 &&
3815- (pmState == PM_STARTUP || pmState == PM_RECOVERY ||
3816- pmState == PM_HOT_STANDBY ) &&
3817- Shutdown <= SmartShutdown )
3818- {
3819- WalReceiverPID = StartChildProcess (B_WAL_RECEIVER );
3820- if (WalReceiverPID != 0 )
3821- WalReceiverRequested = false;
3822- /* else leave the flag set, so we'll try again later */
3823- }
3824- }
3825-
3826- /*
3827- * MaybeStartWalSummarizer
3828- * Start the WAL summarizer process, if not running and our state allows.
3829- */
3830- static void
3831- MaybeStartWalSummarizer (void )
3832- {
3833- if (summarize_wal && WalSummarizerPID == 0 &&
3834- (pmState == PM_RUN || pmState == PM_HOT_STANDBY ) &&
3835- Shutdown <= SmartShutdown )
3836- WalSummarizerPID = StartChildProcess (B_WAL_SUMMARIZER );
3837- }
3838-
3839-
3840- /*
3841- * MaybeStartSlotSyncWorker
3842- * Start the slot sync worker, if not running and our state allows.
3843- *
3844- * We allow to start the slot sync worker when we are on a hot standby,
3845- * fast or immediate shutdown is not in progress, slot sync parameters
3846- * are configured correctly, and it is the first time of worker's launch,
3847- * or enough time has passed since the worker was launched last.
3848- */
3849- static void
3850- MaybeStartSlotSyncWorker (void )
3851- {
3852- if (SlotSyncWorkerPID == 0 && pmState == PM_HOT_STANDBY &&
3853- Shutdown <= SmartShutdown && sync_replication_slots &&
3854- ValidateSlotSyncParams (LOG ) && SlotSyncWorkerCanRestart ())
3855- SlotSyncWorkerPID = StartChildProcess (B_SLOTSYNC_WORKER );
3856- }
38573822
38583823/*
38593824 * Create the opts file
0 commit comments