X86 64位汇编Linux"Hello World"链接问题 [英] X86 64-bits Assembly Linux 'Hello World' linking issue

查看:159
本文介绍了X86 64位汇编Linux"Hello World"链接问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试跟进此线程,但不幸的是这并不能完全解决我的问题.我尝试运行的代码如下:

I am attempting to follow up on this thread which unfortunately does not quite solve my problem. The code I am trying to run is as follows:

; File hello.asm

        section .data
msg:    db      "Hello World!",0x0a,0

        section .text
        global main
        extern printf

main:
        push  rbp
        mov   rbp, rsp
        lea   rdi, [msg]  ; parameter 1 for printf
        xor   eax, eax    ; 0 floating point parameter
        call  printf
        xor   eax, eax    ; returns 0
        pop   rbp
        ret

我的系统是debian Stretch:

My system is debian stretch:

$ uname -a
Linux <host> 4.8.0-1-amd64 #1 SMP Debian 4.8.7-1 (2016-11-13) x86_64 GNU/Linux

我正在使用yasm汇编程序,如下所示:

I am using the yasm assembler as follows:

$ yasm -f elf64 -g dwarf2 hello.asm

因为在上述源代码中,我的进入点是带有最终ret指令的main,所以我想我需要与gcc而不是ld -e main链接:

Because my entry point in the above source is main with a final ret instruction, I am guessing I need to link with gcc rather than ld -e main:

$ gcc -lc hello.o

但是,我收到以下错误消息:

However, I am getting the following error message:

/usr/bin/ld: hello.o: relocation R_X86_64_32 against `.data' can not be used when making a shared object; recompile with -fPIC
/usr/bin/ld: final link failed: Nonrepresentable section on output
collect2: error: ld returned 1 exit status

此错误提及有关使用-fPIC重新编译的内容,但这是gcc编译器选项,而不是汇编程序yasm的有效选项.所以我不知道该怎么办.

This error mentions something about recompiling with -fPIC but this is a gcc compiler option, not a valid option of the assembler yasm. So I don't know what to do here.

仅出于测试目的,我尝试与ld链接:

Just for the sake of testing, I have attempted to link with ld:

$ ld -e main -lc hello.o

这是成功的,但是在运行时我得到了与上述线程中提到的相同的错误:

which is successful, but I obtain the same error as mentioned in the above thread when running:

$ ./a.out
bash: ./a.out: No such file or directory       # The file *is* there ...

(在回答线程之后,我试图将ld二进制文件中提到的.so库与系统的库进行比较,它们都是/lib64/ld-linux-x86-64.so.2.)

(following the answer of the thread, I have attempted to compare the .so library mentioned in the ld binary file with my system's library, and they are both /lib64/ld-linux-x86-64.so.2.)

我也试图用_start替换main入口点(现在忘记了正确退出程序的问题)并链接了ld -lc hello.o,但是我遇到了同样的错误没有这样的文件或目录"像之前一样.我会继续玩这个游戏,但我想我也会问.

I have also attempted to replace the main entry point with _start (forgetting the issue of properly exiting the program for now) and link with ld -lc hello.o but I get the same error 'No such file or directory' as before. I will continue playing with this, but thought I would ask also.

任何工作建议(带有main_startgccld的建议)都将受到赞赏.

Any working suggestion (with main or _start , gcc or ld) would be warmly appreciated.

按照吉姆的建议,我在hello.asm的顶部添加了default rel,与gcc链接时获得了不同的错误消息(ld -e main -lc不变)

As suggested by Jim I have added default rel at the top of hello.asm and I obtain a different error message when linking with gcc (no change with ld -e main -lc)

$ gcc -lc hello.o

/usr/bin/ld: hello.o: relocation R_X86_64_PC32 against symbol `printf@@GLIBC_2.2.5' can not be used when making a shared object; recompile with -fPIC
/usr/bin/ld: final link failed: Bad value
collect2: error: ld returned 1 exit status

:该帖子与debian stretch上的失败有关:

This post relates to a failure on debian stretch:

Linux: 4.8.0-1-amd64 #1 SMP Debian 4.8.7-1 (2016-11-13) x86_64 GNU/Linux
yasm: 1.3.0
gcc: (Debian 6.2.1-5) 6.2.1 20161124
ld: GNU ld (GNU Binutils for Debian) 2.27.51.20161220

按照吉姆的评论我刚刚在 debian jessie 上测试了相同的代码,在gcc -lc hello.o和以下版本中效果很好:

Following on Jim's comment I have just tested the same code on debian jessie which works perfectly fine with gcc -lc hello.o and the following versions:

Linux: 3.16.0-4-amd64 #1 SMP Debian 3.16.36-1+deb8u2 (2016-10-19) x86_64 GNU/Linux
yasm: 1.2.0
gcc: (Debian 4.9.2-10) 4.9.2
ld: GNU ld (GNU Binutils for Debian) 2.25

待迈克尔·帕奇(Michael Petch)正式回答:问题已解决 gcc -static hello.o

EDIT 3: Pending a formal answer from Michael Petch: issue resolved with gcc -static hello.o

推荐答案

Debian Stretch中的GCC 默认为建筑物位置独立的可执行文件,以构建链接到特定地址的可执行文件,就像传统的-no-pie传递给GCC一样.

GCC in Debian Stretch defaults to building position independent executables, to build executable linked to specific address as is traditional pass -no-pie to GCC.

或者指定正确的重定位类型,我不知道该怎么做.

Alternatively specify the correct relocation type, I don't know how to do this in yasm.

这篇关于X86 64位汇编Linux"Hello World"链接问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆