MIPS上的$ gp,.cpload和位置独立性

时间:2014-02-05 01:34:23

标签: linux assembly mips

我正在阅读有关Linux here上的MIPS的PIC实现。它说:

  

存储在$ gp寄存器(又名$ 28)中的全局指针是被调用者保存的寄存器。

Wikipedia article about MIPS说的一样。

然而,根据他们的说法,当在函数序言中使用.cpload指令时,它会先破坏$ gp的先前值而不先保存它。当使用.cprestore时,它会将当前 $ gp保存到堆栈帧,而不是函数入口处的$ gp值。 .cprestorejal / jalr的影响也是如此:一旦被调用者返回,它就会恢复$ gp - 假设被调用者可能已经破坏了它。

最后,关于$ gp的函数结尾没有任何内容。

总而言之,听起来不像被叫方保存的寄存器给我。听起来像是来电者保存的寄存器。我在这里误解了什么?

1 个答案:

答案 0 :(得分:0)

MIPS上的Linux程序可以编写为pic或不编辑。如果编译为pic,那么他们必须使用" abicalls",并且它的行为与no-abicalls惯例的行为略有不同。

来自"部分位置无关功能序言" " SYSTEM V应用程序二进制接口 - MIPS处理器补充第3版"我们可以引用:

  

计算gp后,函数会分配本地堆栈空间并将gp保存在堆栈中,因此可以在后续函数调用后恢复。换句话说,gp是一个调用者保存的寄存器。

     

下图中的代码说明了与位置无关的函数序言。 _gp_disp表示函数开头和全局偏移表之间的偏移量。

name:
   la gp, _gp_disp
   addu gp, gp, t9
   addiu sp, sp, –64
   sw gp, 32(sp)

总而言之,如果您正在使用-mabicalls,那么gp会在所有需要全局符号的函数(有一些例外)的开头计算,另外还有任何代码(abi或不)调用abi代码将确保被调用的函数地址存储在t9