在8086汇编语言程序设计中,使用逻辑地址来引用存储器。这个特性对所有的x86芯片,包括现代的奔腾微处理器来说都是通用的吗?
发布于 2011-02-02 13:45:05
所有16位和32位x86线路(8086、8088、80186、80286、80386、i486、奔腾等)使用某种形式的段/偏移量寻址。然而,段所指的确切内容从80286 /88/186行到8086/88/186行发生了巨大的变化。
在早期的芯片中,没有虚拟寻址,段指的是20位内存地址的高16位,而偏移量是该地址的16位偏移量。这意味着您可以通过一组非常重叠的64KB块访问1MB的直接可寻址内存。
后来的“保护模式”芯片极大地改变了这一点。代替仅仅是物理地址的高16位的段,它现在是到两个查找表( GDT或LDT)之一的索引,这两个查找表包含指向该段的基地址、大小限制、保护许可等的存储器结构。偏移量从存储的基地址开始工作,并根据大小限制器进行检查,以确保您不会访问它之外的内存,从而确保重叠的地址(如果有)必须显式设置为如此,而不是隐式地重叠较早的芯片集。80286版仍然有64KB大小的数据段,但80386版和更高版本完全摆脱了这一限制。
数据段仍由芯片隐式使用。代码从CS段获取(除非另有特别说明)。从DS段获取数据(除非另有特别说明)。ES在许多操作中用作目的地(同样,除非...你知道该怎么做)。堆栈通过SS访问,依此类推。许多操作系统(甚至是所有的?)然而,在32位处理器(80286以后)上,只将所有段映射到相同的内存空间,从而模仿平面地址空间布局。如果您在Windows NT或更高版本上编程,或者在Linux系统或类似系统上编程,您可能根本不会考虑段。
AMD64指令又是不同的,基本上是朝着完全消除段的方向迈出的一步。它通常是用于在该环境中保护的寻呼系统。
发布于 2011-02-02 13:34:42
在32位保护模式中,所有寻址仍然使用段寄存器--但在几乎每个32位操作系统中,四个主段寄存器的基址设置为0,限制为4 of,因此它们基本上都是“传递”。所有地址转换都是通过分页单元来完成的。
在64位模式下,大多数其他选项(没有人使用)都会被简单地删除。段在一定程度上仍然被使用(主要用于在64位模式和兼容模式之间切换),但仅此而已。
发布于 2011-02-02 13:24:34
所有32位x86机器都支持全套段寄存器并通过它们访问内存。amd64/Intel 64芯片仍有有限的支持,但删除了大部分分段功能。
在保护模式下,与实模式不同,段寄存器不是简单地缩放并添加到地址;它们是GDT或LDT (全局或局部描述符表)的索引,其中包含描述基址(起始地址)和大小限制的段描述符,以及段的权限位。检查地址是否小于限制,并将其添加到指定的基址,并根据权限位检查访问。
https://stackoverflow.com/questions/4870995
复制相似问题