diff options
Diffstat (limited to 'libbb/u_signal_names.c')
-rw-r--r-- | libbb/u_signal_names.c | 200 |
1 files changed, 40 insertions, 160 deletions
diff --git a/libbb/u_signal_names.c b/libbb/u_signal_names.c index bf65fa3e9..62fab810d 100644 --- a/libbb/u_signal_names.c +++ b/libbb/u_signal_names.c | |||
@@ -1,179 +1,59 @@ | |||
1 | /* vi: set sw=4 ts=4: */ | 1 | /* vi: set sw=4 ts=4: */ |
2 | /* | 2 | /* |
3 | * Utility routines. | 3 | * Signal name/number conversion routines. |
4 | * | 4 | * |
5 | * Copyright (C) many different people. | 5 | * Copyright 2006 Rob Landley <rob@landley.net> |
6 | * If you wrote this, please acknowledge your work. | ||
7 | * | 6 | * |
8 | * Licensed under GPLv2 or later, see file LICENSE in this tarball for details. | 7 | * Licensed under GPLv2 or later, see file LICENSE in this tarball for details. |
9 | */ | 8 | */ |
10 | 9 | ||
11 | #include <signal.h> | ||
12 | #include <ctype.h> | ||
13 | #include <string.h> | ||
14 | #include <strings.h> | ||
15 | #include <stdlib.h> | ||
16 | #include <stdio.h> | ||
17 | |||
18 | #include "libbb.h" | 10 | #include "libbb.h" |
19 | 11 | ||
20 | struct signal_name { | 12 | static struct signal_name { |
21 | const char *name; | 13 | char *name; |
22 | int number; | 14 | int number; |
15 | } signals[] = { | ||
16 | // SUSv3 says kill must support these, and specifies the numerical values, | ||
17 | // http://www.opengroup.org/onlinepubs/009695399/utilities/kill.html | ||
18 | {"0", 0}, {"HUP", 1}, {"INT", 2}, {"QUIT", 3}, {"ABRT", 6}, {"KILL", 9}, | ||
19 | {"ALRM", 14}, {"TERM", 15}, | ||
20 | // And Posix adds the following: | ||
21 | {"ILL", SIGILL}, {"TRAP", SIGTRAP}, {"FPE", SIGFPE}, {"USR1", SIGUSR1}, | ||
22 | {"SEGV", SIGSEGV}, {"USR2", SIGUSR2}, {"PIPE", SIGPIPE}, {"CHLD", SIGCHLD}, | ||
23 | {"CONT", SIGCONT}, {"STOP", SIGSTOP}, {"TSTP", SIGTSTP}, {"TTIN", SIGTTIN}, | ||
24 | {"TTOU", SIGTTOU} | ||
23 | }; | 25 | }; |
24 | 26 | ||
25 | static const struct signal_name signames[] = { | 27 | // Convert signal name to number. |
26 | /* POSIX signals */ | ||
27 | { "EXIT", 0 }, /* 0 */ | ||
28 | { "HUP", SIGHUP }, /* 1 */ | ||
29 | { "INT", SIGINT }, /* 2 */ | ||
30 | { "QUIT", SIGQUIT }, /* 3 */ | ||
31 | { "ILL", SIGILL }, /* 4 */ | ||
32 | { "ABRT", SIGABRT }, /* 6 */ | ||
33 | { "FPE", SIGFPE }, /* 8 */ | ||
34 | { "KILL", SIGKILL }, /* 9 */ | ||
35 | { "SEGV", SIGSEGV }, /* 11 */ | ||
36 | { "PIPE", SIGPIPE }, /* 13 */ | ||
37 | { "ALRM", SIGALRM }, /* 14 */ | ||
38 | { "TERM", SIGTERM }, /* 15 */ | ||
39 | { "USR1", SIGUSR1 }, /* 10 (arm,i386,m68k,ppc), 30 (alpha,sparc*), 16 (mips) */ | ||
40 | { "USR2", SIGUSR2 }, /* 12 (arm,i386,m68k,ppc), 31 (alpha,sparc*), 17 (mips) */ | ||
41 | { "CHLD", SIGCHLD }, /* 17 (arm,i386,m68k,ppc), 20 (alpha,sparc*), 18 (mips) */ | ||
42 | { "CONT", SIGCONT }, /* 18 (arm,i386,m68k,ppc), 19 (alpha,sparc*), 25 (mips) */ | ||
43 | { "STOP", SIGSTOP }, /* 19 (arm,i386,m68k,ppc), 17 (alpha,sparc*), 23 (mips) */ | ||
44 | { "TSTP", SIGTSTP }, /* 20 (arm,i386,m68k,ppc), 18 (alpha,sparc*), 24 (mips) */ | ||
45 | { "TTIN", SIGTTIN }, /* 21 (arm,i386,m68k,ppc,alpha,sparc*), 26 (mips) */ | ||
46 | { "TTOU", SIGTTOU }, /* 22 (arm,i386,m68k,ppc,alpha,sparc*), 27 (mips) */ | ||
47 | /* Miscellaneous other signals */ | ||
48 | #ifdef SIGTRAP | ||
49 | { "TRAP", SIGTRAP }, /* 5 */ | ||
50 | #endif | ||
51 | #ifdef SIGIOT | ||
52 | { "IOT", SIGIOT }, /* 6, same as SIGABRT */ | ||
53 | #endif | ||
54 | #ifdef SIGEMT | ||
55 | { "EMT", SIGEMT }, /* 7 (mips,alpha,sparc*) */ | ||
56 | #endif | ||
57 | #ifdef SIGBUS | ||
58 | { "BUS", SIGBUS }, /* 7 (arm,i386,m68k,ppc), 10 (mips,alpha,sparc*) */ | ||
59 | #endif | ||
60 | #ifdef SIGSYS | ||
61 | { "SYS", SIGSYS }, /* 12 (mips,alpha,sparc*) */ | ||
62 | #endif | ||
63 | #ifdef SIGSTKFLT | ||
64 | { "STKFLT", SIGSTKFLT }, /* 16 (arm,i386,m68k,ppc) */ | ||
65 | #endif | ||
66 | #ifdef SIGURG | ||
67 | { "URG", SIGURG }, /* 23 (arm,i386,m68k,ppc), 16 (alpha,sparc*), 21 (mips) */ | ||
68 | #endif | ||
69 | #ifdef SIGIO | ||
70 | { "IO", SIGIO }, /* 29 (arm,i386,m68k,ppc), 23 (alpha,sparc*), 22 (mips) */ | ||
71 | #endif | ||
72 | #ifdef SIGPOLL | ||
73 | { "POLL", SIGPOLL }, /* same as SIGIO */ | ||
74 | #endif | ||
75 | #ifdef SIGCLD | ||
76 | { "CLD", SIGCLD }, /* same as SIGCHLD (mips) */ | ||
77 | #endif | ||
78 | #ifdef SIGXCPU | ||
79 | { "XCPU", SIGXCPU }, /* 24 (arm,i386,m68k,ppc,alpha,sparc*), 30 (mips) */ | ||
80 | #endif | ||
81 | #ifdef SIGXFSZ | ||
82 | { "XFSZ", SIGXFSZ }, /* 25 (arm,i386,m68k,ppc,alpha,sparc*), 31 (mips) */ | ||
83 | #endif | ||
84 | #ifdef SIGVTALRM | ||
85 | { "VTALRM", SIGVTALRM }, /* 26 (arm,i386,m68k,ppc,alpha,sparc*), 28 (mips) */ | ||
86 | #endif | ||
87 | #ifdef SIGPROF | ||
88 | { "PROF", SIGPROF }, /* 27 (arm,i386,m68k,ppc,alpha,sparc*), 29 (mips) */ | ||
89 | #endif | ||
90 | #ifdef SIGPWR | ||
91 | { "PWR", SIGPWR }, /* 30 (arm,i386,m68k,ppc), 29 (alpha,sparc*), 19 (mips) */ | ||
92 | #endif | ||
93 | #ifdef SIGINFO | ||
94 | { "INFO", SIGINFO }, /* 29 (alpha) */ | ||
95 | #endif | ||
96 | #ifdef SIGLOST | ||
97 | { "LOST", SIGLOST }, /* 29 (arm,i386,m68k,ppc,sparc*) */ | ||
98 | #endif | ||
99 | #ifdef SIGWINCH | ||
100 | { "WINCH", SIGWINCH }, /* 28 (arm,i386,m68k,ppc,alpha,sparc*), 20 (mips) */ | ||
101 | #endif | ||
102 | #ifdef SIGUNUSED | ||
103 | { "UNUSED", SIGUNUSED }, /* 31 (arm,i386,m68k,ppc) */ | ||
104 | #endif | ||
105 | {0, 0} | ||
106 | }; | ||
107 | 28 | ||
108 | /* | 29 | int get_signum(char *name) |
109 | if str_sig == NULL returned signal name [*signo], | 30 | { |
110 | if str_sig != NULL - set *signo from signal_name, | 31 | int i; |
111 | findings with digit number or with or without SIG-prefix name | 32 | |
112 | 33 | i = atoi(name); | |
113 | if startnum=0 flag for support finding zero signal, | 34 | if(i) return i; |
114 | but str_sig="0" always found, (hmm - standart or realize?) | 35 | for(i=0; i < sizeof(signals) / sizeof(struct signal_name); i++) |
115 | if startnum<0 returned reverse signal_number <-> signal_name | 36 | if (!strcasecmp(signals[i].name, name) || |
116 | if found error - returned NULL | 37 | (!strncasecmp(signals[i].name, "SIG", 3) |
38 | && !strcasecmp(signals[i].name+3, signals[i].name))) | ||
39 | return signals[i].number; | ||
40 | return -1; | ||
41 | } | ||
117 | 42 | ||
118 | */ | 43 | // Convert signal number to name |
119 | 44 | ||
120 | const char * | 45 | char *get_signame(int number) |
121 | u_signal_names(const char *str_sig, int *signo, int startnum) | ||
122 | { | 46 | { |
123 | static char retstr[16]; | 47 | int i; |
124 | const struct signal_name *s = signames; | 48 | static char buf[8]; |
125 | static const char prefix[] = "SIG"; | 49 | |
126 | const char *sptr; | 50 | itoa_to_buf(number, buf, 8); |
127 | 51 | for (i=0; i < sizeof(signals) / sizeof(struct signal_name); i++) { | |
128 | if(startnum) | 52 | if (number == signals[i].number) { |
129 | s++; | 53 | sprintf("SIG%s", signals[i].name); |
130 | if(str_sig==NULL) { | 54 | break; |
131 | while (s->name != 0) { | ||
132 | if(s->number == *signo) | ||
133 | break; | ||
134 | s++; | ||
135 | } | ||
136 | } else { | ||
137 | if (isdigit(((unsigned char)*str_sig))) { | ||
138 | char *endp; | ||
139 | long int sn = strtol(str_sig, &endp, 10); | ||
140 | /* test correct and overflow */ | ||
141 | if(*endp == 0 && sn >= 0 && sn < NSIG) { | ||
142 | *signo = (int)sn; | ||
143 | /* test for unnamed */ | ||
144 | sptr = u_signal_names(0, signo, 0); | ||
145 | if(sptr==NULL) | ||
146 | return NULL; | ||
147 | if(sn!=0) | ||
148 | sptr += 3; | ||
149 | return sptr; | ||
150 | } | ||
151 | } else { | ||
152 | sptr = str_sig; | ||
153 | while (s->name != 0) { | ||
154 | if (strcasecmp(s->name, sptr) == 0) { | ||
155 | *signo = s->number; | ||
156 | if(startnum<0) { | ||
157 | sprintf(retstr, "%d", *signo); | ||
158 | return retstr; | ||
159 | } | ||
160 | break; | ||
161 | } | ||
162 | if(s!=signames && sptr == str_sig && | ||
163 | strncasecmp(sptr, prefix, 3) == 0) { | ||
164 | sptr += 3; /* strlen(prefix) */ | ||
165 | continue; | ||
166 | } | ||
167 | sptr = str_sig; | ||
168 | s++; | ||
169 | } | ||
170 | } | 55 | } |
171 | } | 56 | } |
172 | if(s->name==0) | 57 | |
173 | return NULL; | 58 | return buf; |
174 | if(s!=signames) | ||
175 | strcpy(retstr, prefix); | ||
176 | else | ||
177 | retstr[0] = 0; | ||
178 | return strcat(retstr, s->name); | ||
179 | } | 59 | } |