https://gcc.gnu.org/bugzilla/show_bug.cgi?id=63634
Bug ID: 63634 Summary: Compiler generated R_AARCH64_TLSLE_ADD_TPREL_HI12/LO12 pair overflowed by large TP offset Product: gcc Version: 5.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: target Assignee: unassigned at gcc dot gnu.org Reporter: shenhan at google dot com CC: jingyu at google dot com, shenhan at google dot com Target: aarch64 Created attachment 33798 --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=33798&action=edit Test case (Trunk) Compiler generates by default the following insn and relocation pair to access a TLS variable via its offset from TP, like below - main: mrs x3, tpidr_el0 mov w2, 7 add x0, x3, #:tprel_hi12:.LANCHOR0 add x0, x0, #:tprel_lo12_nc:.LANCHOR0 add x1, x0, 1000 .L2: strb w2, [x0], 1 cmp x0, x1 bne .L2 >> add x3, x3, #:tprel_hi12:.LANCHOR1 >> add x3, x3, #:tprel_lo12_nc:.LANCHOR1 ldr w0, [x3, 1024] ret Insns where indicated by ">>" are generated to add offset to x3, which is the TP(thread pointer), the actually offset value is filled in by linker at static link phase. However this means offsets are limited to 24 bits, in other words, it fails the attach test case. (The bad things is bfd fails silently, resulting a bad binary.) To fix this, the compiler/assembler at least needs to generate the following to support 32-bit TP offset. >> movk xx, #:R_AARCH64_TLSLE_MOVW_TPREL_G1, lsl 16 >> movk xx, #:R_AARCH64_TLSLE_MOVW_TPREL_G0 >> add x3, xx