本次实验使用的Win7 32位的10-10-12分页内核(单核)
分析过程
通过!IDT
指令获取到其调用的时钟中断函数HalpHpetClockInterrupt
通过lm获取hal模块路径
取出放入IDA分析,发现其后会进入KeUpdateSystemTime
继续跟入,发现其调用了HalRequestSoftwareInterrupt
跟入后续调用KfLowerIrql
调用HalpCheckForSoftwareInterrupt
调用HalpDispatchSoftwareInterrupt
最终调用KiDispatchInterrupt
通过分析其中最重要的地方是判断时间片是否到期和是否存在下一个线程
时间片到期的话,则调用KiQuantumEnd
通过阅读WRK代码,该KiQuantumEnd
实现也是判断时间片,如果时间片到期了判断DisableQuantum
与Priority
,并重新设置时间片和线程
存在下一个线程的话,将直接切换线程
总结
线程切换的三种情况
1.当前线程主动调用API:API函数–>KiSwapThread–>KiSwapContext–>SwapContext
2.当前线程的时间片到期:KiDispatchInterrrupt–>KiQuantumEnd–>KiSwapContext–>SwapContext
3.有备用线程:KiDispatchInterrrupt–>SwapContext
4.如果时钟中断的时候时间片没有到期且没有备用线程,那么函数会直接返回,不会发生线程切换
第一种是主动调用到内核API发送的,所以叫主动切换
第二种和第三种都是在时钟中断中发生的,所以叫被动切换
参考资料
https://blog.csdn.net/qq_38474570/article/details/104273704
https://www.cnblogs.com/onetrainee/p/12755998.html