123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350 |
- /* sig2str.c -- convert between signal names and numbers
- Copyright (C) 2002, 2004, 2006, 2009-2017 Free Software Foundation, Inc.
- This program is free software: you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 3 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program. If not, see <http://www.gnu.org/licenses/>. */
- /* Written by Paul Eggert. */
- #include <config.h>
- #include <limits.h>
- #include <signal.h>
- #include <stdlib.h>
- #include <stdio.h>
- #include <string.h>
- #include "sig2str.h"
- #ifndef SIGRTMIN
- # define SIGRTMIN 0
- # undef SIGRTMAX
- #endif
- #ifndef SIGRTMAX
- # define SIGRTMAX (SIGRTMIN - 1)
- #endif
- #define NUMNAME(name) { SIG##name, #name }
- /* Signal names and numbers. Put the preferred name first. */
- static struct numname { int num; char const name[8]; } numname_table[] =
- {
- /* Signals required by POSIX 1003.1-2001 base, listed in
- traditional numeric order where possible. */
- #ifdef SIGHUP
- NUMNAME (HUP),
- #endif
- #ifdef SIGINT
- NUMNAME (INT),
- #endif
- #ifdef SIGQUIT
- NUMNAME (QUIT),
- #endif
- #ifdef SIGILL
- NUMNAME (ILL),
- #endif
- #ifdef SIGTRAP
- NUMNAME (TRAP),
- #endif
- #ifdef SIGABRT
- NUMNAME (ABRT),
- #endif
- #ifdef SIGFPE
- NUMNAME (FPE),
- #endif
- #ifdef SIGKILL
- NUMNAME (KILL),
- #endif
- #ifdef SIGSEGV
- NUMNAME (SEGV),
- #endif
- /* On Haiku, SIGSEGV == SIGBUS, but we prefer SIGSEGV to match
- strsignal.c output, so SIGBUS must be listed second. */
- #ifdef SIGBUS
- NUMNAME (BUS),
- #endif
- #ifdef SIGPIPE
- NUMNAME (PIPE),
- #endif
- #ifdef SIGALRM
- NUMNAME (ALRM),
- #endif
- #ifdef SIGTERM
- NUMNAME (TERM),
- #endif
- #ifdef SIGUSR1
- NUMNAME (USR1),
- #endif
- #ifdef SIGUSR2
- NUMNAME (USR2),
- #endif
- #ifdef SIGCHLD
- NUMNAME (CHLD),
- #endif
- #ifdef SIGURG
- NUMNAME (URG),
- #endif
- #ifdef SIGSTOP
- NUMNAME (STOP),
- #endif
- #ifdef SIGTSTP
- NUMNAME (TSTP),
- #endif
- #ifdef SIGCONT
- NUMNAME (CONT),
- #endif
- #ifdef SIGTTIN
- NUMNAME (TTIN),
- #endif
- #ifdef SIGTTOU
- NUMNAME (TTOU),
- #endif
- /* Signals required by POSIX 1003.1-2001 with the XSI extension. */
- #ifdef SIGSYS
- NUMNAME (SYS),
- #endif
- #ifdef SIGPOLL
- NUMNAME (POLL),
- #endif
- #ifdef SIGVTALRM
- NUMNAME (VTALRM),
- #endif
- #ifdef SIGPROF
- NUMNAME (PROF),
- #endif
- #ifdef SIGXCPU
- NUMNAME (XCPU),
- #endif
- #ifdef SIGXFSZ
- NUMNAME (XFSZ),
- #endif
- /* Unix Version 7. */
- #ifdef SIGIOT
- NUMNAME (IOT), /* Older name for ABRT. */
- #endif
- #ifdef SIGEMT
- NUMNAME (EMT),
- #endif
- /* USG Unix. */
- #ifdef SIGPHONE
- NUMNAME (PHONE),
- #endif
- #ifdef SIGWIND
- NUMNAME (WIND),
- #endif
- /* Unix System V. */
- #ifdef SIGCLD
- NUMNAME (CLD),
- #endif
- #ifdef SIGPWR
- NUMNAME (PWR),
- #endif
- /* GNU/Linux 2.2 and Solaris 8. */
- #ifdef SIGCANCEL
- NUMNAME (CANCEL),
- #endif
- #ifdef SIGLWP
- NUMNAME (LWP),
- #endif
- #ifdef SIGWAITING
- NUMNAME (WAITING),
- #endif
- #ifdef SIGFREEZE
- NUMNAME (FREEZE),
- #endif
- #ifdef SIGTHAW
- NUMNAME (THAW),
- #endif
- #ifdef SIGLOST
- NUMNAME (LOST),
- #endif
- #ifdef SIGWINCH
- NUMNAME (WINCH),
- #endif
- /* GNU/Linux 2.2. */
- #ifdef SIGINFO
- NUMNAME (INFO),
- #endif
- #ifdef SIGIO
- NUMNAME (IO),
- #endif
- #ifdef SIGSTKFLT
- NUMNAME (STKFLT),
- #endif
- /* AIX 5L. */
- #ifdef SIGDANGER
- NUMNAME (DANGER),
- #endif
- #ifdef SIGGRANT
- NUMNAME (GRANT),
- #endif
- #ifdef SIGMIGRATE
- NUMNAME (MIGRATE),
- #endif
- #ifdef SIGMSG
- NUMNAME (MSG),
- #endif
- #ifdef SIGPRE
- NUMNAME (PRE),
- #endif
- #ifdef SIGRETRACT
- NUMNAME (RETRACT),
- #endif
- #ifdef SIGSAK
- NUMNAME (SAK),
- #endif
- #ifdef SIGSOUND
- NUMNAME (SOUND),
- #endif
- /* Older AIX versions. */
- #ifdef SIGALRM1
- NUMNAME (ALRM1), /* unknown; taken from Bash 2.05 */
- #endif
- #ifdef SIGKAP
- NUMNAME (KAP), /* Older name for SIGGRANT. */
- #endif
- #ifdef SIGVIRT
- NUMNAME (VIRT), /* unknown; taken from Bash 2.05 */
- #endif
- #ifdef SIGWINDOW
- NUMNAME (WINDOW), /* Older name for SIGWINCH. */
- #endif
- /* BeOS */
- #ifdef SIGKILLTHR
- NUMNAME (KILLTHR),
- #endif
- /* Older HP-UX versions. */
- #ifdef SIGDIL
- NUMNAME (DIL),
- #endif
- /* Korn shell and Bash, of uncertain vintage. */
- { 0, "EXIT" }
- };
- #define NUMNAME_ENTRIES (sizeof numname_table / sizeof numname_table[0])
- /* ISDIGIT differs from isdigit, as follows:
- - Its arg may be any int or unsigned int; it need not be an unsigned char
- or EOF.
- - It's typically faster.
- POSIX says that only '0' through '9' are digits. Prefer ISDIGIT to
- isdigit unless it's important to use the locale's definition
- of "digit" even when the host does not conform to POSIX. */
- #define ISDIGIT(c) ((unsigned int) (c) - '0' <= 9)
- /* Convert the signal name SIGNAME to a signal number. Return the
- signal number if successful, -1 otherwise. */
- static int
- str2signum (char const *signame)
- {
- if (ISDIGIT (*signame))
- {
- char *endp;
- long int n = strtol (signame, &endp, 10);
- if (! *endp && n <= SIGNUM_BOUND)
- return n;
- }
- else
- {
- unsigned int i;
- for (i = 0; i < NUMNAME_ENTRIES; i++)
- if (strcmp (numname_table[i].name, signame) == 0)
- return numname_table[i].num;
- {
- char *endp;
- int rtmin = SIGRTMIN;
- int rtmax = SIGRTMAX;
- if (0 < rtmin && strncmp (signame, "RTMIN", 5) == 0)
- {
- long int n = strtol (signame + 5, &endp, 10);
- if (! *endp && 0 <= n && n <= rtmax - rtmin)
- return rtmin + n;
- }
- else if (0 < rtmax && strncmp (signame, "RTMAX", 5) == 0)
- {
- long int n = strtol (signame + 5, &endp, 10);
- if (! *endp && rtmin - rtmax <= n && n <= 0)
- return rtmax + n;
- }
- }
- }
- return -1;
- }
- /* Convert the signal name SIGNAME to the signal number *SIGNUM.
- Return 0 if successful, -1 otherwise. */
- int
- str2sig (char const *signame, int *signum)
- {
- *signum = str2signum (signame);
- return *signum < 0 ? -1 : 0;
- }
- /* Convert SIGNUM to a signal name in SIGNAME. SIGNAME must point to
- a buffer of at least SIG2STR_MAX bytes. Return 0 if successful, -1
- otherwise. */
- int
- sig2str (int signum, char *signame)
- {
- unsigned int i;
- for (i = 0; i < NUMNAME_ENTRIES; i++)
- if (numname_table[i].num == signum)
- {
- strcpy (signame, numname_table[i].name);
- return 0;
- }
- {
- int rtmin = SIGRTMIN;
- int rtmax = SIGRTMAX;
- int base, delta;
- if (! (rtmin <= signum && signum <= rtmax))
- return -1;
- if (signum <= rtmin + (rtmax - rtmin) / 2)
- {
- strcpy (signame, "RTMIN");
- base = rtmin;
- }
- else
- {
- strcpy (signame, "RTMAX");
- base = rtmax;
- }
- delta = signum - base;
- if (delta != 0)
- sprintf (signame + 5, "%+d", delta);
- return 0;
- }
- }
|