From 97033ba455c4c1e359835879eee2e3c690395792 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Tue, 9 Jun 2020 08:59:33 +0200 Subject: [PATCH] pager: set PR_DEATHSIG for pager to SIGINT rather than SIGTERM "less" doesn't properly reset its terminal on SIGTERM, it does so only on SIGINT. Let's thus configure SIGINT instead of SIGTERM. I think this is something less should fix too, and clean up things correctly on SIGTERM, too. However, given that we explicitly enable SIGINT behaviour by passing "K" to $LESS I figure it makes sense if we also send SIGINT instead of SIGTERM to match it. Fixes: #16084 --- src/basic/process-util.c | 4 ++-- src/basic/process-util.h | 19 ++++++++++--------- src/shared/pager.c | 3 ++- 3 files changed, 14 insertions(+), 12 deletions(-) diff --git a/src/basic/process-util.c b/src/basic/process-util.c index 8cb229ca09..f6ecc7f86f 100644 --- a/src/basic/process-util.c +++ b/src/basic/process-util.c @@ -1301,8 +1301,8 @@ int safe_fork_full( r, "Failed to rename process, ignoring: %m"); } - if (flags & FORK_DEATHSIG) - if (prctl(PR_SET_PDEATHSIG, SIGTERM) < 0) { + if (flags & (FORK_DEATHSIG|FORK_DEATHSIG_SIGINT)) + if (prctl(PR_SET_PDEATHSIG, (flags & FORK_DEATHSIG_SIGINT) ? SIGINT : SIGTERM) < 0) { log_full_errno(prio, errno, "Failed to set death signal: %m"); _exit(EXIT_FAILURE); } diff --git a/src/basic/process-util.h b/src/basic/process-util.h index ca9825293c..e0b52246ba 100644 --- a/src/basic/process-util.h +++ b/src/basic/process-util.h @@ -150,15 +150,16 @@ int must_be_root(void); typedef enum ForkFlags { FORK_RESET_SIGNALS = 1 << 0, /* Reset all signal handlers and signal mask */ FORK_CLOSE_ALL_FDS = 1 << 1, /* Close all open file descriptors in the child, except for 0,1,2 */ - FORK_DEATHSIG = 1 << 2, /* Set PR_DEATHSIG in the child */ - FORK_NULL_STDIO = 1 << 3, /* Connect 0,1,2 to /dev/null */ - FORK_REOPEN_LOG = 1 << 4, /* Reopen log connection */ - FORK_LOG = 1 << 5, /* Log above LOG_DEBUG log level about failures */ - FORK_WAIT = 1 << 6, /* Wait until child exited */ - FORK_NEW_MOUNTNS = 1 << 7, /* Run child in its own mount namespace */ - FORK_MOUNTNS_SLAVE = 1 << 8, /* Make child's mount namespace MS_SLAVE */ - FORK_RLIMIT_NOFILE_SAFE = 1 << 9, /* Set RLIMIT_NOFILE soft limit to 1K for select() compat */ - FORK_STDOUT_TO_STDERR = 1 << 10, /* Make stdout a copy of stderr */ + FORK_DEATHSIG = 1 << 2, /* Set PR_DEATHSIG in the child to SIGTERM */ + FORK_DEATHSIG_SIGINT = 1 << 3, /* Set PR_DEATHSIG in the child to SIGINT */ + FORK_NULL_STDIO = 1 << 4, /* Connect 0,1,2 to /dev/null */ + FORK_REOPEN_LOG = 1 << 5, /* Reopen log connection */ + FORK_LOG = 1 << 6, /* Log above LOG_DEBUG log level about failures */ + FORK_WAIT = 1 << 7, /* Wait until child exited */ + FORK_NEW_MOUNTNS = 1 << 8, /* Run child in its own mount namespace */ + FORK_MOUNTNS_SLAVE = 1 << 9, /* Make child's mount namespace MS_SLAVE */ + FORK_RLIMIT_NOFILE_SAFE = 1 << 10, /* Set RLIMIT_NOFILE soft limit to 1K for select() compat */ + FORK_STDOUT_TO_STDERR = 1 << 11, /* Make stdout a copy of stderr */ } ForkFlags; int safe_fork_full(const char *name, const int except_fds[], size_t n_except_fds, ForkFlags flags, pid_t *ret_pid); diff --git a/src/shared/pager.c b/src/shared/pager.c index 1fe9db1791..e03be6d23b 100644 --- a/src/shared/pager.c +++ b/src/shared/pager.c @@ -131,7 +131,8 @@ int pager_open(PagerFlags flags) { if (flags & PAGER_JUMP_TO_END) less_opts = strjoina(less_opts, " +G"); - r = safe_fork("(pager)", FORK_RESET_SIGNALS|FORK_DEATHSIG|FORK_RLIMIT_NOFILE_SAFE|FORK_LOG, &pager_pid); + /* We set SIGINT as PR_DEATHSIG signal here, to match the "K" parameter we set in $LESS, which enables SIGINT behaviour. */ + r = safe_fork("(pager)", FORK_RESET_SIGNALS|FORK_DEATHSIG_SIGINT|FORK_RLIMIT_NOFILE_SAFE|FORK_LOG, &pager_pid); if (r < 0) return r; if (r == 0) { -- 2.25.1