From 6bd924f2e7ff90d6c293f131b8ddb20898b9950d Mon Sep 17 00:00:00 2001 From: Bharath Rupireddy Date: Fri, 24 Jul 2020 12:01:14 +0530 Subject: [PATCH v2] Fix for Parallel worker hangs while handling errors. Worker is not able to receive the signals while processing error flow. Worker hangs in this case because when the worker is started the signals will be masked using sigprocmask. Unblocking of signals is done by calling BackgroundWorkerUnblockSignals in ParallelWorkerMain. Now due to error handling the worker has jumped to setjmp in StartBackgroundWorker function. Here the signals are in blocked state, hence the signal is not received by the worker process. --- src/backend/postmaster/bgworker.c | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/src/backend/postmaster/bgworker.c b/src/backend/postmaster/bgworker.c index beb5e85434..ee187689a4 100644 --- a/src/backend/postmaster/bgworker.c +++ b/src/backend/postmaster/bgworker.c @@ -747,6 +747,20 @@ StartBackgroundWorker(void) */ if (sigsetjmp(local_sigjmp_buf, 1) != 0) { + /* + * In case of parallel workers, unblock SIGUSR1 signal, it was blocked + * when the postmaster forked us. Leader process will send SIGUSR1 signal + * to the worker process(worker process will be in waiting state as + * there is no space available) to indicate shared memory space is freed + * up. Once the signal is received worker process will start populating + * the error message further. + */ + if ((worker->bgw_flags & BGWORKER_CLASS_PARALLEL) != 0) + { + sigdelset(&BlockSig, SIGUSR1); + PG_SETMASK(&BlockSig); + } + /* Since not using PG_TRY, must reset error stack by hand */ error_context_stack = NULL; @@ -756,6 +770,18 @@ StartBackgroundWorker(void) /* Report the error to the server log */ EmitErrorReport(); + /* + * Undo the unblocking of SIGUSR1 which was done above, as to + * not cause any further issues from unblocking SIGUSR1 during + * the execution of callbacks and other processing that will be + * done during proc_exit(). + */ + if ((worker->bgw_flags & BGWORKER_CLASS_PARALLEL) != 0) + { + sigaddset(&BlockSig, SIGUSR1); + PG_SETMASK(&BlockSig); + } + /* * Do we need more cleanup here? For shmem-connected bgworkers, we * will call InitProcess below, which will install ProcKill as exit -- 2.25.1