mips 异常处理

一、硬件完成的工作
1
set epc
2
set EXL 表示进入内核模式和禁止中断
3
set cause寄存器;有的异常也需设置BadVaddr寄存器
4
、跳到异常入口执行
二、软件工作

1
、区分不同的异常,Cause寄存器的ExcCode

2
、准备空间保存寄存器状态,由SAVE_ALL宏完成
说明几点:
1
)、获得空间方法如下:
若是用户态 --> 内核态,则 k0 = sp, sp = *kernelsp - PT_SIZEstore k0, PT_R29(sp),保存其它寄存器。
若是内核态
 --> 内核态,直接 k0 = sp, sp = sp - PT_SIZEstore k0, PT_R29(sp),然后保存其它寄存器。
获得空间大小是PT_SIZE,寄存器按照特定的方式保存,形成一个 struct pt_regs 结构,传递给子函数。
2
)、在SAVE_ALL宏中,保存了epc,statuscause寄存器,这样就可以异常嵌套

3
、调用子函数(sp作为参数),做任何你想做的事。

4
、从子函数返回到ret_from_exception宏,ret_from_exception宏调用RESTORE_ALL宏完成寄存器状态的回复,最后恢复sp寄存器,即恢复到sp+PT_SIZE处。

5
eret,同时完成清除SREXL)位,把控制权交给epc指向的指令。
三、疑问探究

C
语言中主函数中调用子函数,栈的处理过程:

1
、进入子函数的时候,编译器完成sp - size
2
、子函数执行过程中,定义的变量会放到栈上,如果用到s0-s7寄存器,编译器会把s0-s7的值保存到栈上
3
、子函数返回时后,编译器先恢复
s0-s7寄存器,再将sp + 适当的size到进入子函数时sp处。

评论

此博客中的热门博文

mips 精确异常和延时槽

libvirt event 处理

802.11协议用到的简写