我试着写一个非常简单的引导代码,钩子INT 10,如下所示:
New_int10:
Pushf
Cli
Call [CS:old_Int10]
Iret
代码工作良好的所有情况下,然而,当我试图启动到窗口。系统挂起。我在Bochs中调试,并注意到操作系统尝试将切换到v8086
模式,然后调用Int10
和我的新Int10处理程序(在address 0x97400
) 执行失败(它不去处理程序,导致系统挂起,似乎在保护模式下的一些映射不正确)。
如果不改变INT10
,我可以步进int10 handler
(address 0xC0152
的原始处理程序)。
我有没有错过什么?
我已经挂钩Int15h
注册新的处理程序的区域与e820 type = 2
更新:我做了更多的调试和发现…当窗口(它只发生在windows启动到安全模式时)切换到v8086模式时,它设置VME(在CR4中)= 1,IPOL=3,程序跳转到0x97400。不幸的是,页面映射当前将此地址映射到另一个物理地址0x7dd2000…所以应用程序就疯狂了。地址0xC0000仍然映射到0xC0000,这解释了为什么如果我们不更改INT10,窗口可以启动。
我的问题:有没有办法通知窗口引导加载程序不重新映射地址0x97400?
谢谢
好了,我终于解决了这个问题。
我必须将edba从0x9fc00复制到0x97400,并将0x40e调整到新位置0x97400。然后我将代码重新定位到EDBA旁边,并更新EDBA的大小。然后代码就可以运行了。
我猜窗口引导加载程序试图将640K映射到一个新的位置,这是0x7dd2000。然后它只复制bda(从0到4ff)和ebda(从0x9fc00到0xa000)到新的位置…所以重新定位edba并更新edba的大小就可以了。