archiver_power.patch
text/x-patch
Filename: archiver_power.patch
Type: text/x-patch
Part: 0
Patch
Same data as JSON:
GET /api/v1/attachments/:id/patch
the parsed metadata as JSON — format, series position, per-file stats; never the diff bytes.
API reference →
Format: unified
| File | + | − |
|---|---|---|
| src/backend/postmaster/pgarch.c | 39 | 15 |
diff --git a/src/backend/postmaster/pgarch.c b/src/backend/postmaster/pgarch.c
index b40375a..01e5350 100644
--- a/src/backend/postmaster/pgarch.c
+++ b/src/backend/postmaster/pgarch.c
@@ -44,6 +44,7 @@
#include "storage/pmsignal.h"
#include "utils/guc.h"
#include "utils/ps_status.h"
+#include "storage/latch.h"
/* ----------
@@ -87,6 +88,12 @@ static volatile sig_atomic_t got_SIGTERM = false;
static volatile sig_atomic_t wakened = false;
static volatile sig_atomic_t ready_to_stop = false;
+/*
+ * Latch that archiver loop waits on until it is awakened by
+ * signals, each of which there is a handler for
+ */
+static volatile Latch mainloop_latch;
+
/* ----------
* Local function forward declarations
* ----------
@@ -228,6 +235,8 @@ PgArchiverMain(int argc, char *argv[])
MyProcPid = getpid(); /* reset MyProcPid */
+ InitLatch(&mainloop_latch); /* initialise latch used in main loop, now that we are a subprocess */
+
MyStartTime = time(NULL); /* record Start Time for logging */
/*
@@ -282,6 +291,8 @@ ArchSigHupHandler(SIGNAL_ARGS)
{
/* set flag to re-read config file at next convenient time */
got_SIGHUP = true;
+ /* Let the waiting loop iterate */
+ SetLatch(&mainloop_latch);
}
/* SIGTERM signal handler for archiver process */
@@ -295,6 +306,8 @@ ArchSigTermHandler(SIGNAL_ARGS)
* archive commands.
*/
got_SIGTERM = true;
+ /* Let the waiting loop iterate */
+ SetLatch(&mainloop_latch);
}
/* SIGUSR1 signal handler for archiver process */
@@ -303,6 +316,8 @@ pgarch_waken(SIGNAL_ARGS)
{
/* set flag that there is work to be done */
wakened = true;
+ /* Let the waiting loop iterate */
+ SetLatch(&mainloop_latch);
}
/* SIGUSR2 signal handler for archiver process */
@@ -311,6 +326,8 @@ pgarch_waken_stop(SIGNAL_ARGS)
{
/* set flag to do a final cycle and shut down afterwards */
ready_to_stop = true;
+ /* Let the waiting loop iterate */
+ SetLatch(&mainloop_latch);
}
/*
@@ -334,6 +351,13 @@ pgarch_MainLoop(void)
do
{
+ /*
+ * There shouldn't be anything for the archiver to do except to wait
+ * on a latch ... however, the archiver exists to protect our data,
+ * so she wakes up occasionally to allow herself to be proactive.
+ */
+ ResetLatch(&mainloop_latch);
+
/* When we get SIGUSR2, we do one more archive cycle, then exit */
time_to_stop = ready_to_stop;
@@ -370,28 +394,28 @@ pgarch_MainLoop(void)
last_copy_time = time(NULL);
}
- /*
- * There shouldn't be anything for the archiver to do except to wait
- * for a signal ... however, the archiver exists to protect our data,
- * so she wakes up occasionally to allow herself to be proactive.
+ /*
+ * Wait on latch, until various signals are received, or
+ * until a poll will be forced by PGARCH_AUTOWAKE_INTERVAL
+ * having passed since last_copy_time
*
- * On some platforms, signals won't interrupt the sleep. To ensure we
- * respond reasonably promptly when someone signals us, break down the
- * sleep into 1-second increments, and check for interrupts after each
- * nap.
+ * The caveat about signals invalidating the timeout of
+ * WaitLatch() on some platforms can be safely disregarded,
+ * because we handle all expected signals, and all handlers
+ * call SetLatch() where that matters anyway
*/
- while (!(wakened || ready_to_stop || got_SIGHUP ||
- !PostmasterIsAlive(true)))
- {
- time_t curtime;
- pg_usleep(1000000L);
+ if (!time_to_stop) /* Don't wait during last iteration */
+ {
+ time_t curtime = time(NULL);
+ unsigned int timeout_secs = (unsigned int) PGARCH_AUTOWAKE_INTERVAL -
+ (unsigned int) (curtime - last_copy_time);
+ WaitLatch(&mainloop_latch, timeout_secs * 1000000L);
curtime = time(NULL);
if ((unsigned int) (curtime - last_copy_time) >=
(unsigned int) PGARCH_AUTOWAKE_INTERVAL)
- wakened = true;
+ wakened = true; /* wakened by timeout - this wasn't a SIGHUP, etc */
}
-
/*
* The archiver quits either when the postmaster dies (not expected)
* or after completing one more archiving cycle after receiving