Position Independant Executables without shared libraries
Position Independant Executables without shared libraries
Hi everyone,
I was wondering if anyone has any pointers on how to implement ELF Position Independant Executables, i.e. with GCC's -fpie and -pie flags? Although I can find lots of information around on dynamic linking of shared libraries, at the moment I just want the ability to load a binary into memory without it having to be at a specific virtual location. The PIE flags in GCC and GNU ld seem to do that, however I can't find any information on what support I need in my ELF loader.
My OS is targeted to IA32/i386 using a GNU/gcc 3.4 cross toolchain, and I have a working ELF loader for static executables, however just loading PIE binaries doesn't seem to work for unobvious reasons. If anyone knows what I have to do at load time, or can point me to any documentation for how to write the system dependant stuff for PIE binaries, please let me know.
I do have paging working, and some acceptable memory management, but I want user binaries to be located at an address decided at runtime, rather than at compile-time.
Thanks in advance,
David
I was wondering if anyone has any pointers on how to implement ELF Position Independant Executables, i.e. with GCC's -fpie and -pie flags? Although I can find lots of information around on dynamic linking of shared libraries, at the moment I just want the ability to load a binary into memory without it having to be at a specific virtual location. The PIE flags in GCC and GNU ld seem to do that, however I can't find any information on what support I need in my ELF loader.
My OS is targeted to IA32/i386 using a GNU/gcc 3.4 cross toolchain, and I have a working ELF loader for static executables, however just loading PIE binaries doesn't seem to work for unobvious reasons. If anyone knows what I have to do at load time, or can point me to any documentation for how to write the system dependant stuff for PIE binaries, please let me know.
I do have paging working, and some acceptable memory management, but I want user binaries to be located at an address decided at runtime, rather than at compile-time.
Thanks in advance,
David
- Pype.Clicker
- Member
- Posts: 5964
- Joined: Wed Oct 18, 2006 2:31 am
- Location: In a galaxy, far, far away
- Contact:
Re:Position Independant Executables without shared libraries
well, honnestly, i never heard of "Position Independant Executable" flag, only of "Position Independent Code". I can tell you also that, under regular x86 architecture, there's no simple way to work with PIC code (e.g. it lacks an instruction-relative addressing mode for data)
PIC binaries produced by GCC use the "global offset table" that will contain pointers towards the miscellaneous parts of the program and a specific register (EBX iirc) will be pointing towards that table so that you can access your own "global data" at any time. It's not very nice but at least it ensures everyone can share the code bits.
On the other side, you might want to _relocate_ the binary at load time, that is fix every global variable references so that the program feels home in the newly decided virtual address. That may be slower to load, but it'll be faster to run. Using paging tricks, you could even do "just-in-time" relocation
PIC binaries produced by GCC use the "global offset table" that will contain pointers towards the miscellaneous parts of the program and a specific register (EBX iirc) will be pointing towards that table so that you can access your own "global data" at any time. It's not very nice but at least it ensures everyone can share the code bits.
On the other side, you might want to _relocate_ the binary at load time, that is fix every global variable references so that the program feels home in the newly decided virtual address. That may be slower to load, but it'll be faster to run. Using paging tricks, you could even do "just-in-time" relocation
Re:Position Independant Executables without shared libraries
Hello,
i have written a tool that creates a relocatable binary.
It appends a signature and a list of offsets to relocate to the binary file.
I like my tool, because its possible to run a binary file at every address
i have written a tool that creates a relocatable binary.
It appends a signature and a list of offsets to relocate to the binary file.
I like my tool, because its possible to run a binary file at every address
Re:Position Independant Executables without shared libraries
Hello,
IMHO your idea seems to be fundamentally flawed.
There is only one reason you need position independant code - so you can share libraries.
And you stated you aren't sharing libraries.
So why waste the time!??!??!?
Design your virtual address space properly and each program will always have the same basic layout.
IMHO your idea seems to be fundamentally flawed.
There is only one reason you need position independant code - so you can share libraries.
And you stated you aren't sharing libraries.
So why waste the time!??!??!?
Design your virtual address space properly and each program will always have the same basic layout.
Re:Position Independant Executables without shared libraries
You mean:tom1000000 wrote: Hello,
IMHO your idea seems to be fundamentally flawed.
There is only one reason you need position independant code - so you can share libraries.
And you stated you aren't sharing libraries.
So why waste the time!??!??!?
Design your virtual address space properly and each program will always have the same basic layout.
application=static base address,
shared library=position independent?
I guess it's not always that easy. Just think of an OS that runs without using paging hardware, maybe because it is simply designed this way, or because it should be portable to platforms without an MMU (like ARM, for example). Or an OS that supports modular applications, where several modules of code are put and linked into the same address space, on demand (so these are not really shared libraries then).
I agree however that relocatable binaries are probably a better choice than position independent code, just because you won't loose anything at run time.
cheers Joe
Re:Position Independant Executables without shared libraries
@tom1000000, you assume that every one is using paging, for those like me that are not, we need to be able to run position independant code.
Re:Position Independant Executables without shared libraries
There is such a thing as a Position Independent Executable. The only source of information I've seen on it is its use by the Hardened branch of the Linux from Scratch project. It seems that they use it for all their executable files, but that there are a few "gotchas". Find more info here
Re:Position Independant Executables without shared libraries
Hello,
Sorry I did assume you had paging available.
Good luck with your development.
Tom
Sorry I did assume you had paging available.
Good luck with your development.
Tom
-
- Posts: 1
- Joined: Tue Aug 06, 2024 3:34 pm
Re: Position Independant Executables without shared libraries
One can easily write x86_64 assembly code that is PIE.
jumps are inherently PIC
In NASM syntax:
mov rax, [abs absolute_symbol]
mov rax, [rel relative_symbol]
call [rel local_routine]
call [abs absolute_routine]
lea rax, [abs absolute_address]
lex rax, [rel relative_address]
I tend to use DEFAULT rel, so all "rel"s above are omitted.
The issue is how gcc handles it with C code.
But very important, changing -mcmodel=small (from large) got rid of the _GLOBAL_POSITION_TABLE_. It also reduced my binary size by about 40%. Although pointers are all 64 bits, gcc assumes the binary is under 2GB, so all references to symbols use 32 bit offsets instead of 64.
Sorry for the necro posting, but google got me here, it might get somebody else here too.
jumps are inherently PIC
In NASM syntax:
mov rax, [abs absolute_symbol]
mov rax, [rel relative_symbol]
call [rel local_routine]
call [abs absolute_routine]
lea rax, [abs absolute_address]
lex rax, [rel relative_address]
I tend to use DEFAULT rel, so all "rel"s above are omitted.
The issue is how gcc handles it with C code.
But very important, changing -mcmodel=small (from large) got rid of the _GLOBAL_POSITION_TABLE_. It also reduced my binary size by about 40%. Although pointers are all 64 bits, gcc assumes the binary is under 2GB, so all references to symbols use 32 bit offsets instead of 64.
Sorry for the necro posting, but google got me here, it might get somebody else here too.
Last edited by macpacheco on Sun Aug 18, 2024 12:58 pm, edited 2 times in total.
Re: Position Independant Executables without shared libraries
Please do not necropost. The thread you have replied to is 19 years old. At the time, x86_64 was quite the novelty, and not many people had access to it yet.
Carpe diem!