diff options
author | Tom Lane <tgl@sss.pgh.pa.us> | 2020-12-24 12:58:32 -0500 |
---|---|---|
committer | Tom Lane <tgl@sss.pgh.pa.us> | 2020-12-24 12:58:32 -0500 |
commit | 7e784d1dc191be24480a6b31a4ddc8e0e52be24d (patch) | |
tree | 9daab8615ef976cab2b95161793eeca6bf52eb1f /src/backend/tcop/postgres.c | |
parent | 90fbf7c57df601c7e0b43ae7cf71f0f69908a7cc (diff) | |
download | postgresql-7e784d1dc191be24480a6b31a4ddc8e0e52be24d.tar.gz postgresql-7e784d1dc191be24480a6b31a4ddc8e0e52be24d.zip |
Improve client error messages for immediate-stop situations.
Up to now, if the DBA issued "pg_ctl stop -m immediate", the message
sent to clients was the same as for a crash-and-restart situation.
This is confusing, not least because the message claims that the
database will soon be up again, something we have no business
predicting.
Improve things so that we can generate distinct messages for the two
cases (and also recognize an ad-hoc SIGQUIT, should somebody try that).
To do that, add a field to pmsignal.c's shared memory data structure
that the postmaster sets just before broadcasting SIGQUIT to its
children. No interlocking seems to be necessary; the intervening
signal-sending and signal-receipt should sufficiently serialize accesses
to the field. Hence, this isn't any riskier than the existing usages
of pmsignal.c.
We might in future extend this idea to improve other
postmaster-to-children signal scenarios, although none of them
currently seem to be as badly overloaded as SIGQUIT.
Discussion: https://postgr.es/m/559291.1608587013@sss.pgh.pa.us
Diffstat (limited to 'src/backend/tcop/postgres.c')
-rw-r--r-- | src/backend/tcop/postgres.c | 45 |
1 files changed, 32 insertions, 13 deletions
diff --git a/src/backend/tcop/postgres.c b/src/backend/tcop/postgres.c index 3679799e50a..d35c5020ea6 100644 --- a/src/backend/tcop/postgres.c +++ b/src/backend/tcop/postgres.c @@ -67,6 +67,7 @@ #include "rewrite/rewriteHandler.h" #include "storage/bufmgr.h" #include "storage/ipc.h" +#include "storage/pmsignal.h" #include "storage/proc.h" #include "storage/procsignal.h" #include "storage/sinval.h" @@ -2752,8 +2753,8 @@ drop_unnamed_stmt(void) /* * quickdie() occurs when signaled SIGQUIT by the postmaster. * - * Some backend has bought the farm, - * so we need to stop what we're doing and exit. + * Either some backend has bought the farm, or we've been told to shut down + * "immediately"; so we need to stop what we're doing and exit. */ void quickdie(SIGNAL_ARGS) @@ -2788,18 +2789,36 @@ quickdie(SIGNAL_ARGS) * wrong, so there's not much to lose. Assuming the postmaster is still * running, it will SIGKILL us soon if we get stuck for some reason. * - * Ideally this should be ereport(FATAL), but then we'd not get control - * back... + * Ideally these should be ereport(FATAL), but then we'd not get control + * back to force the correct type of process exit. */ - ereport(WARNING, - (errcode(ERRCODE_CRASH_SHUTDOWN), - errmsg("terminating connection because of crash of another server process"), - errdetail("The postmaster has commanded this server process to roll back" - " the current transaction and exit, because another" - " server process exited abnormally and possibly corrupted" - " shared memory."), - errhint("In a moment you should be able to reconnect to the" - " database and repeat your command."))); + switch (GetQuitSignalReason()) + { + case PMQUIT_NOT_SENT: + /* Hmm, SIGQUIT arrived out of the blue */ + ereport(WARNING, + (errcode(ERRCODE_ADMIN_SHUTDOWN), + errmsg("terminating connection because of unexpected SIGQUIT signal"))); + break; + case PMQUIT_FOR_CRASH: + /* A crash-and-restart cycle is in progress */ + ereport(WARNING, + (errcode(ERRCODE_CRASH_SHUTDOWN), + errmsg("terminating connection because of crash of another server process"), + errdetail("The postmaster has commanded this server process to roll back" + " the current transaction and exit, because another" + " server process exited abnormally and possibly corrupted" + " shared memory."), + errhint("In a moment you should be able to reconnect to the" + " database and repeat your command."))); + break; + case PMQUIT_FOR_STOP: + /* Immediate-mode stop */ + ereport(WARNING, + (errcode(ERRCODE_ADMIN_SHUTDOWN), + errmsg("terminating connection due to immediate shutdown command"))); + break; + } /* * We DO NOT want to run proc_exit() or atexit() callbacks -- we're here |