异常
异常的发生和捕捉,是在硬件层面完成的。但是异常的处理,是由软件来完成的
异常处理
异常表
IO发出的信号异常代码,是由操作系统来分配的,像加法移除的异常代码,由CPU触发
根据异常代码在异常表里找到相应的处理代码
异常处理似乎很像一个函数调用,但异常处理需要:
- 把 CPU 内当前运行程序用到的所有寄存器,都放到栈里面
- 像陷阱涉及用户态内核态的异常处理的栈要压到内核里
- 像故障这样的异常,在异常处理程序执行完成之后。从栈里返回出来,继续执行的不是顺序的下一条指令,而是故障发生的当前指令
异常的类别
类别 | 原因 | 异步/同步 | 返回行为 |
---|---|---|---|
中断 | 来自I/O设备的信号 | 异步 | 总是返回到下一条指令 |
陷阱 | 有意的异常 | 同步 | 总是返回到下一条指令 |
故障 | 潜在可恢复的错误 | 同步 | 可能返回到当前指令 |
终止 | 不可恢复的错误 | 同步 | 不会返回 |
Linux/X86-64系统中的异常
- 除法错误
- 一般保护故障
- 缺页
- 机器检查
非本地跳转
用户级异常控制流形式
// 保存当前调用环境,供后面的longjmp调用int setjmp(jmp_buf env);int sigsetjmp(sigjmp_buf env,int savesigs);
void longjmp(jmp_buf env,int retval);void siglongjmp(sigjmp_buf env,int retval);