This is the mail archive of the gcc@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

Wrong dynamic-linker used on Solaris 7/x86


I've just stumbled across a problem on Solaris 7/x86.  A program
wouldn't run with a NULL environment if linked with GNU ld, but it
would work fine if linked with Solaris ld.  Simple demonstration:

#include <unistd.h>
int main(int argc, char *argv[]) {
  static char *env[] = { NULL };
  execle (argv[0], argv[0], NULL, env);
}

The program that got the empty environment would crash when ld.so.1
dereferenced an invalid address.  I've discussed the problem with a
friend I've got at Sun, and he pointed out that truss shouldn't have
mentioned ld.so.1 at all; it should have been handled by the kernel.

Indeed, when the program was linked with Solaris ld, truss didn't
mention ld.so.1.  Only with GNU ld was ld.so.1 explicitly mentioned.

It turned out that the problem is that GNU ld uses /usr/lib/libc.so.1
as the default --dynamic-linker on ELF x86 targets.  For Solaris/x86,
the correct choice would have been /usr/lib/ld.so.1.

Now I'm at a loss on how to address the problem.  I suppose it would
be reasonable to arrange for GCC to pass the dynamic linker name to
the linker.

One problem is that Solaris ld uses the `-I' switch to specify the
dynamic linker, whereas GNU ld doesn't accept this flag; it requires
`--dynamic-linker' instead.  I could introduce a different
configuration for GCC --with-gnu-ld that would use --dynamic-linker by
default, but this seems messy.  However, it would get GCC to work
correctly even with older versions of GNU ld.  Another option is to
implement -I as an alias to --dynamic-linker on Solaris; this would
allow gcc to use the same LINK_SPEC, but would require a fixed GNU ld.
The plus of this option is that one could switch between GNU ld and
Solaris ld with -B switches, as it is possible today.


The other alternative is to modify BFD so that it defaults to the same
dynamic linker that Solaris ld does.  The problem is that all (most?) 
ELF x86 systems use elf32-i386.c, that defines ELF_DYNAMIC_INTERPRETER
to "/usr/lib/libc.so.1".  If I change this, I might be breaking other
targets.  If I introduce an alternate BFD vec that sets
ELF_DYNAMIC_INTERPRETER appropriately for Solaris/x86, it will be
mostly indistinguishable from the current one, so automatic emulation
detection won't work.


Suggestions?

-- 
Alexandre Oliva   Enjoy Guarana', see http://www.ic.unicamp.br/~oliva/
Red Hat GCC Developer                  aoliva@{cygnus.com, redhat.com}
CS PhD student at IC-Unicamp        oliva@{lsd.ic.unicamp.br, gnu.org}
Free Software Evangelist    *Please* write to mailing lists, not to me


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]