Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/assembly/6.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Assembly 在x86机器上触发中断时,CR3是否会更改?_Assembly_X86_Paging_Intel_Interrupt - Fatal编程技术网

Assembly 在x86机器上触发中断时,CR3是否会更改?

Assembly 在x86机器上触发中断时,CR3是否会更改?,assembly,x86,paging,intel,interrupt,Assembly,X86,Paging,Intel,Interrupt,在x86机器上,当触发中断时,CR3是否会改变(不仅仅是EIP的值)?当发生中断或异常时,处理器会保存以下状态(请参阅《英特尔64和IA-32体系结构软件开发人员手册》第3卷(3A、3B和3C):系统编程指南,6.12.1.): 如果DPL(目标特权级别)等于CPL(当前特权级别),则在将控制权移交给中断处理程序之前,将以下寄存器和可能的错误代码推送到当前堆栈: EFLAGS, CS, EIP 另一方面,如果DPL低于CPL,则除上述寄存器外,SS和ESP寄存器被推到另一个堆栈上(在TSS

在x86机器上,当触发中断时,CR3是否会改变(不仅仅是EIP的值)?

当发生中断或异常时,处理器会保存以下状态(请参阅《英特尔64和IA-32体系结构软件开发人员手册》第3卷(3A、3B和3C):系统编程指南,6.12.1.):

  • 如果DPL(目标特权级别)等于CPL(当前特权级别),则在将控制权移交给中断处理程序之前,将以下寄存器和可能的错误代码推送到当前堆栈:

    EFLAGS, CS, EIP
    
  • 另一方面,如果DPL低于CPL,则除上述寄存器外,
    SS
    ESP
    寄存器被推到另一个堆栈上(在TSS中指定)

由于处理器必须使操作系统能够恢复中断进程的状态,因此处理器不可能自行更改上述寄存器以外的任何寄存器。因此,
CR3
没有改变

这意味着中断处理程序的代码必须可以在可能发生中断的每个虚拟地址空间中访问。因此,而且由于这样的处理程序通常从内核调用额外的代码,大多数内核将自己的代码和数据的一大部分映射到每个进程的地址空间,从而减少了每个进程的可用内存空间。通常,这种映射建立在可寻址内存空间的“上端”,大约3GB

在我很久以前写的一个爱好内核中,我采取了尽量保持进程地址空间尽可能大的方法,因此我只将中断处理程序以及一些代码和需要更改的数据映射到一个专用的内核地址空间,然后才将中断实际处理到进程的地址空间中。结果证明这是相当困难的,只有一个值得怀疑的好处,这就是为什么我猜大多数系统不采用这种方法


如果中断描述符表中有任务门描述符,则当该中断触发时,将发生硬件任务切换,将处理器的状态保存到当前TSS中,并从任务门引用的TSS加载状态。这包括加载
CR3
寄存器的值,从而更改虚拟地址空间(参见上述手册的7.3)

然而,这在实践中很难做到,因为硬件任务切换——顾名思义——高度依赖于硬件,因此仅在x86 CPU上受支持。由于很少使用该功能,即使是相应的64位CPU也不再支持该功能:

在64位模式下,不支持任务切换[…]

[上面提到的英特尔手册,7.2.3]


可能吧。您可能有一个专门用于中断服务的任务。它的CR3值可能与它中断的任务的CR3值不同(在任务状态段(AKA TSS)中有一个CR3字段)。因此,您可能会在每个中断中切换两次CR3,也就是说,在每个任务切换上。

没有提到这一点。你有理由怀疑它正在改变吗?也许你可以在一个可以单步执行的虚拟机中尝试你的代码。你是说硬件是否会改变它,或者OSs是否经常这样做?我同意——用一些示例代码测试这一点可能是检查这一点的最好(最简单)方法。如果你不知道怎么做,那将是另一个问题:)回答得好,但要吹毛求疵:我相信64位CPU确实支持任务切换,只是不支持64位模式。因此,首先感谢您在本文中给出的答案。此信息在OSdev站点中不可用。