BIOS连续两次从不同的端口读取到同一个寄存器

BIOS reads twice from different port to the same register in a row

我是装配新手。在试图弄清楚 BIOS 的作用时,我使用 gdb 来跟踪它。然而,我发现了一些对我来说很奇怪的事情。
代码段是这样的:

[f000:d129]    0xfd129: mov    eax,0x8f
[f000:d12f]    0xfd12f: out    0x70,al
[f000:d131]    0xfd131: in     al,0x71
[f000:d133]    0xfd133: in     al,0x92
[f000:d135]    0xfd135: or     al,0x2
[f000:d137]    0xfd137: out    0x92,al

我想知道为什么BIOS会连续读取端口0x71和0x92。第二条指令会覆盖从端口 0x71 读取的值吗?那为什么会从0x71端口读取呢?

谢谢!

IO口0x70是"CMOS/RTC index register",IO口0x71是"CMOS/RTC data register"。要访问 CMOS 中的内容,您应该设置索引,然后 read/write 到数据寄存器。

对于某些 RTC 芯片,如果您设置索引但不读取或写入数据寄存器,则芯片将处于未定义状态。这意味着如果你想为以后设置一个索引,你必须从数据寄存器中读取以避免现在和以后之间的"undefined state"。

换句话说;读取的值不相关 - 读取会产生副作用,而副作用才是最重要的。

端口 0x700x71CMOS registers

我找到的关于此主题的最佳列表 is from the BOCHS emulator
根据这个列表,代码如下:

mov    eax,0x8f   ; sets 'NMI disabled ' and 'CMOS RAM index' = 64
out    0x70,al    ; write
in     al,0x71    ; any write to 0x70 should be followed by an action to 0x71 or the RTC wil be left in an unknown state.
in     al,0x92    ; read PS/2 system control port A
or     al,0x2     ; set BIT1 = indicates A20 active
out    0x92,al    ; write PS/2 system control port A

因此此代码禁用 NMI 并设置 A20 line to an active state. The last three lines implement the Fast A20 Gate


I wonder why the BIOS reads from port 0x71 and 0x92 in a row

原因很简单

any write to 0070 should be followed by an action to 0071 or the RTC will be left in an unknown state.

因此第一次读取(读取到 in al,0x71)除了确保这一点没有其他目的,因此可以忽略其结果。