[rs6000] Implement ABI_AIX indirect call handling for -mno-speculate-indirect-jumps

Message ID 50f8a204-375d-913f-baaa-0c0096901d36@linux.vnet.ibm.com
State New
Headers show
Series
  • [rs6000] Implement ABI_AIX indirect call handling for -mno-speculate-indirect-jumps
Related show

Commit Message

Bill Schmidt Jan. 16, 2018, 6:42 p.m.
Hi,

This patch fills in a gap from the previous -mno-speculate-indirect-jumps
patch.  That patch didn't provide support for indirect calls using ABI_AIX
as the default ABI.  This fills in that missing support and changes the
one related powerpc64le-only test case to be compiled for all subtargets.

After some analysis, it doesn't appear possible for sibcalls to be
generated for ELFv1 or ELFv2 using a bctr, given the need for a local
call to avoid the required TOC restore afterwards.  I haven't been able
to find a way to get a bctr generated even when one could theoretically
prove the bctr must go to a local function.

This has been bootstrapped and tested on powerpc64le-linux-gnu with no
regressions.  Testing is still ongoing for powerpc64-linux-gnu.  Provided
that testing completes with no surprises, is this okay for trunk (and
shortly for backport to 7)?

Thanks!
Bill


[gcc]

2018-01-16  Bill Schmidt  <wschmidt@linux.vnet.ibm.com>

        * config/rs6000/rs6000.md (*call_indirect_aix<mode>): Disable for
        -mno-speculate-indirect-jumps.
        (*call_indirect_aix<mode>_nospec): New define_insn.
        (*call_value_indirect_aix<mode>): Disable for
        -mno-speculate-indirect-jumps.
        (*call_value_indirect_aix<mode>_nospec): New define_insn.

[gcc/testsuite]

2018-01-16  Bill Schmidt  <wschmidt@linux.vnet.ibm.com>

        * gcc.target/powerpc/safe-indirect-jump-1.c: Remove
        powerpc64le-only restriction.

Patch

Index: gcc/config/rs6000/rs6000.md
===================================================================
--- gcc/config/rs6000/rs6000.md	(revision 256753)
+++ gcc/config/rs6000/rs6000.md	(working copy)
@@ -10669,11 +10669,22 @@ 
    (use (match_operand:P 2 "memory_operand" "<ptrm>,<ptrm>"))
    (set (reg:P TOC_REGNUM) (unspec:P [(match_operand:P 3 "const_int_operand" "n,n")] UNSPEC_TOCSLOT))
    (clobber (reg:P LR_REGNO))]
-  "DEFAULT_ABI == ABI_AIX"
+  "DEFAULT_ABI == ABI_AIX && rs6000_speculate_indirect_jumps"
   "<ptrload> 2,%2\;b%T0l\;<ptrload> 2,%3(1)"
   [(set_attr "type" "jmpreg")
    (set_attr "length" "12")])
 
+(define_insn "*call_indirect_aix<mode>_nospec"
+  [(call (mem:SI (match_operand:P 0 "register_operand" "c,*l"))
+	 (match_operand 1 "" "g,g"))
+   (use (match_operand:P 2 "memory_operand" "<ptrm>,<ptrm>"))
+   (set (reg:P TOC_REGNUM) (unspec:P [(match_operand:P 3 "const_int_operand" "n,n")] UNSPEC_TOCSLOT))
+   (clobber (reg:P LR_REGNO))]
+  "DEFAULT_ABI == ABI_AIX && !rs6000_speculate_indirect_jumps"
+  "crset eq\;<ptrload> 2,%2\;beq%T0l-\;<ptrload> 2,%3(1)"
+  [(set_attr "type" "jmpreg")
+   (set_attr "length" "16")])
+
 (define_insn "*call_value_indirect_aix<mode>"
   [(set (match_operand 0 "" "")
 	(call (mem:SI (match_operand:P 1 "register_operand" "c,*l"))
@@ -10681,11 +10692,23 @@ 
    (use (match_operand:P 3 "memory_operand" "<ptrm>,<ptrm>"))
    (set (reg:P TOC_REGNUM) (unspec:P [(match_operand:P 4 "const_int_operand" "n,n")] UNSPEC_TOCSLOT))
    (clobber (reg:P LR_REGNO))]
-  "DEFAULT_ABI == ABI_AIX"
+  "DEFAULT_ABI == ABI_AIX && rs6000_speculate_indirect_jumps"
   "<ptrload> 2,%3\;b%T1l\;<ptrload> 2,%4(1)"
   [(set_attr "type" "jmpreg")
    (set_attr "length" "12")])
 
+(define_insn "*call_value_indirect_aix<mode>_nospec"
+  [(set (match_operand 0 "" "")
+	(call (mem:SI (match_operand:P 1 "register_operand" "c,*l"))
+	      (match_operand 2 "" "g,g")))
+   (use (match_operand:P 3 "memory_operand" "<ptrm>,<ptrm>"))
+   (set (reg:P TOC_REGNUM) (unspec:P [(match_operand:P 4 "const_int_operand" "n,n")] UNSPEC_TOCSLOT))
+   (clobber (reg:P LR_REGNO))]
+  "DEFAULT_ABI == ABI_AIX && !rs6000_speculate_indirect_jumps"
+  "crset eq\;<ptrload> 2,%3\;beq%T1l-\;<ptrload> 2,%4(1)"
+  [(set_attr "type" "jmpreg")
+   (set_attr "length" "16")])
+
 ;; Call to indirect functions with the ELFv2 ABI.
 ;; Operand0 is the addresss of the function to call
 ;; Operand2 is the offset of the stack location holding the current TOC pointer
Index: gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-1.c
===================================================================
--- gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-1.c	(revision 256753)
+++ gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-1.c	(working copy)
@@ -1,4 +1,4 @@ 
-/* { dg-do compile { target { powerpc64le-*-* } } } */
+/* { dg-do compile } */
 /* { dg-additional-options "-mno-speculate-indirect-jumps" } */
 
 /* Test for deliberate misprediction of indirect calls for ELFv2.  */