问题描述
在bootasm.S
.p2align 2 # force 4 byte alignment
gdt:
SEG_NULLASM # null seg
SEG_ASM(STA_X|STA_R, 0x0, 0xffffffff) # code seg
SEG_ASM(STA_W, 0x0, 0xffffffff) # data seg
gdtdesc:
.word (gdtdesc - gdt - 1) # sizeof(gdt) - 1
.long gdt # address gdt
这是用在
lgdt gdtdesc
gdtdesc的第一个字不应该是gdt的字节大小吗?在这种情况下,它是 3*8=24
,它等于 gdtdesc - gdt
.为什么 gdtdesc - gdt - 1
在这里?
Shouldn't the first word of gdtdesc be the size of gdt in bytes? In this case, it's 3*8=24
, which equals to gdtdesc - gdt
.Why gdtdesc - gdt - 1
here?
推荐答案
根据手册,lgdt
想要以字节为单位的 GDT 大小,但也将其描述为限制".该措辞在最后一个字节的大小与地址之间存在歧义.(这是一种允许更高限制而不包含 16 位限制的方法.)
According to the manual, lgdt
wants the GDT size in bytes, but also describes it as the "limit". That wording is ambiguous between size vs. address of the last byte. (Which would make sense as a way to allow a higher limit without wrapping the 16-bit limit.)
但是 https://wiki.osdev.org/GDT_Tutorial 中的示例使用 sizeof(gdt) 所以这要么是 xv6 中的错误,要么是 osdev 教程中的错误.
But the examples in https://wiki.osdev.org/GDT_Tutorial use sizeof(gdt) so that's either a bug in xv6 or in the osdev tutorial.
https://wiki.osdev.org/Global_Descriptor_Table 同意 xv6,说限制";大小为 1,与 GDT 教程不同.这是有道理的:
https://wiki.osdev.org/Global_Descriptor_Table agrees with xv6, saying "limit" is size-1, unlike the GDT tutorial. This makes sense:
size
是表的大小减1.这是因为size的最大值是65535,而GDT最大可以是65536字节(最多 8192 个条目).此外,任何 GDT 的大小都不能为 0.
如果要确认详细信息,请查看 Intel 或 AMD 的手册;他们希望在系统开发细节的某个地方澄清这一点,与 lgdt
的指令集参考条目分开.
If you want to confirm the details, check Intel or AMD's manuals; they will hopefully clarify this point somewhere in the system development details, separate from the instruction-set reference entry for lgdt
.
或者你希望他们会.但不幸的是,英特尔表示:
Or you'd hope they would. But unfortunately Intel says:
第 2.4.1 节全局描述符表寄存器 (GDTR)
表限制指定表中的字节数".
"the table limit specifies the number of bytes in the table".
这可能只是意味着编写它的人如此陷入限制 = 最后一个字节的偏移量 = 大小的想法,以至于他们甚至没有意识到这一点还不清楚.段限制本身(在 GDT 条目中)也以这种方式工作,使用 0xFFFFF
(粒度=页面)将限制指定为 4GiB 地址空间的最顶部,即无限制.
Which probably just means that whoever wrote it is so caught up in the limit = offset of last byte = size idea that they didn't even realize this isn't clear. Segment limits themselves (in GDT entries) also work this way, using 0xFFFFF
(with granularity=page) to specify the limit as the very top of the 4GiB address space, i.e. unlimited.
这篇关于为什么在 xv6 中有 sizeof(gdt)-1 的 gdtdesc的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!