Subject: re: sparc64-netbsd toolchain lossage :-(
To: None <,,>
From: None <>
List: tech-toolchain
Date: 08/14/2001 19:56:05
|    actually, just this part is needed.  so the ld.elf_so seems to be
|    right.  i guess the above is trashing already set relocations..
| err, ignore the above.  it is exactly backwards.  that part of the
| change does not affect the behaviour (and is probably is a general
| bug fix.)  the lossage is due to the change in .plt vs .rela.plt.

After a great deal of poking around, I think I have some idea what's
going on here.

Each PLT entry loads its index into a register and calls a dynamic
linker entry point.  The dynamic linker entry point uses the PLT
index as the index of the associated relocation entry.  _rtld_bind()
expects a byte address rather than an array index, so the code needs
to convert the index into an offset into the table.  Luckily we always
use `.rela' so we can do this.  The first 4 PLT entries are reserved
for both SPARC ELF32 and ELF64.  In both cases, relocation entries
parallel PLT entries with a one-to-one correspondance.

Apparently, both the sparc32 code, and the new sparc64 ld do not
generate the 4 reserved entries in the relocation table.  As far
as I can tell, this violates the ELF spec, but is what the Sun
linker does.

So, how can we solve this problem?

We could go ahead and change the sparc64 glue code to subtract
4 from the array index the same way the sparc32 code does, but
this will cause a flag day for all sparc64 dynamic binaries.

We could revert that change to the linker, but that will mean
we need to keep local changes to binutils forever.

Or we can add an ugly hack into _rtld_bind() that checks the
first pltrela entry to see if its type is JMP_SLOT, and if it
is, move the pointer up 4 entries.