本文介绍了如何判断SIGILL是源自非法指令还是源自kill -ILL?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在通过void (*sa_sigaction)(int, siginfo_t *, void *);安装的信号处理程序中,如何判断SIGILL是源自非法指令还是源自发送SIGILL的某些进程?我查看了siginfo_t的si_pid,但是在遇到非法指令的情况下,这似乎是未初始化的,因此我无法以此为依据. -当然,我正在寻找一种最好的简单且可移植的解决方案,而不是阅读si_addr上的指令代码并试图确定它是否合法.

In a signal handler installed through void (*sa_sigaction)(int, siginfo_t *, void *);, how can I tell whether a SIGILL originated from an illegal instruction or from some process having sent SIGILL? I looked at si_pid of siginfo_t, but this seems to be uninitialized in case an illegal instruction was encountered, so that I can't base my decision on it. - Of course, I'm searching for a preferably simple and portable solution, rather than reading the instruction code at si_addr and trying to determine if it is legal.

推荐答案

善意 SIGILL的ILL_值(例如IL_ILLADR)之一的si_code.用户请求的SIGILL将具有SI_值之一(通常为SI_USER)的si_code.

A bona fide SIGILL will have an si_code of one of the ILL_ values (e.g., IL_ILLADR). A user-requested SIGILL will have an si_code of one of the SI_ values (often SI_USER).

相关的POSIX值为:

[Kernel-generated]
ILL_ILLOPC  Illegal opcode.
ILL_ILLOPN  Illegal operand.
ILL_ILLADR  Illegal addressing mode.
ILL_ILLTRP  Illegal trap.
ILL_PRVOPC  Privileged opcode.
ILL_PRVREG  Privileged register.
ILL_COPROC  Coprocessor error.
ILL_BADSTK  Internal stack error.

[User-requested]
SI_USER     Signal sent by kill().
SI_QUEUE    Signal sent by the sigqueue().
SI_TIMER    Signal generated by expiration of a timer set by timer_settime().
SI_ASYNCIO  Signal generated by completion of an asynchronous I/O request.
SI_MESGQ    Signal generated by arrival of a message on an empty message queue.

例如,>食谱在这个问题中给我ILL_ILLOPN,而kill(1)kill(2)给我零(SI_USER).

For example, the recipe in this question gives me ILL_ILLOPN, whereas kill(1) and kill(2) give me zero (SI_USER).

当然,您的实现可能会将值添加到POSIX列表中.从历史上看,用户或过程生成的si_code值是< = 0 ,这仍然很普遍.您的实现中可能也有一个方便宏,可以在此处提供帮助.例如,Linux提供:

Of course, your implementation might add values to the POSIX list. Historically, user- or process-generated si_code values were <= 0, and this is still quite common. Your implementation might have a convenience macro to assist here, too. For example, Linux provides:

#define SI_FROMUSER(siptr)      ((siptr)->si_code <= 0)
#define SI_FROMKERNEL(siptr)    ((siptr)->si_code > 0)

这篇关于如何判断SIGILL是源自非法指令还是源自kill -ILL?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

09-25 12:34