https://sourceware.org/bugzilla/show_bug.cgi?id=23825
--- Comment #3 from Jim Wilson <wilson at gcc dot gnu.org> --- I got an internal bug report with a simplified testcase related to this, took another look, and found the problem. hifiveu017:1097$ cat tmp.c #include <stdio.h> extern __thread int a; int main (void) {printf ("a = %d\n", a); return 0; } hifiveu017:1097$ cat tmp2.c __thread int a = 10; hifiveu017:1098$ gcc --shared -fpic -o libtmp.so tmp2.c hifiveu017:1099$ gcc tmp.c libtmp.so -Wl,--rpath=`pwd` hifiveu017:1100$ ./a.out Segmentation fault (core dumped) hifiveu017:1101$ Running objdump on a.out, we see 15 .tdata 00000004 0000000000011df8 0000000000011df8 00000df8 2**2 ALLOC, THREAD_LOCAL 16 .preinit_array 00000008 0000000000011df8 0000000000011df8 00000df8 2**0 CONTENTS, ALLOC, LOAD, DATA So the problem here is that tdata has a size, and is alloc, but the next section preinit_array starts at the same address as tdata which is wrong. I tracked this down a bit of code in ld/ldlang.c which does /* .tbss sections effectively have zero size. */ if (!IS_TBSS (os->bfd_section) || bfd_link_relocatable (&link_info)) dotdelta = TO_ADDR (os->bfd_section->size); else dotdelta = 0; dot += dotdelta; This may be right for .tbss, but is not right for the RISC-V .tdata section. The RISC-V .tdata section ended up this way because we have code in bfd/elfnn-riscv.c that does htab->sdyntdata = bfd_make_section_anyway_with_flags (dynobj, ".tdata.dyn", (SEC_ALLOC | SEC_THREAD_LOCAL | SEC_LINKER_CREATED)); So if there is a .tdata.dyn section and no .tdata section, .tdata.dyn gets merged into .tdata and .tdata ends up looking like a .tbss section and gets handled wrong by the linker. There is also a second problem here, which is that a bss-like section can only work at the end of a segment, but there is no code in the linker script to ensure that .tdata.dyn ends up at the end of a segment. It is is just mixed in with the other .tdata.* sections, with no guarantee that it is the last one. I think the solution to this is to just claim that .tdata.dyn has contents, to ensure that space is allocated for it. Normally, it is only used as a target for copy relocs, and hence has no contents, but this causes multiple problems. This section will normally be small, so I don't think there is much performance loss from just pretending that it has contents. I have a patch that does this, and it fixes my testcase, and elf/tst-tls12 from glibc. -- You are receiving this mail because: You are on the CC list for the bug. _______________________________________________ bug-binutils mailing list bug-binutils@gnu.org https://lists.gnu.org/mailman/listinfo/bug-binutils