4
\$\begingroup\$

I am trying to get a signal name to print when getting a signal number. I actually have :

char* getsig(int sig){
    switch (sig)
    {
    case SIGKILL:
        return "SIGKILL";
    case SIGSTOP:
        return "SIGSTOP";
    case SIGTERM:
        return "SIGTERM";
    case SIGTRAP:
        return "SIGTRAP";
    case SIGABRT:
        return "SIGABRT";
    case SIGALRM:
        return "SIGALARM";
    case SIGSEGV:
        return "SIGSEGV";
    case SIGQUIT:
        return "SIGQUIT";
    case SIGINT:
        return "SIGINT";
    case SIGCHLD:
        return "SIGCHLD";
    case SIGCONT:
        return "SIGCONT";
    case SIGPIPE:
        return "SIGPIPE";
    case SIGFPE:
        return "SIGFPE";
    case SIGILL:
        return "SIGILL";
    case 0:
        return "[NO SIGNAL TO DELIVER]";
    default:
        return "UNKN";
    }
}

I can see that this is wrong : I have no certitude that those char* names will be stored in data section on every compiler. I am certain that there is a clean way of doing such a thing, but I cannot find it on the internet. Do anyone has an idea of how I could do this task the beautiful way?

Edit

The final aim is to print a potential signal delivered by a ptrace(PTRACE_CONT, ...); call, e.g: printf("ptrace(PTRACE_CONT); [delivered %s]\n", getsig(data));

\$\endgroup\$
1

1 Answer 1

4
\$\begingroup\$

The way to do this in C is to define an array, and use designated array initializers to ensure the correct mapping between number and string, like so:

static const char *signames[] = {
    [SIGKILL] = "SIGKILL",
    [SIGSTOP] = "SIGSTOP",
    ...
    [0] = "[NO SIGNAL TO DELIVER]",
};

const char *getsig(int sig) {
    if (sig < 0 || sig >= sizeof(signames) / sizeof(*signames) || !signames[sig])
        return "UNKN";

    return signames[sig];
}

Note that it is hard to make this portable; the list of available signals varies by operating system, and some don't even have the concept of signals. Some operating systems and/or standard libraries might already have some function to convert signal numbers to strings, if you target a specific platform and don't care about compatibility, you might consider using that.

Note that strsignal() should be available on any POSIX platform, although it gives you a more human readable string like "Killed" instead of "SIGKILL".

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.