Linux内核启动:异常和中断服务程序的挂接

Linux内核启动:异常和中断服务程序的挂接

目录

教学视频

1. 初始化IDT

直达底部

教学视频

视频教程 Linux内核启动:异常和中断服务程序的挂接

1. 初始化IDT

操作系统需要经常处理中断或异常。中断技术也是广泛使用的,系统调用就是利用中断技术实现的。 中断、异常都需要具体的服务程序来执行。 trap_init() 函数将中断、异常处理的服务 程序与IDT进行挂接来逐步重建中断服务体系。

代码如下:

举个例子,n是0;gate_addr是&idt[0],也就是idt的第一项中断描述符的地址;type是 15;dpl(描述符特权级)是0;addr是中断服务程序divide_error(void)的入口地址。

  • “movw%% dx,%%ax\n\t” 是把edx的低字赋值给eax的低字;edx是(char*)(addr),也就是&divide_error; eax的值是0x00080000,8应该看成1000,每一位都有意义,这样 eax的值就是0x00080000+((char *)(addr)的低字),其中的0x0008是段选择符。
  • "movw% 0,%%dx\n\t”是把(short)(0x8000+(dpl<<13)+(type<<8))赋值给dx。edx是(char *)(addr),也就是&divide_error。 因为这部分数据是按位拼接的,必须计算精确,我们耐心详细计算一下: 0x8000就是二进制的 1000 0000 0000 0000;dpl 是00,dpl<<13就是000 0000 0000 0000;type是15,type<<8 就是 1111 0000 0000;加起来就是1000 1111 0000 0000,这就是dx的值。 edx的计算结果就是(char *)(addr)的高字即&divide_error的高字+ 1000 1111 0000 0000。
  • "movl%% eax,% 1\n\t” 是把eax的值赋给*((char *)(gate_addr)),就是赋 给idt[0]的前4字节。
  • "movl%% edx,%2”是把edx的值赋给*( 4+(char *)(gate_ addr)),就是赋给idt[0]的后4字节。 8字节合起来就是完整的idt[0]。

所有中断服务程序与IDT的初始化基本上都类似。 set_system_gate(n, addr)与set_ trap_ gate(n, addr)用的_set_gate(gate_ addr, type, dpl, addr)是一样 的; 差别是set_trap_gate的dpl是0,而set_system_ gate的dpl是3。

dpl为0的意思是只能由内核处理,dpl为3的意思是系统系统调用可以由3特权级(用户特权级)调用。

接下来将IDT的int 0x11~int0x2F都初始化,将IDT中对应的指向中断服务程序的指针设置为 reserved(保留)。 设置协处理器的IDT项。允许主8259A中断控制器的IRQ2、 IRQ3的中断请求。 设置并口(可以接打印机)的IDT项。32位中断服务体系是为适应中断信号机制而建立的。

这些代码的目的就是要拼出中断描述符。回顾一下中断描述符的格式,如下

异常描述符设定效果如下

返回目录

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值