代码之家  ›  专栏  ›  技术社区  ›  Jet Blue

RISC访问地址大于最大整数

  •  1
  • Jet Blue  · 技术社区  · 6 年前

    假设您运行的是32位risc系统。使用什么指令访问64位内存地址?

    在CISC指令集中,您可以使用多字指令简单地传递额外的字。例如:

    1a) JMP
    1b) loAddress
    1c) hiAddress
    

    考虑到risc指令只有一个单词,您如何访问多个单词的地址?

    假设ALU是32位的并且有进位标志。

    此外,在CISC系统中(例如 8080 )loaddress和hiaddress单词都将存储在程序内存中。即 JMP 指令知道查看程序内存中的下一项以检索 loAddress ,之后的项将检索 hiAddress . RISC发生了什么?

    1 回复  |  直到 6 年前
        1
  •  3
  •   Peter Cordes    6 年前

    即使在CISC上,你所描述的也很不寻常。 这不是因为它是CISC,而是因为它使用比寄存器更宽的地址 . 这通常只存在于8位CPU中。(尽管x86分段也符合条件,间接跳远将指针指向 m16:32 段/偏移对。或者在16位模式下, m16:16 . 作为小端,偏移量是第一个。)在64位模式之外, jmp ptr16:32 也可编码,绝对段:偏移量作为指令流的一部分。)

    通常,当你想设计一个具有更大地址空间的cpu时,你也要使寄存器更宽,这样你就能有效地处理地址。当你想用8位寄存器/alu来节省晶体管的时候,它只在非常低端,但是不能把地址空间限制在256字节,在这里你可以找到这种设计。


    即使地址大小与单词大小匹配,这里也存在一个真正的问题。 构造任意32位(或64位)常数是不同is a以不同方式解决的问题。 . ARM经常使用来自附近“文字池”的PC相对负载,而其他的则经常使用 lui 或相当于设置16位的高位,其余的为零,然后 ori 一个16位的立即数。(ARM有一些巧妙的技巧,通过使用移位/旋转立即数,只设置几个位就可以对立即数进行编码。)

    一般来说,在risc上,如果需要跳远,可能需要使用多条指令在寄存器中构造地址。 然后使用跳转来注册指令。

    mips分支指令很有趣:它有相对分支,可以向程序计数器添加一个相当大范围的有符号位移;绝对跳转指令可以用一个新地址替换pc的低28位。(由26位立即左移构成,因为mips需要对齐指令,所以不需要存储低2位。) How to Calculate Jump Target Address and Branch Target Address? . 但是当目标无法从当前位置到达时,你需要 jr 登记册上有地址的。

    x86-64还缺少64位相对跳转指令。如果你需要跳出超过+2gib的距离(不是 far 在一个新的cs段中),您需要一个间接跳转。正常跳转/分支指令仍在使用 rel8 rel32 位移,保持机器代码紧凑。唯一可以接受64位立即数的指令是 mov -登记。正常的代码模型假设同一个库或可执行文件中的所有代码彼此都在2gib之内,因此链接器将能够填充32位置换。


    8位RISC

    我知道的唯一一个比寄存器宽的程序计数器的risc is a是avr,一个8位寄存器的微控制器。 它可以把成对的寄存器当作16位地址 ,它的PC机是16位的。它 IJMP (indirect jump) instruction 设置pc=z(其中 Z 是一对8位寄存器)。在有22位程序计数器而不是只有16位的AVR上,它归零 PC(21:16)

    EIJMP (扩展间接跳转)从I/O空间中为PC的高位获取EIND寄存器,而低位仍然来自 Z

    AVR指令几乎都是2字节长,但有些版本有 a 4-byte jmp instruction 这需要一个0.4M的绝对地址作为跳转目标。


    带有32位寄存器的主流risc机器也有32位程序计数器和虚拟地址空间 . (可能有超过4gib的物理内存,但不能在一个进程中同时映射所有内存)。

    他们中的大多数在设计上都是以文字为导向的,所以他们所需要的就是 jr reg (MIPS)或任何等同于分支到任何可能地址的地址,因为它适合于一个寄存器。这是减少的一部分 复杂性 RISC的字面意思是。


    在像mips、sparc或powerpc这样的普通risc上, 64位地址仅在64位isa扩展中可用 ,其中有64位整数寄存器。所以你会使用mips这样的指令 ld $2, 0($3) 使用 $3 作为64位基址。看到这个 MIPS-IV ISA manual . (MIPS-III增加了64位扩展名,指令如下 ld daddu . 显然,mips-i留下了大量未使用的操作码编码空间,因此新的操作码有足够的空间来执行完整的64位alu操作。)

    一些32位CPU添加了扩展以支持大型 身体的 不增加虚拟地址空间的地址。例如,x86的pae用36位物理地址定义了一种新的页表格式。但即使有分段,单个进程一次处理的虚拟内存也不能超过4gib。(x86段基+偏移发生 之前 virt->phys转换,创建32位线性地址。因此它对于线程本地存储仍然有用,例如 [fs:0] 作为不同的线性地址取决于线程 fs 段基。)


    32位risc isas的扩展寻址

    保罗·克莱顿评论:

    PA-RISC有“空间寄存器”,提供扩展寻址。32位powerpc具有段寄存器,段寄存器是根据16个条目表中有效地址的最有效4位(提供52位虚拟地址空间)选择的。对于PA-RISC,“SRS 5到7只能通过在最高特权级别执行代码来修改。”对于PowerPC,任何段寄存器更改都需要特权。

    所以很明显一些risc isa在完全64位之前扩展了它们的地址。但我不知道细节,也不打算花时间研究这个问题。其他答案欢迎!