From 2dd50adc460e63c57eddb696f908dd6b1abfd723 Mon Sep 17 00:00:00 2001 From: Rob Landley Date: Sun, 26 Feb 2012 13:48:00 -0600 Subject: Factor out common code between killall/kill and move it to lib/lib.c, plus cleanups on kill.c. --- lib/lib.c | 51 +++++++++++++++ lib/lib.h | 5 ++ toys/kill.c | 192 ++++++++++++--------------------------------------------- toys/killall.c | 38 ------------ 4 files changed, 97 insertions(+), 189 deletions(-) diff --git a/lib/lib.c b/lib/lib.c index ba6d132d..3f04cb61 100644 --- a/lib/lib.c +++ b/lib/lib.c @@ -842,3 +842,54 @@ void for_each_pid_with_name_in(char **names, void (*callback)(pid_t pid)) closedir(dp); } + +struct signame { + int num; + char *name; +}; + +// Signals required by POSIX 2008: +// http://pubs.opengroup.org/onlinepubs/9699919799/basedefs/signal.h.html + +#define SIGNIFY(x) {SIG##x, #x} + +static struct signame signames[] = { + SIGNIFY(ABRT), SIGNIFY(ALRM), SIGNIFY(BUS), SIGNIFY(CHLD), SIGNIFY(CONT), + SIGNIFY(FPE), SIGNIFY(HUP), SIGNIFY(ILL), SIGNIFY(INT), SIGNIFY(KILL), + SIGNIFY(PIPE), SIGNIFY(QUIT), SIGNIFY(SEGV), SIGNIFY(STOP), SIGNIFY(TERM), + SIGNIFY(TSTP), SIGNIFY(TTIN), SIGNIFY(TTOU), SIGNIFY(USR1), SIGNIFY(USR2), + SIGNIFY(SYS), SIGNIFY(TRAP), SIGNIFY(URG), SIGNIFY(VTALRM), SIGNIFY(XCPU), + SIGNIFY(XFSZ) +}; + +// not in posix: SIGNIFY(STKFLT), SIGNIFY(WINCH), SIGNIFY(IO), SIGNIFY(PWR) +// obsolete: SIGNIFY(PROF) SIGNIFY(POLL) + +// Convert name to signal number. If name == NULL print names. +int sig_to_num(char *pidstr) +{ + int i; + + if (pidstr) { + char *s; + i = strtol(pidstr, &s, 10); + if (!*s) return i; + + if (!strncasecmp(pidstr, "sig", 3)) pidstr+=3; + } + for (i = 0; i < sizeof(signames)/sizeof(struct signame); i++) + if (!pidstr) xputs(signames[i].name); + else if (!strcasecmp(pidstr, signames[i].name)) + return signames[i].num; + + return -1; +} + +char *num_to_sig(int sig) +{ + int i; + + for (i=0; i=0) s = num_to_sig(signum&127); + puts(s ? s : "UNKNOWN"); + } else sig_to_num(NULL); + return; } - return -1; -} -static int send_signal(int sig, pid_t pid) -{ - if (kill(pid, sig) < 0) { - perror("kill"); - return -1; - } - return 0; -} + // signal must come before pids, so "kill -9 -1" isn't confusing. +printf("*args=%s\n", *args); -static void list_all_signals() -{ - int i = 0; - for (;;) { - printf("%s ", signals[i++].signame); - if (i % 16 == 0) - printf("\n"); - if (signals[i].signum == -1) - break; - } - printf("\n"); -} + if (!TT.signame && *args && **args=='-') TT.signame=*(args++)+1; +printf("TT.signame=%s\n", TT.signame); + if (TT.signame) { + char *arg; + int i = strtol(TT.signame, &arg, 10); + if (!*arg) arg = num_to_sig(i); + else arg = TT.signame; -static int list_signal(int signum) -{ - char *signam = signum_to_signame(signum); - if (signam) { - printf("%s\n", signam); - return 0; - } else { - printf("Unknown signal %d\n", signum); - return -1; - } -} + if (!arg || -1 == (signum = sig_to_num(arg))) + error_exit("Unknown signal '%s'", arg); + } else signum = SIGTERM; -static int list_signal_by_name(char *signame) -{ - int signum = signame_to_signum(signame); - if (signum > 0) { - printf("%d\n", signum); - return 0; - } else { - printf("Unknown signal %s\n", signame); - return -1; + if (!*args) { + toys.exithelp++; + error_exit("missing argument"); } -} -void kill_main(void) -{ - int signum = 0; - int have_signal = 0; - char *signame, *tmp; - pid_t pid; - while (*toys.optargs) { - char *arg = *(toys.optargs++); - if (arg[0] == '-' && !have_signal) { - arg++; - switch(arg[0]) { - case 'l': - if (!*toys.optargs) - list_all_signals(); - else { - signum = strtol(*(toys.optargs), &signame, 10); - if (signame == *(toys.optargs)) - list_signal_by_name(signame); - else - list_signal(signum); - } - return; - case 's': - arg = *(toys.optargs++); - default: - signum = strtol(arg, &signame, 10); - if (signame == arg) { - signum = signame_to_signum(signame); - if (signum < 0) { - toys.exitval = EXIT_FAILURE; - return; - } - } - have_signal = 1; - } - } else { - /* pids */ - pid = strtol(arg, &tmp, 10); - if (tmp == arg) { - toys.exitval = EXIT_FAILURE; - return; - } - if (send_signal(signum, pid) < 0) { - toys.exitval = EXIT_FAILURE; - return; - } - + while (*args) { + char *arg = *(args++); + + pid = strtol(arg, &tmp, 10); + if (*tmp || kill(pid, signum) < 0) { + error_msg("unknown pid '%s'", arg); + toys.exitval = EXIT_FAILURE; } } } diff --git a/toys/killall.c b/toys/killall.c index 44379833..b4e06944 100644 --- a/toys/killall.c +++ b/toys/killall.c @@ -30,44 +30,6 @@ DEFINE_GLOBALS( ) #define TT this.killall -struct signame { - int num; - char *name; -}; - -// Signals required by POSIX 2008: -// http://pubs.opengroup.org/onlinepubs/9699919799/basedefs/signal.h.html - -#define SIGNIFY(x) {SIG##x, #x} - -static struct signame signames[] = { - SIGNIFY(ABRT), SIGNIFY(ALRM), SIGNIFY(BUS), SIGNIFY(CHLD), SIGNIFY(CONT), - SIGNIFY(FPE), SIGNIFY(HUP), SIGNIFY(ILL), SIGNIFY(INT), SIGNIFY(KILL), - SIGNIFY(PIPE), SIGNIFY(QUIT), SIGNIFY(SEGV), SIGNIFY(STOP), SIGNIFY(TERM), - SIGNIFY(TSTP), SIGNIFY(TTIN), SIGNIFY(TTOU), SIGNIFY(USR1), SIGNIFY(USR2), - SIGNIFY(SYS), SIGNIFY(TRAP), SIGNIFY(URG), SIGNIFY(VTALRM), SIGNIFY(XCPU), - SIGNIFY(XFSZ) -}; - -// SIGNIFY(STKFLT), SIGNIFY(WINCH), SIGNIFY(IO), SIGNIFY(PWR) - -// Convert name to signal number. If name == NULL print names. -static int sig_to_num(char *pidstr) -{ - int i; - - if (pidstr) { - if (isdigit(*pidstr)) return atol(pidstr); - if (!strncasecmp(pidstr, "sig", 3)) pidstr+=3; - } - for (i = 0; i < sizeof(signames)/sizeof(struct signame); i++) - if (!pidstr) xputs(signames[i].name); - else if (!strcasecmp(pidstr, signames[i].name)) - return signames[i].num; - - return -1; -} - static void kill_process(pid_t pid) { int ret; -- cgit v1.2.3