ICode9

精准搜索请尝试: 精确搜索
首页 > 系统相关> 文章详细

无法从汇编(yasm)代码调用64位Linux上的C标准库函数

2019-05-27 07:37:46  阅读:269  来源: 互联网

标签:c-3 linux assembly x86-64 yasm


我有一个用汇编编写的函数foo,并在Linux(Ubuntu)64位上用yasm和GCC编译.它只是使用puts()向stdout输出一条消息,它的外观如下:

bits 64

extern puts
global foo

section .data

message:
  db 'foo() called', 0

section .text

foo:
  push rbp
  mov rbp, rsp
  lea rdi, [rel message]
  call puts
  pop rbp
  ret

它由GCC编译的C程序调用:

extern void foo();

int main() {
    foo();
    return 0;
}

构建命令:

yasm -f elf64 foo_64_unix.asm
gcc -c foo_main.c -o foo_main.o
gcc foo_64_unix.o foo_main.o -o foo
./foo

这是问题所在:

运行程序时,它会打印一条错误消息,并在调用puts期间立即发生段错误:

./foo: Symbol `puts' causes overflow in R_X86_64_PC32 relocation
Segmentation fault

用objdump反汇编后,我看到调用的地址错误:

0000000000000660 <foo>:
 660:   90                      nop
 661:   55                      push   %rbp
 662:   48 89 e5                mov    %rsp,%rbp
 665:   48 8d 3d a4 09 20 00    lea    0x2009a4(%rip),%rdi
 66c:   e8 00 00 00 00          callq  671 <foo+0x11>      <-- here
 671:   5d                      pop    %rbp
 672:   c3                      retq

(671是下一条指令的地址,不是put的地址)

但是,如果我在C中重写相同的代码,则调用方式会有所不同:

645:   e8 c6 fe ff ff          callq  510 <puts@plt>

即它引用了PLT的投注.

有可能告诉yasm生成类似的代码吗?

解决方法:

已删除注释的已清理版本

在IIRC中,0xe8操作码后面跟着一个有符号的偏移量,该偏移量将被应用于PC(此时已经前进到下一条指令)以计算分支目标.因此objdump将分支目标解释为0x671.

Yasm正在渲染零,因为它可能会在该偏移上放置一个重定位,这就是它要求加载器在加载期间填充正确的放置偏移量.加载程序在计算reloc时遇到溢出,这可能表示puts与调用的距离比在32位有符号偏移量中表示的更远.因此,加载程序无法修复此指令,并且您会崩溃.

66c:e8 00 00 00 00显示未填充的地址.如果你查看你的reloc表,你应该在0x66d上看到一个reloc.汇编程序使用relocs填充地址/偏移量作为全零值并不罕见.

This page表明YASM有一个WRT指令可以控制.got,.plt等的使用.

根据this page的S9.2.5看起来你可以说CALL把WRT ..plt(假设Yasm使用相同的语法,因为这是一个NASM参考)

标签:c-3,linux,assembly,x86-64,yasm
来源: https://codeday.me/bug/20190527/1161833.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有