From: Craig Small Date: Tue, 18 Sep 2018 11:17:00 +0000 (+1000) Subject: killall: Another go at option parsing X-Git-Tag: v23.2~1 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=258ee9166e585f87005d3a9686938a4fa26669f9;p=psmisc killall: Another go at option parsing This now seems to be working. There are some evil hacks, especially for the -ve option combination but it seems that we have a winner. Added a bunch more option parsing tests which picked up -ILL passed but -VTALRM did not. Not sure why, but length seems my guess References: psmisc/psmisc#13 psmisc/psmisc#12 --- diff --git a/ChangeLog b/ChangeLog index 16f3c19..7fd2abd 100644 --- a/ChangeLog +++ b/ChangeLog @@ -5,8 +5,8 @@ Changes in 23.2 * docs: Fix fuser.1 groff errors Debian #900225 * killall: look at all namespaces by default * killall: Fix -INT option parsing #11 - * killall: change to getopt_long without _only #12 * killall: ignore -n 0 #15 + * killall: another crack at fixing getopt #12 #13 * peekfd: Attach to all threads option !15 * pslog: Define PATH_MAX if required Debian:#905797 diff --git a/src/killall.c b/src/killall.c index 64c406a..2715515 100644 --- a/src/killall.c +++ b/src/killall.c @@ -857,7 +857,7 @@ main (int argc, char **argv) opterr = 0; #ifdef WITH_SELINUX - while ( (optc = getopt_long(argc,argv,"egy:o:ilqrs:u:vwZ:VIn:",options,NULL)) != -1) { + while ( (optc = getopt_long_only(argc,argv,"egy:o:ilqrs:u:vwZ:VIn:",options,NULL)) != -1) { #else while ( (optc = getopt_long_only(argc,argv,"egy:o:ilqrs:u:vwVIn:",options,NULL)) != -1) { #endif @@ -914,7 +914,7 @@ main (int argc, char **argv) ignore_case = 1; } else { sig_num = get_signal (argv[optind]+1, "killall"); - skip_error=1; + skip_error=optind; } break; case 'V': @@ -922,8 +922,10 @@ main (int argc, char **argv) if (strcmp(argv[optind-1],"-V") == 0 || strncmp(argv[optind-1],"--",2) == 0) { print_version(); return 0; + } else { + sig_num = get_signal (argv[optind]+1, "killall"); + skip_error=optind; } - sig_num = get_signal (argv[optind]+1, "killall"); break; case 'n': { long num; @@ -948,6 +950,15 @@ main (int argc, char **argv) break; #endif /*WITH_SELINUX*/ case '?': + if (skip_error == optind) + break; + /* Sigh, this is a hack because -ve could be -version or + * -verbose */ + if (strncmp(argv[optind-1], "-ve", 3) == 0) { + verbose=1; + exact=1; + break; + } /* Signal names are in uppercase, so check to see if the argv * is upper case */ if (argv[optind-1][1] >= 'A' && argv[optind-1][1] <= 'Z') { @@ -957,9 +968,6 @@ main (int argc, char **argv) if (argv[optind-1][1] >= '0' && argv[optind-1][1] <= '9') { sig_num = atoi(argv[optind-1]+1); } else { - if (skip_error) - skip_error=0; - else usage(NULL); } } diff --git a/testsuite/killall.test/killall.exp b/testsuite/killall.test/killall.exp index b244893..8bb3889 100644 --- a/testsuite/killall.test/killall.exp +++ b/testsuite/killall.test/killall.exp @@ -17,3 +17,16 @@ set test "killall process not found" spawn $killall ${fake_proc_name} expect_pass "$test" "${fake_proc_name}: no process found" +set test "killall using -ve" +spawn $killall -ve ${fake_proc_name} +expect_pass "$test" "${fake_proc_name}: no process found" + +set signals [regexp -all -inline {\w+} [exec $killall -l]] +foreach signame $signals { + set test "killall using signal $signame" + spawn $killall -$signame ${fake_proc_name} + expect_pass "$test" "${fake_proc_name}: no process found" + set test "killall using signal SIG$signame" + spawn $killall -SIG$signame ${fake_proc_name} + expect_pass "$test" "${fake_proc_name}: no process found" +}