Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
Skip to content

Commit b8bd32a

Browse files
committed
Unify SIGHUP handling between normal and walsender backends.
Because walsender and normal backends share the same main loop it's problematic to have two different flag variables, set in signal handlers, indicating a pending configuration reload. Only certain walsender commands reach code paths checking for the variable (START_[LOGICAL_]REPLICATION, CREATE_REPLICATION_SLOT ... LOGICAL, notably not base backups). This is a bug present since the introduction of walsender, but has gotten worse in releases since then which allow walsender to do more. A later patch, not slated for v10, will similarly unify SIGHUP handling in other types of processes as well. Author: Petr Jelinek, Andres Freund Reviewed-By: Michael Paquier Discussion: https://postgr.es/m/20170423235941.qosiuoyqprq4nu7v@alap3.anarazel.de Backpatch: 9.2-, bug is present since 9.0
1 parent 862204a commit b8bd32a

File tree

4 files changed

+27
-38
lines changed

4 files changed

+27
-38
lines changed

src/backend/replication/walsender.c

Lines changed: 7 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -176,7 +176,6 @@ static bool streamingDoneReceiving;
176176
static bool WalSndCaughtUp = false;
177177

178178
/* Flags set by signal handlers for later service in main loop */
179-
static volatile sig_atomic_t got_SIGHUP = false;
180179
static volatile sig_atomic_t got_SIGUSR2 = false;
181180
static volatile sig_atomic_t got_STOPPING = false;
182181

@@ -192,7 +191,6 @@ static LogicalDecodingContext *logical_decoding_ctx = NULL;
192191
static XLogRecPtr logical_startptr = InvalidXLogRecPtr;
193192

194193
/* Signal handlers */
195-
static void WalSndSigHupHandler(SIGNAL_ARGS);
196194
static void WalSndLastCycleHandler(SIGNAL_ARGS);
197195

198196
/* Prototypes for private functions */
@@ -1119,9 +1117,9 @@ WalSndWriteData(LogicalDecodingContext *ctx, XLogRecPtr lsn, TransactionId xid,
11191117
CHECK_FOR_INTERRUPTS();
11201118

11211119
/* Process any requests or signals received recently */
1122-
if (got_SIGHUP)
1120+
if (ConfigReloadPending)
11231121
{
1124-
got_SIGHUP = false;
1122+
ConfigReloadPending = false;
11251123
ProcessConfigFile(PGC_SIGHUP);
11261124
SyncRepInitConfig();
11271125
}
@@ -1202,9 +1200,9 @@ WalSndWaitForWal(XLogRecPtr loc)
12021200
CHECK_FOR_INTERRUPTS();
12031201

12041202
/* Process any requests or signals received recently */
1205-
if (got_SIGHUP)
1203+
if (ConfigReloadPending)
12061204
{
1207-
got_SIGHUP = false;
1205+
ConfigReloadPending = false;
12081206
ProcessConfigFile(PGC_SIGHUP);
12091207
SyncRepInitConfig();
12101208
}
@@ -1857,9 +1855,9 @@ WalSndLoop(WalSndSendDataCallback send_data)
18571855
CHECK_FOR_INTERRUPTS();
18581856

18591857
/* Process any requests or signals received recently */
1860-
if (got_SIGHUP)
1858+
if (ConfigReloadPending)
18611859
{
1862-
got_SIGHUP = false;
1860+
ConfigReloadPending = false;
18631861
ProcessConfigFile(PGC_SIGHUP);
18641862
SyncRepInitConfig();
18651863
}
@@ -2628,19 +2626,6 @@ HandleWalSndInitStopping(void)
26282626
got_STOPPING = true;
26292627
}
26302628

2631-
/* SIGHUP: set flag to re-read config file at next convenient time */
2632-
static void
2633-
WalSndSigHupHandler(SIGNAL_ARGS)
2634-
{
2635-
int save_errno = errno;
2636-
2637-
got_SIGHUP = true;
2638-
2639-
SetLatch(MyLatch);
2640-
2641-
errno = save_errno;
2642-
}
2643-
26442629
/*
26452630
* SIGUSR2: set flag to do a last cycle and shut down afterwards. The WAL
26462631
* sender should already have been switched to WALSNDSTATE_STOPPING at
@@ -2662,7 +2647,7 @@ void
26622647
WalSndSignals(void)
26632648
{
26642649
/* Set up signal handlers */
2665-
pqsignal(SIGHUP, WalSndSigHupHandler); /* set flag to read config
2650+
pqsignal(SIGHUP, PostgresSigHupHandler); /* set flag to read config
26662651
* file */
26672652
pqsignal(SIGINT, SIG_IGN); /* not used */
26682653
pqsignal(SIGTERM, die); /* request shutdown */

src/backend/tcop/postgres.c

Lines changed: 14 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -121,13 +121,6 @@ char *stack_base_ptr = NULL;
121121
char *register_stack_base_ptr = NULL;
122122
#endif
123123

124-
/*
125-
* Flag to mark SIGHUP. Whenever the main loop comes around it
126-
* will reread the configuration file. (Better than doing the
127-
* reading in the signal handler, ey?)
128-
*/
129-
static volatile sig_atomic_t got_SIGHUP = false;
130-
131124
/*
132125
* Flag to keep track of whether we have started a transaction.
133126
* For extended query protocol this has to be remembered across messages.
@@ -186,7 +179,6 @@ static bool IsTransactionExitStmt(Node *parsetree);
186179
static bool IsTransactionExitStmtList(List *parseTrees);
187180
static bool IsTransactionStmtList(List *parseTrees);
188181
static void drop_unnamed_stmt(void);
189-
static void SigHupHandler(SIGNAL_ARGS);
190182
static void log_disconnections(int code, Datum arg);
191183

192184

@@ -2689,13 +2681,19 @@ FloatExceptionHandler(SIGNAL_ARGS)
26892681
"invalid operation, such as division by zero.")));
26902682
}
26912683

2692-
/* SIGHUP: set flag to re-read config file at next convenient time */
2693-
static void
2694-
SigHupHandler(SIGNAL_ARGS)
2684+
/*
2685+
* SIGHUP: set flag to re-read config file at next convenient time.
2686+
*
2687+
* Sets the ConfigReloadPending flag, which should be checked at convenient
2688+
* places inside main loops. (Better than doing the reading in the signal
2689+
* handler, ey?)
2690+
*/
2691+
void
2692+
PostgresSigHupHandler(SIGNAL_ARGS)
26952693
{
26962694
int save_errno = errno;
26972695

2698-
got_SIGHUP = true;
2696+
ConfigReloadPending = true;
26992697
SetLatch(MyLatch);
27002698

27012699
errno = save_errno;
@@ -3633,8 +3631,8 @@ PostgresMain(int argc, char *argv[],
36333631
WalSndSignals();
36343632
else
36353633
{
3636-
pqsignal(SIGHUP, SigHupHandler); /* set flag to read config
3637-
* file */
3634+
pqsignal(SIGHUP, PostgresSigHupHandler); /* set flag to read config
3635+
* file */
36383636
pqsignal(SIGINT, StatementCancelHandler); /* cancel current query */
36393637
pqsignal(SIGTERM, die); /* cancel current query and exit */
36403638

@@ -4045,9 +4043,9 @@ PostgresMain(int argc, char *argv[],
40454043
* (6) check for any other interesting events that happened while we
40464044
* slept.
40474045
*/
4048-
if (got_SIGHUP)
4046+
if (ConfigReloadPending)
40494047
{
4050-
got_SIGHUP = false;
4048+
ConfigReloadPending = false;
40514049
ProcessConfigFile(PGC_SIGHUP);
40524050
}
40534051

src/backend/utils/init/globals.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ volatile bool QueryCancelPending = false;
3131
volatile bool ProcDiePending = false;
3232
volatile bool ClientConnectionLost = false;
3333
volatile bool IdleInTransactionSessionTimeoutPending = false;
34+
volatile sig_atomic_t ConfigReloadPending = false;
3435
volatile uint32 InterruptHoldoffCount = 0;
3536
volatile uint32 QueryCancelHoldoffCount = 0;
3637
volatile uint32 CritSectionCount = 0;

src/include/miscadmin.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,8 @@
2323
#ifndef MISCADMIN_H
2424
#define MISCADMIN_H
2525

26+
#include <signal.h>
27+
2628
#include "pgtime.h" /* for pg_time_t */
2729

2830

@@ -81,6 +83,7 @@ extern PGDLLIMPORT volatile bool InterruptPending;
8183
extern PGDLLIMPORT volatile bool QueryCancelPending;
8284
extern PGDLLIMPORT volatile bool ProcDiePending;
8385
extern PGDLLIMPORT volatile bool IdleInTransactionSessionTimeoutPending;
86+
extern PGDLLIMPORT volatile sig_atomic_t ConfigReloadPending;
8487

8588
extern volatile bool ClientConnectionLost;
8689

@@ -272,6 +275,8 @@ extern void restore_stack_base(pg_stack_base_t base);
272275
extern void check_stack_depth(void);
273276
extern bool stack_is_too_deep(void);
274277

278+
extern void PostgresSigHupHandler(SIGNAL_ARGS);
279+
275280
/* in tcop/utility.c */
276281
extern void PreventCommandIfReadOnly(const char *cmdname);
277282
extern void PreventCommandIfParallelMode(const char *cmdname);

0 commit comments

Comments
 (0)