[PATCH 1/2] mcstrans: defer SIGTERM cleanup to the main loop
Stephen Smalley <[email protected]>
| Newsgroups | org.kernel.vger.selinux |
|---|---|
| Message-ID | <[email protected]> |
sigterm_handler() calls cleanup_exit(), which walks and frees the translation and color tables and unlinks the socket. None of that is async-signal-safe; a SIGTERM arriving while the main loop is inside malloc/free or inside finish_context_translations() during a SIGHUP reload can deadlock or corrupt the heap. Set a flag from the handler and let the top of the poll loop call cleanup_exit() from normal context, matching the existing SIGHUP restart_daemon pattern. poll() is not restarted (SA_RESTART is not set) so a signal delivered during the blocking poll returns EINTR and the loop rechecks the flag. The narrow check then poll window matches the existing SIGHUP handling. Signed-off-by: Stephen Smalley <[email protected]> --- mcstrans/src/mcstransd.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/mcstrans/src/mcstransd.c b/mcstrans/src/mcstransd.c index 5bdaadb7..3db58a17 100644 --- a/mcstrans/src/mcstransd.c +++ b/mcstrans/src/mcstransd.c @@ -58,6 +58,7 @@ static int sockfd = -1; /* socket we are listening on */ static volatile sig_atomic_t restart_daemon = false; +static volatile sig_atomic_t terminate = false; static void cleanup_exit(int ret) __attribute__((noreturn)); static void cleanup_exit(int ret) { @@ -407,6 +408,10 @@ static void process_connections(void) ufds[0].revents = 0; while (1) { + if (terminate) { + free(ufds); + cleanup_exit(0); + } if (restart_daemon) { syslog(LOG_NOTICE, "Reload Translations"); finish_context_colors(); @@ -442,11 +447,9 @@ static void process_connections(void) } } -static void sigterm_handler(int sig) __attribute__((noreturn)); - static void sigterm_handler(int UNUSED(sig)) { - cleanup_exit(0); + terminate = true; } static void sighup_handler(int UNUSED(sig)) -- 2.55.0