Segfault calling dlopen()'ed executable built with -pie and using TLS

Cary Coutant
Tue Apr 19 21:15:00 GMT 2016

>> In theory, I think you could build a shared object that has an entry
>> point so it could act as an executable, but you'd need to build some
>> startup files that don't currently exist. For a binary to act as an
>> executable, it needs an entry point, but the entry point is not
>> "main"
>> -- it's "_start", defined in crt1.o, which performs a bunch of
>> runtime
>> initialization before actually calling "main". The crt1.o that comes
>> with your compiler probably has non-PIC code in it, so you can't link
>> it into a shared library.
> Yes, indeed, but I'm not calling _start() from the loader, I'm calling
> main()... so I guess non-PIC-ness of the startup code does not matter,
> does it?

Maybe I misunderstood your original question. Yes, you're calling the
payload's main() from your loader, and that's OK because your loader
has already started up through the crt startup code. But I thought you
were trying to link the payload binary so that it could also serve as
an executable that could be launched by itself rather than via the
loader. To do that, you need the startup code in the crt*.o files, and
that code will call your payload's main().

> What else differs between -shared and -pie so that dlopen()'ing -shared
> executable works well with TLS, but dlopen()'ing -pie executable does
> not work?

Off the top of my head, I can't think of anything, but I suspect
there's at least a 50% chance that there are other obstacles.


More information about the Gcc-help mailing list