Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Difference in position-independent code: x86 vs x86-64

Tags:

c

linux

x86

x86-64

elf

I was recently building a certain shared library (ELF) targeting x86-64 architecture, like this:

g++ -o binary.so -shared --no-undefined ... -lfoo -lbar 

This failed with the following error:

relocation R_X86_64_32 against `a local symbol' can not be used when making a shared object; recompile with -fPIC

Of course, it means I need to rebuild it as position-independent code, so it's suitable for linking into a shared library.

But this works perfectly well on x86 with exactly the same build arguments. So the question is, how is relocation on x86 different from x86-64 and why don't I need to compile with -fPIC on the former?

like image 535
Alex B Avatar asked Jun 30 '10 05:06

Alex B


People also ask

Why do we need Position Independent Code?

Position-independent code is not tied to a specific address. This independence allows the code to execute efficiently at a different address in each process that uses the code. Position-independent code is recommended for the creation of shared objects.

What is position independent code Linux?

In computing, position-independent code (PIC) or position-independent executable (PIE) is a body of machine code that, being placed somewhere in the primary memory, executes properly regardless of its absolute address.


1 Answers

I have found a nice and detailed explanation, which boils down to:

  1. x86-64 uses IP-relative offset to load global data, x86-32 cannot, so it dereferences a global offset.
  2. IP-relative offset does not work for shared libraries, because global symbols can be overridden, so x86-64 breaks down when not built with PIC.
  3. If x86-64 built with PIC, the IP-relative offset dereference now yields a pointer to GOT entry, which is then dereferenced.
  4. x86-32, however, already uses a dereference of a global offset, so it is turned into GOT entry directly.
like image 181
Alex B Avatar answered Sep 20 '22 23:09

Alex B