Position independent code

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
ohboy

Position independent code

Post by ohboy »

Hello!
I wonder how I can make memory position independent code, like "jump 10 bytes" instead of "jump to this location"?
That's how shared libraries work huh?
AR

Re:Position independent code

Post by AR »

You can generate position independant code with "-fPIC" on the GCC command line IIRC.

As for the relative jumps, I'm not sure how to declare them in GAS but in NASM:

Code: Select all

jmp near jmppoint      ;Allows for very short jumps (Default NASM)
jmp short jmppoint     ;Allows for longer jumps

jmppoint:
To jump to an absolute address is "jmp far jmppoint" IIRC.
User avatar
Pype.Clicker
Member
Member
Posts: 5964
Joined: Wed Oct 18, 2006 2:31 am
Location: In a galaxy, far, far away
Contact:

Re:Position independent code

Post by Pype.Clicker »

jumps will usually be relative unless you tell the assembler otherwise. The only notable exception is for jump/call'ing something that's not in the current object file (e.g. in a library or whatever you made ".extern") ...
ohboy

Re:Position independent code

Post by ohboy »

Oh, I forgot to tell: I want to do position independent C-code with GCC, not assembly.
But all that is needed is -fPIC?
JoeKayzA

Re:Position independent code

Post by JoeKayzA »

ohboy wrote: Oh, I forgot to tell: I want to do position independent C-code with GCC, not assembly.
But all that is needed is -fPIC?
To create it, yes, but to actually load and run it, you'll probably have to do some additional steps. Have a look at GCC's ABI as well as ELF (AFAIK, the implementation of PIC also depends on the binary format that is used).

cheers Joe
User avatar
Pype.Clicker
Member
Member
Posts: 5964
Joined: Wed Oct 18, 2006 2:31 am
Location: In a galaxy, far, far away
Contact:

Re:Position independent code

Post by Pype.Clicker »

very honestly, i don't recommend -fPIC for kernel level i386 stuff: the amount of things that gets added in the ELF format (global object tables, etc) and the restrictions on registers use will (imho) quickly get a nuisance. Rather keep a relocation table and perform code relocation on load-time.

PIC only gets useful when you need to load the _same_ code at several place (like in a _shared_ library), but when it's just about loading a thing at an address you can't tell at link time, relocations are clearly a better choice.
inderpreetb

Re:Position independent code

Post by inderpreetb »

i will agree with Pype.Clicker, doing -fPic for OS code will make
it very heavy (with GOT and PLT table), another way might be to generate a relocatable object file with gcc and while loading it parse the relocation table to load it where every u want to.

A small loader might be required.
ohboy

Re:Position independent code

Post by ohboy »

Really how does a relocation table work?
Is every symbol in the code pointing to a value in the table, which is an address?
And then when I load the binary I step through the table and add the address of where I loaded the code to the table entry?
You don't happen to have docs about these relocatable object files, do you?
User avatar
Pype.Clicker
Member
Member
Posts: 5964
Joined: Wed Oct 18, 2006 2:31 am
Location: In a galaxy, far, far away
Contact:

Re:Position independent code

Post by Pype.Clicker »

i do happen to have docs ... and you can easily find them on "wotsit.org" (or googling for ELF/COFF specification)

The master reference for understanding this is the online book "linkers and loaders" which should be referenced by the FAQ.

Let's say your code contains
here:
call _some_external_symbol

the compiler/assembler has produced
<call-opcode> <long int 0000 0000>

then, in the so-called symbol tables, it adds
SYM[X] "_some_external_symbol": unresolved symbol

and in the relocation table,
location <here+1> should be adjusted with the value of symbol X.

The reason why you have both relocation table AND symbol table is of course to allow one to quickly patch a large collection of references to the same symbol.
ohboy

Re:Position independent code

Post by ohboy »

I found an article on "Linux Journal" with the name "Linkers and Loaders", and I'm currently reading it.
I have one more question though, which switch is needed for ld to create relocatable code? -shared?

Thanks for the great help!
User avatar
Pype.Clicker
Member
Member
Posts: 5964
Joined: Wed Oct 18, 2006 2:31 am
Location: In a galaxy, far, far away
Contact:

Re:Position independent code

Post by Pype.Clicker »

i think it's -r. "-shared" makes it a shared object, which is usually PIC, not relocatable.
mystran

Re:Position independent code

Post by mystran »

-fPIC is used to compile to position independent code.
-shared is used to link to shared library.

To create shared libraries compile with -fPIC, and then link with -fPIC -shared. To create anything other than shared libraries, forget about -fPIC as it's just overhead.

As for actual position independent code on x86: since there isn't EIP-relative data-addressing, some tricks are needed. To get current EIP, one can near-call to next instruction, so as to push the "return address". Pop that, and you know where you are.

Ofcourse, once you have one address, you can calculate all the rest as offsets to that. So you put some base address into (say) EBX, and then use EBX relative addressing for all data. The only complication is restoring the base if called from non-PIC code.

There are some other possibilities, but generally PIC on x86 is a pain.
AR

Re:Position independent code

Post by AR »

Which is where relocatable files come in, no need to determine where you are as the loader "relocates" (or in MS speak: "rebases") it.
Post Reply