“陷阱”和“中断”有什么区别?
如果不同系统的术语不同,那在x86上它们的含义是什么?
“陷阱”和“中断”有什么区别?
如果不同系统的术语不同,那在x86上它们的含义是什么?
陷阱和中断密切相关。陷阱是一种异常,而异常类似于中断。
Intel x86定义了两个重叠的类别,向量事件(中断 vs 异常),以及异常类别(故障 vs 陷阱 vs 中止)。
本文中所有引用都来自于2016年4月版的Intel软件开发者手册。对于(明确而复杂的)x86视角,我建议阅读SDM关于中断和异常处理的章节。
向量事件(中断和异常)会导致处理器跳转到一个中断处理程序,同时保存处理器的大部分状态(足以在稍后从该点继续执行)。
异常和中断都有一个ID,称为向量,它确定处理器跳转到哪个中断处理程序。中断处理程序在中断描述符表中描述。
陷阱(trap)是在执行陷阱指令后立即报告的异常。陷阱允许程序或任务继续执行,而不会丢失程序连续性。陷阱处理程序的返回地址指向陷阱指令后要执行的指令。
故障(fault)是一种通常可以纠正的异常,并且一旦被纠正,程序可以重新启动,而不会丢失连续性。当报告故障时,处理器将机器状态恢复到故障指令开始执行之前的状态。故障处理程序的返回地址(CS和EIP寄存器的保存内容)指向故障指令,而不是指向故障指令后的指令。
例如:页面故障通常是可恢复的。应用程序的某个地址空间可能已经从RAM交换到磁盘上。当应用程序尝试访问已交换出的内存时,它会触发页面故障。内核可以将该内存从磁盘拷贝到RAM,并将控制权交还给应用程序。应用程序将从故障指令处继续执行(访问已交换出的内存的故障指令),但这次内存访问应该不会出现故障。
一个非法指令错误处理程序,如果要模拟浮点数或其他缺失的指令,需要在确定故障指令是否可以处理后,手动增加返回地址,以获得所需的陷阱类行为。x86 #UD
是一种"错误"而不是"陷阱"。(处理程序需要一个指向故障指令的指针来确定它是哪个指令。)
异常是一种不总是报告导致异常的指令位置,并且不允许重新启动引发异常的程序或任务的例外情况。异常用于报告严重错误,例如硬件错误和系统表中不一致或非法值。
软件调用的中断(由INT指令触发)的行为方式类似于陷阱。在处理器保存状态并跳转到中断处理程序之前,指令完成执行。
通常来说,像是异常、故障、中止、陷阱和中断这些术语都指的是同一件事情,并统称为“中断”。
那么,陷阱和中断之间的区别是什么呢?
陷阱:是由程序员发起的并且预期的控制传递到一个特殊的处理程序例程的过程。(例如:80x86 INT指令就是一个很好的例子)
而
中断(硬件):是基于CPU外部硬件事件的程序控制中断(例如:按下键盘上的某个键或定时器芯片的超时事件)。
陷阱是一种特殊的中断,通常被称为软件中断。 中断是一个更普遍的术语,涵盖了硬件中断(来自硬件设备的中断)和软件中断(来自软件的中断,如陷阱)。
代码程序会调用陷阱,例如调用操作系统例程(通常是同步的)。
事件会调用中断(通常是硬件事件,如网络卡接收到数据或CPU定时器),正如其名称所示,中断了正常的控制流,因为CPU必须切换到驱动程序例程来处理该事件。
我认为陷阱是由当前指令的执行引起的,因此它们被称为同步事件。而中断是由处理器中正在运行的独立指令引起的,与外部事件有关,因此被称为异步事件。
中断是硬件中断,而陷阱是软件调用的中断。硬件中断的发生通常会禁用其他硬件中断,但这对于陷阱来说并不成立。如果您需要在服务陷阱之前禁止硬件中断,则需要显式清除中断标志。通常计算机上的中断标志影响(硬件)中断而不是陷阱。这意味着清除此标志将无法防止陷阱。与陷阱不同,中断应该保留 CPU 的先前状态。
陷阱是一种软件中断。如果您编写一个声明了被零除的变量的程序,则会将其视为陷阱。每当您运行此程序时,它都会在同一时间抛出相同的错误。系统调用是陷阱的特殊版本,在其中程序请求操作系统提供其所需的服务。 在中断(硬件中断的通用术语)的情况下,例如i/o错误,cpu在随机时间被中断,这当然不是我们程序员的问题。这是硬件引起的。
中断是系统内部由硬件产生的流程变化。中断处理程序被唤醒来处理中断的原因;然后将控制返回到中断上下文和指令。陷阱是软件生成的中断。可以使用中断来表示I/O完成,以避免需要设备轮询。可以使用陷阱来调用操作系统例程或捕获算术错误。
gcc -ftrapping-math
告诉它(尝试但未成功地)进行优化,以使结果与 C 抽象机器匹配,即使像除以 0 这样的事情也会运行信号处理程序。(即在 FP 异常上陷阱)。但术语取决于供应商的文档。然而,在 Intel 上,int 0x??
不是唯一的陷阱方式。TRAP、软件中断和硬件中断之间的区别? 表示像 div
除以零(#DE
异常)这样的事情也是一个陷阱。这个问题的被接受的答案也是如此。 - Peter Cordes