2

I'm trying to dynamically link a 64-bit nasm program using ld instead of gcc, in a 64-bit Linux system. The assembly code is this:

extern printf
extern exit

section .data
  msg: db "Hello x%d", 10, 0   

section .text
global _start

_start:
  mov rdi, [rel msg]
  mov rsi, 64
  call printf

  mov rdi, 0
  call exit

I'm trying to call printf and exit from libc. I assemble and build with:

$ nasm -felf64 src/printf.asm -o bin/printf.o
$ ld bin/printf.o -lc -I /lib/ld-linux.so.2 -o bin/printf

Then I run and get an error:

$ bin/printf
bash: bin/printf: Accessing a corrupted shared library

There is a question with a similar problem here, but the problem there is the opposite: they try to create a 32-bit program in a 64-bit machine. I'm just trying to make a 64-bit program.


I found the solution: there is a /lib64 directory with a ld-linux-x86-64.so.2 that you should use to link with 64-bit libraries. I'm still getting a segmentation fault though.

Michael Petch
  • 46,082
  • 8
  • 107
  • 198
Xito Dev
  • 89
  • 7
  • 1
    You can always ask GCC to tell you what it uses as options to pass to the linker. This answer tells you how: https://stackoverflow.com/a/1170843/3857942 – Michael Petch Jun 08 '20 at 03:45

1 Answers1

3

I'm just trying to make a 64-bit program.

Yes, but you are supplying 32-bit interpreter for it, which wouldn't work for a 64-bit program.

Try using /lib64/ld-linux-x86-64.so.2 instead.

After that fix, the program starts, but crashes with SIGSEGV inside printf. Fix:

mov rdi, [rel msg]

should be:

mov rdi, msg
Employed Russian
  • 199,314
  • 34
  • 295
  • 362