https://gcc.gnu.org/bugzilla/show_bug.cgi?id=94177
Bug ID: 94177 Summary: TLS global-dynamic model clobbers function parameter on AIX Product: gcc Version: 10.0 Status: UNCONFIRMED Keywords: wrong-code Severity: normal Priority: P3 Component: target Assignee: unassigned at gcc dot gnu.org Reporter: dje at gcc dot gnu.org Target Milestone: --- Target: powerpc-ibm-aix* In global-dynamic model, if a TLS variable first is referenced in the argument list to a function call, GCC can load the parameters to the call before invoking the function to legitimize the TLS variable, and the legitimize function clobbers some of the same function argument registers. extern int foo (char *, int *, int); int main() { static __thread int result; foo ("%p %u\n", &result, 169); return 0; } $ gcc -fPIC -S bug_tls.c li 5,169 lwz 10,LCM..1(2) lwz 9,LC..1(2) mr 3,10 mr 4,9 bla __tls_get_addr <*** clobbers r4, r5 already loaded with arguments to foo mr 9,3 mr 4,9 lwz 3,LC..2(2) bl .foo The pattern that generates __tls_get_addr shows that it clobbers r4 and r5 (define_insn "tls_get_addr_internal<mode>" [(set (reg:P 3) (unspec:P [(reg:P 3) (reg:P 4)] UNSPEC_TLSTLS)) (clobber (reg:P 0)) (clobber (reg:P 4)) (clobber (reg:P 5)) (clobber (reg:P 11)) (clobber (reg:CC CR0_REGNO)) (clobber (reg:P LR_REGNO))] "TARGET_XCOFF && HAVE_AS_TLS" "bla __tls_get_addr") but GCC overwrites the parameters in calls.c during initial RTL generation.