Debian NASM获得文件在这里意味着什么?

Debian NASM获得文件在这里意味着什么?,debian,nasm,relocation,Debian,Nasm,Relocation,我在这里专门从9.2节开始阅读本节: 我已经读了一整天了,我想确保在继续之前我了解这里发生的事情。我相信他们说我们需要执行位置无关的代码,因为在使用共享库时,访问某些全局库时的重新定位不能硬编码。为此,我们使用全局偏移表 我仍然相信他们会说: call .get_GOT .get_GOT: pop ebx add ebx,_GLOBAL_OFFSET_TABLE_+$$-.get_GOT wrt ..gotpc 通过

我在这里专门从9.2节开始阅读本节:

我已经读了一整天了,我想确保在继续之前我了解这里发生的事情。我相信他们说我们需要执行位置无关的代码,因为在使用共享库时,访问某些全局库时的重新定位不能硬编码。为此,我们使用全局偏移表

我仍然相信他们会说:

        call    .get_GOT 
.get_GOT: 
        pop     ebx 
        add     ebx,_GLOBAL_OFFSET_TABLE_+$$-.get_GOT wrt ..gotpc 
通过首先将值ebx推到堆栈上实现使用GOT,其中.get_GOT将GOT的位置放置在相对于rip寄存器的位置,并在ebx中返回它

这就是我认为我理解正确的全部。如果有人能澄清这件事发生了什么

add     ebx,_GLOBAL_OFFSET_TABLE_+$$-.get_GOT wrt ..gotpc 

我将不胜感激。另外,请将其分成关于add指令中整个第二个操作数部分的部分。谢谢。

我在理解所有上下文方面有些困难

调用x相当于PUSH-RIP,JMP-x

下一条指令就是当前的RIP

注意:此代码是链接器的提要,因此链接器将读取代码并输入正确的调用地址,但NASM在汇编时无法知道此类地址

最后一条指令是ADD:我们将EBX添加到一个常量。是,将在装配时计算一个常数

我们缺乏足够的详细信息,但正如您所见,我们从RIP(在ebx中)添加了一个偏移量

$$计算到当前节的开头

对于wrt运算符:,本节可能会更好地解释您正在查找的代码


我对NASM的信任度太高,无法继续下去。

这是一件疯狂的事情,不知何故,它仍然是一件事。。。我看到的每一个地方都解释得很糟糕

我将使用64位寄存器来回答,因为现在世界是64位的,指针是64位的

在呼叫和推送之后,
rbx
包含
.get\u get
的地址。这是因为调用将
rip
推送到堆栈上,并且
rip
始终指向当前指令(通常是下一条指令)后面的地址。因此,pop将
.get\u get
的绝对地址移动到
rbx
。到目前为止,一切顺利

\u GLOBAL\u OFFSET\u TABLE是一个符号(位于ELF文件的符号表中),定义为指向GOT的开始。为什么不直接使用
mov-rbx、\u-GLOBAL\u-OFFSET\u-TABLE\u
?由于历史的原因。。。或者至少输给了我。此指令在我的(64位)机器上运行良好。同样,
$
是一个定义为指向当前节开头的符号

资料来源:

现在,让我们做一些地址数学

    add ebx,   _GLOBAL_OFFSET_TABLE_ + $$ - .get_GOT wrt ..gotpc
=   .get_GOT + _GLOBAL_OFFSET_TABLE_ + $$ - .get_GOT wrt ..gotpc
请注意,我们有
.get\u-get-.get\u-get
。我们可以摆脱它

=   .get_GOT + _GLOBAL_OFFSET_TABLE_ + $$ - .get_GOT wrt ..gotpc
=   _GLOBAL_OFFSET_TABLE_ + $$ wrt ..gotpc
现在,让我们看看
wrt..gotpc
的定义

参考使用wrt..gotpc标记全局偏移表基的符号,将给出从当前节开始到全局偏移表的距离。(((GLOBAL_OFFSET_TABLE))是用于引用GOT的标准符号名。)因此,您需要向结果中添加$$以获取GOT的实际地址

资料来源:

基于此,我们可以将表达式
\u GLOBAL\u OFFSET\u TABLE\uwrt..gotpc
替换为表达式
\u GLOBAL\u OFFSET\u TABLE-$
。(这可能是积极的,因为GOT很可能位于比程序更高的地址中。)这说明了需要添加NASM手册中提到的
$

我们代替

=   _GLOBAL_OFFSET_TABLE_ + $$ wrt ..gotpc
=   $$ + _GLOBAL_OFFSET_TABLE_ wrt ..gotpc
=   $$ + (_GLOBAL_OFFSET_TABLE_ - $$)
=   _GLOBAL_OFFSET_TABLE_
瞧!希望这有帮助