|
Message-ID: <20140617050132.GA1271@brightrain.aerifal.cx> Date: Tue, 17 Jun 2014 01:01:32 -0400 From: Rich Felker <dalias@...c.org> To: musl@...ts.openwall.com Subject: arch-specific reloc.h inconsistencies (bugs?) I'm trying to refactor arch/*/reloc.h to replace the arch-specific do_single_reloc functions with an arch-generic version in dynlink.c and a simple remapping in reloc.h from arch-specific reloc types to a few generic operations that cover everything. This should reduce the burden of porting to new archs, but the immediate motivation is that I'm trying to add "gnu2" tls model (aka TLSDESC, see http://www.fsfla.org/~lxoliva/writeups/TLS/RFC-TLSDESC-x86.txt) and if I don't refactor this now it's going to lead to some really ugly complex code duplication whereby each reloc.h file copies logic that's not arch knowledge but rather an implementation detail of musl's dynamic linker. And this would be really nasty to maintain in the future. Anyway, as the first step for this task, I've been looking over the reloc types in each arch/*/reloc.h file, and I found a few inconsistencies that seem like they may be bugs. I'm going to do more research, but if anyone already has ideas on these, please let me know so I don't waste time on it: 1. powerpc and sh use RELA (addend in the reloc structure rather than inline at the address to be relocated), but the addend is ignored and an inline addend is instead read for thread-pointer-relative (TPREL) relocations. On sh this also happens for DTPMOD and DTPOFF relocations. For DTPMOD that's definitely a bug since an addend makes no sense for these whatsoever, but I'm not sure about the others. It might be a "historical bug" that has to be duplicated for compatibility with toolchains that enshrined it, or it might just be a musl bug (likely due to copy-and-paste from other archs). 2. On sh, GLOB_DAT and JMP_SLOT relocations ignore the addend. This seems like it would give wrong results for things like: char *global2 = &global1[N]; 3. Also on sh, there's a strange REL32 relocation that applies base_addr as an addend to an expression which already contains a symbol value. This seems nonsensical to me just from a "units" perspective but maybe it's right since another address (the address to which the relocation is being supplied) is subtracted. 4. mips has a REL32 relocation which doubles as both a relative (adjust against self's load address) relocation and a symbolic (adjust to point to the address a symbol resolves to) one. The current logic for which way to treat it as is based on the resolved symbol value (sym_val, whether it's zero or nonzero) whereas I think it should be based on whether the symbol was found or not (i.e. whether def.sym is null or not). This likely does not matter in practice but it seems like a bug. With that said, I have locally a working patch for TLSDESC support on i386 already, and based on naive cycle counting it looks like it may be measurably faster than glibc's implementation when dynamic TLS is used, and possibly fast enough that it's not measurably slower than static TLS in real-world usage cases. If resolving the reloc.h refactoring issues doesn't happen immediately I'll go ahead and commit the code for i386 with the intent of finishing the refactoring before I add TLSDESC for other archs. Rich
Powered by blists - more mailing lists
Confused about mailing lists and their use? Read about mailing lists on Wikipedia and check out these guidelines on proper formatting of your messages.