From e63131b326b1d6256fb782d453649238d5f6088c Mon Sep 17 00:00:00 2001 From: =?utf8?q?P=C3=A1draig=20Brady?= Date: Fri, 21 Nov 2025 14:22:22 +0000 Subject: [PATCH] csplit,ls,sort: handle a more complete set of signals * src/term-sig.h: A new file defining a TERM_SIG array signals. * src/local.mk: Reference the new file. * src/csplit.c: Likewise. * src/sort.c: Likewise. * src/timeout.c: Likewise. * src/ls.c: Likewise. Also handle SIGTSTP separately. * NEWS: Mention the improvement. --- NEWS | 4 +++ src/csplit.c | 31 +++++------------------ src/local.mk | 1 + src/ls.c | 68 +++++++++++++++++++++----------------------------- src/sort.c | 37 +++++++-------------------- src/term-sig.h | 50 +++++++++++++++++++++++++++++++++++++ src/timeout.c | 37 +-------------------------- 7 files changed, 100 insertions(+), 128 deletions(-) create mode 100644 src/term-sig.h diff --git a/NEWS b/NEWS index 86dd62c5dd..acb3a4e187 100644 --- a/NEWS +++ b/NEWS @@ -32,6 +32,10 @@ GNU coreutils NEWS -*- outline -*- timeout(1) in a shell backgrounded job, will not terminate upon receiving SIGINT or SIGQUIT, as these are ignored by default in shell background jobs. +** Improvements + + csplit, ls, and sort, now handle a more complete set of terminating signals. + * Noteworthy changes in release 9.9 (2025-11-10) [stable] diff --git a/src/csplit.c b/src/csplit.c index 3ee89aff34..57254ef4e5 100644 --- a/src/csplit.c +++ b/src/csplit.c @@ -33,6 +33,7 @@ #include "quote.h" #include "safe-read.h" #include "stdio--.h" +#include "term-sig.h" #include "xdectoint.h" #include "xstrtol.h" @@ -1365,36 +1366,16 @@ main (int argc, char **argv) parse_patterns (argc, optind, argv); { - static int const sig[] = - { - /* The usual suspects. */ - SIGALRM, SIGHUP, SIGINT, SIGPIPE, SIGQUIT, SIGTERM, -#ifdef SIGPOLL - SIGPOLL, -#endif -#ifdef SIGPROF - SIGPROF, -#endif -#ifdef SIGVTALRM - SIGVTALRM, -#endif -#ifdef SIGXCPU - SIGXCPU, -#endif -#ifdef SIGXFSZ - SIGXFSZ, -#endif - }; - enum { nsigs = countof (sig) }; + enum { nsigs = countof (term_sig) }; struct sigaction act; sigemptyset (&caught_signals); for (int i = 0; i < nsigs; i++) { - sigaction (sig[i], nullptr, &act); + sigaction (term_sig[i], nullptr, &act); if (act.sa_handler != SIG_IGN) - sigaddset (&caught_signals, sig[i]); + sigaddset (&caught_signals, term_sig[i]); } act.sa_handler = interrupt_handler; @@ -1402,8 +1383,8 @@ main (int argc, char **argv) act.sa_flags = 0; for (int i = 0; i < nsigs; i++) - if (sigismember (&caught_signals, sig[i])) - sigaction (sig[i], &act, nullptr); + if (sigismember (&caught_signals, term_sig[i])) + sigaction (term_sig[i], &act, nullptr); } split_file (); diff --git a/src/local.mk b/src/local.mk index 5d2c379c56..49bb982071 100644 --- a/src/local.mk +++ b/src/local.mk @@ -62,6 +62,7 @@ noinst_HEADERS = \ src/statx.h \ src/system.h \ src/temp-stream.h \ + src/term-sig.h \ src/uname.h \ src/wc.h diff --git a/src/ls.c b/src/ls.c index 22d9fe9db7..5f3f597554 100644 --- a/src/ls.c +++ b/src/ls.c @@ -102,6 +102,7 @@ #include "stat-size.h" #include "stat-time.h" #include "strftime.h" +#include "term-sig.h" #include "xdectoint.h" #include "xstrtol.h" #include "xstrtol-error.h" @@ -1598,33 +1599,16 @@ static void signal_setup (bool init) { /* The signals that are trapped, and the number of such signals. */ - static int const sig[] = + static int const stop_sig[] = { /* This one is handled specially. */ SIGTSTP, - - /* The usual suspects. */ - SIGALRM, SIGHUP, SIGINT, SIGPIPE, SIGQUIT, SIGTERM, -#ifdef SIGPOLL - SIGPOLL, -#endif -#ifdef SIGPROF - SIGPROF, -#endif -#ifdef SIGVTALRM - SIGVTALRM, -#endif -#ifdef SIGXCPU - SIGXCPU, -#endif -#ifdef SIGXFSZ - SIGXFSZ, -#endif }; - enum { nsigs = countof (sig) }; + + enum { nsigs = countof (term_sig), nstop = countof (stop_sig) }; #if ! SA_NOCLDSTOP - static bool caught_sig[nsigs]; + static bool caught_sig[nsigs + nstop]; #endif if (init) @@ -1633,29 +1617,34 @@ signal_setup (bool init) struct sigaction act; sigemptyset (&caught_signals); - for (int j = 0; j < nsigs; j++) + for (int j = 0; j < nsigs + nstop; j++) { - sigaction (sig[j], nullptr, &act); + int sig = j < nsigs ? term_sig[j]: stop_sig[j - nsigs]; + sigaction (sig, nullptr, &act); if (act.sa_handler != SIG_IGN) - sigaddset (&caught_signals, sig[j]); + sigaddset (&caught_signals, sig); } act.sa_mask = caught_signals; act.sa_flags = SA_RESTART; - for (int j = 0; j < nsigs; j++) - if (sigismember (&caught_signals, sig[j])) - { - act.sa_handler = sig[j] == SIGTSTP ? stophandler : sighandler; - sigaction (sig[j], &act, nullptr); - } + for (int j = 0; j < nsigs + nstop; j++) + { + int sig = j < nsigs ? term_sig[j]: stop_sig[j - nsigs]; + if (sigismember (&caught_signals, sig)) + { + act.sa_handler = j < nsigs ? sighandler : stophandler; + sigaction (sig, &act, nullptr); + } + } #else - for (int j = 0; j < nsigs; j++) + for (int j = 0; j < nsigs + nstop; j++) { - caught_sig[j] = (signal (sig[j], SIG_IGN) != SIG_IGN); + int sig = j < nsigs ? term_sig[j]: stop_sig[j - nsigs]; + caught_sig[j] = (signal (sig, SIG_IGN) != SIG_IGN); if (caught_sig[j]) { - signal (sig[j], sig[j] == SIGTSTP ? stophandler : sighandler); + signal (sig, j < nsigs ? sighandler : stophandler); siginterrupt (sig[j], 0); } } @@ -1663,15 +1652,16 @@ signal_setup (bool init) } else /* restore. */ { + for (int j = 0; j < nsigs + nstop; j++) + { + int sig = j < nsigs ? term_sig[j]: stop_sig[j - nsigs]; #if SA_NOCLDSTOP - for (int j = 0; j < nsigs; j++) - if (sigismember (&caught_signals, sig[j])) - signal (sig[j], SIG_DFL); + if (sigismember (&caught_signals, sig)) #else - for (int j = 0; j < nsigs; j++) - if (caught_sig[j]) - signal (sig[j], SIG_DFL); + if (caught_sig[j]) #endif + signal (sig, SIG_DFL); + } } } diff --git a/src/sort.c b/src/sort.c index a74470bf8e..dee50d98c0 100644 --- a/src/sort.c +++ b/src/sort.c @@ -51,6 +51,7 @@ #include "readtokens0.h" #include "stdlib--.h" #include "strnumcmp.h" +#include "term-sig.h" #include "xmemcoll.h" #include "xnanosleep.h" #include "xstrtol.h" @@ -4447,27 +4448,7 @@ main (int argc, char **argv) inittables (); { - static int const sig[] = - { - /* The usual suspects. */ - SIGALRM, SIGHUP, SIGINT, SIGQUIT, SIGTERM, -#ifdef SIGPOLL - SIGPOLL, -#endif -#ifdef SIGPROF - SIGPROF, -#endif -#ifdef SIGVTALRM - SIGVTALRM, -#endif -#ifdef SIGXCPU - SIGXCPU, -#endif -#ifdef SIGXFSZ - SIGXFSZ, -#endif - }; - enum { nsigs = countof (sig) }; + enum { nsigs = countof (term_sig) }; #if SA_NOCLDSTOP struct sigaction act; @@ -4475,9 +4456,9 @@ main (int argc, char **argv) sigemptyset (&caught_signals); for (size_t i = 0; i < nsigs; i++) { - sigaction (sig[i], nullptr, &act); + sigaction (term_sig[i], nullptr, &act); if (act.sa_handler != SIG_IGN) - sigaddset (&caught_signals, sig[i]); + sigaddset (&caught_signals, term_sig[i]); } act.sa_handler = sighandler; @@ -4485,14 +4466,14 @@ main (int argc, char **argv) act.sa_flags = 0; for (size_t i = 0; i < nsigs; i++) - if (sigismember (&caught_signals, sig[i])) - sigaction (sig[i], &act, nullptr); + if (sigismember (&caught_signals, term_sig[i])) + sigaction (term_sig[i], &act, nullptr); #else for (size_t i = 0; i < nsigs; i++) - if (signal (sig[i], SIG_IGN) != SIG_IGN) + if (signal (term_sig[i], SIG_IGN) != SIG_IGN) { - signal (sig[i], sighandler); - siginterrupt (sig[i], 1); + signal (term_sig[i], sighandler); + siginterrupt (term_sig[i], 1); } #endif } diff --git a/src/term-sig.h b/src/term-sig.h new file mode 100644 index 0000000000..06ed0a7fdc --- /dev/null +++ b/src/term-sig.h @@ -0,0 +1,50 @@ +#ifndef TERM_SIG_H +# define TERM_SIG_H + +# include + +static int const term_sig[] = + { + SIGALRM, /* our timeout. */ + SIGINT, /* Ctrl-C at terminal for example. */ + SIGQUIT, /* Ctrl-\ at terminal for example. */ + SIGHUP, /* terminal closed for example. */ + SIGTERM, /* if terminated, stop monitored proc. */ + + SIGPIPE, SIGUSR1, SIGUSR2, + + SIGILL, SIGTRAP, SIGABRT, SIGBUS, SIGFPE, SIGSEGV, + +# ifdef SIGXCPU + SIGXCPU, +# endif +# ifdef SIGXFSZ + SIGXFSZ, +# endif +# ifdef SIGSYS + SIGSYS, +# endif +# ifdef SIGVTALRM + SIGVTALRM, +# endif +# ifdef SIGPROF + SIGPROF, +# endif +# ifdef SIGPOLL + SIGPOLL, +# endif +# ifdef SIGPWR + SIGPWR, +# endif +# ifdef SIGSTKFLT + SIGSTKFLT, +# endif +# ifdef SIGEMT + SIGEMT, +# endif +# ifdef SIGBREAK + SIGBREAK, +# endif + }; + +#endif diff --git a/src/timeout.c b/src/timeout.c index 2e770e9ff5..68ddfd5d60 100644 --- a/src/timeout.c +++ b/src/timeout.c @@ -59,6 +59,7 @@ #include "dtimespec-bound.h" #include "sig2str.h" #include "operand2sig.h" +#include "term-sig.h" #include "quote.h" #if HAVE_SETRLIMIT @@ -199,42 +200,6 @@ chld (MAYBE_UNUSED int sig) { } -static int const term_sig[] = - { - SIGALRM, /* our timeout. */ - SIGINT, /* Ctrl-C at terminal for example. */ - SIGQUIT, /* Ctrl-\ at terminal for example. */ - SIGHUP, /* terminal closed for example. */ - SIGTERM, /* if terminated, stop monitored proc. */ - - SIGPIPE, SIGUSR1, SIGUSR2, - SIGILL, SIGTRAP, SIGABRT, SIGBUS, SIGFPE, SIGSEGV, -#ifdef SIGXCPU - SIGXCPU, -#endif -#ifdef SIGXFSZ - SIGXFSZ, -#endif -#ifdef SIGSYS - SIGSYS, -#endif -#ifdef SIGVTALRM - SIGVTALRM, -#endif -#ifdef SIGPROF - SIGPROF, -#endif -#ifdef SIGPOLL - SIGPOLL, -#endif -#ifdef SIGPWR - SIGPWR, -#endif -#ifdef SIGSTKFLT - SIGSTKFLT, -#endif - }; - static void cleanup (int sig) { -- 2.47.3