aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBill Schmidt <wschmidt@linux.vnet.ibm.com>2018-01-18 01:21:50 +0000
committerWilliam Schmidt <wschmidt@gcc.gnu.org>2018-01-18 01:21:50 +0000
commitfe1b6f0d414047a64c65af260016b552b50224d3 (patch)
tree2d380c8b319db1411ee2963b84d02abcf620e4dc
parente91478f6c79ff476482774e4fe2b36ae2e52d695 (diff)
downloadgcc-fe1b6f0d414047a64c65af260016b552b50224d3.zip
gcc-fe1b6f0d414047a64c65af260016b552b50224d3.tar.gz
gcc-fe1b6f0d414047a64c65af260016b552b50224d3.tar.bz2
rs6000.md (*call_indirect_nonlocal_sysv<mode>): Generate different code for -mno-speculate-indirect-jumps.
[gcc] 2018-01-17 Bill Schmidt <wschmidt@linux.vnet.ibm.com> * config/rs6000/rs6000.md (*call_indirect_nonlocal_sysv<mode>): Generate different code for -mno-speculate-indirect-jumps. (*call_value_indirect_nonlocal_sysv<mode>): Likewise. (*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. (*sibcall_nonlocal_sysv<mode>): Generate different code for -mno-speculate-indirect-jumps. (*sibcall_value_nonlocal_sysv<mode>): Likewise. [gcc/testsuite] 2018-01-17 Bill Schmidt <wschmidt@linux.vnet.ibm.com> * gcc.target/powerpc/safe-indirect-jump-1.c: Remove endian restriction, but still restrict to 64-bit. * gcc.target/powerpc/safe-indirect-jump-7.c: New file. * gcc.target/powerpc/safe-indirect-jump-8.c: New file. From-SVN: r256831
-rw-r--r--gcc/ChangeLog15
-rw-r--r--gcc/config/rs6000/rs6000.md147
-rw-r--r--gcc/testsuite/ChangeLog9
-rw-r--r--gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-1.c4
-rw-r--r--gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-7.c14
-rw-r--r--gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-8.c15
6 files changed, 191 insertions, 13 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index e01194c..5e4d6b3 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,18 @@
+2018-01-17 Bill Schmidt <wschmidt@linux.vnet.ibm.com>
+
+ * config/rs6000/rs6000.md (*call_indirect_nonlocal_sysv<mode>):
+ Generate different code for -mno-speculate-indirect-jumps.
+ (*call_value_indirect_nonlocal_sysv<mode>): Likewise.
+ (*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.
+ (*sibcall_nonlocal_sysv<mode>): Generate different code for
+ -mno-speculate-indirect-jumps.
+ (*sibcall_value_nonlocal_sysv<mode>): Likewise.
+
2018-01-17 Michael Meissner <meissner@linux.vnet.ibm.com>
* config/rs6000/rs6000.c (rs6000_emit_move): If we load or store a
diff --git a/gcc/config/rs6000/rs6000.md b/gcc/config/rs6000/rs6000.md
index fe02734..4cef5bb 100644
--- a/gcc/config/rs6000/rs6000.md
+++ b/gcc/config/rs6000/rs6000.md
@@ -10453,10 +10453,35 @@
else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
output_asm_insn ("creqv 6,6,6", operands);
- return "b%T0l";
+ if (rs6000_speculate_indirect_jumps
+ || which_alternative == 1 || which_alternative == 3)
+ return "b%T0l";
+ else
+ return "crset eq\;beq%T0l-";
}
[(set_attr "type" "jmpreg,jmpreg,jmpreg,jmpreg")
- (set_attr "length" "4,4,8,8")])
+ (set (attr "length")
+ (cond [(and (eq (symbol_ref "which_alternative") (const_int 0))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 1)))
+ (const_string "4")
+ (and (eq (symbol_ref "which_alternative") (const_int 0))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 0)))
+ (const_string "8")
+ (eq (symbol_ref "which_alternative") (const_int 1))
+ (const_string "4")
+ (and (eq (symbol_ref "which_alternative") (const_int 2))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 1)))
+ (const_string "8")
+ (and (eq (symbol_ref "which_alternative") (const_int 2))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 0)))
+ (const_string "12")
+ (eq (symbol_ref "which_alternative") (const_int 3))
+ (const_string "8")]
+ (const_string "4")))])
(define_insn_and_split "*call_nonlocal_sysv<mode>"
[(call (mem:SI (match_operand:P 0 "symbol_ref_operand" "s,s"))
@@ -10541,10 +10566,35 @@
else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
output_asm_insn ("creqv 6,6,6", operands);
- return "b%T1l";
+ if (rs6000_speculate_indirect_jumps
+ || which_alternative == 1 || which_alternative == 3)
+ return "b%T1l";
+ else
+ return "crset eq\;beq%T1l-";
}
[(set_attr "type" "jmpreg,jmpreg,jmpreg,jmpreg")
- (set_attr "length" "4,4,8,8")])
+ (set (attr "length")
+ (cond [(and (eq (symbol_ref "which_alternative") (const_int 0))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 1)))
+ (const_string "4")
+ (and (eq (symbol_ref "which_alternative") (const_int 0))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 0)))
+ (const_string "8")
+ (eq (symbol_ref "which_alternative") (const_int 1))
+ (const_string "4")
+ (and (eq (symbol_ref "which_alternative") (const_int 2))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 1)))
+ (const_string "8")
+ (and (eq (symbol_ref "which_alternative") (const_int 2))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 0)))
+ (const_string "12")
+ (eq (symbol_ref "which_alternative") (const_int 3))
+ (const_string "8")]
+ (const_string "4")))])
(define_insn_and_split "*call_value_nonlocal_sysv<mode>"
[(set (match_operand 0 "" "")
@@ -10669,11 +10719,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 +10742,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
@@ -10909,7 +10982,13 @@
output_asm_insn (\"creqv 6,6,6\", operands);
if (which_alternative >= 2)
- return \"b%T0\";
+ {
+ if (rs6000_speculate_indirect_jumps)
+ return \"b%T0\";
+ else
+ /* Can use CR0 since it is volatile across sibcalls. */
+ return \"crset eq\;beq%T0-\;b .\";
+ }
else if (DEFAULT_ABI == ABI_V4 && flag_pic)
{
gcc_assert (!TARGET_SECURE_PLT);
@@ -10919,7 +10998,28 @@
return \"b %z0\";
}"
[(set_attr "type" "branch")
- (set_attr "length" "4,8,4,8")])
+ (set (attr "length")
+ (cond [(eq (symbol_ref "which_alternative") (const_int 0))
+ (const_string "4")
+ (eq (symbol_ref "which_alternative") (const_int 1))
+ (const_string "8")
+ (and (eq (symbol_ref "which_alternative") (const_int 2))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 1)))
+ (const_string "4")
+ (and (eq (symbol_ref "which_alternative") (const_int 2))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 0)))
+ (const_string "12")
+ (and (eq (symbol_ref "which_alternative") (const_int 3))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 1)))
+ (const_string "8")
+ (and (eq (symbol_ref "which_alternative") (const_int 3))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 0)))
+ (const_string "16")]
+ (const_string "4")))])
(define_insn "*sibcall_value_nonlocal_sysv<mode>"
[(set (match_operand 0 "" "")
@@ -10939,7 +11039,13 @@
output_asm_insn (\"creqv 6,6,6\", operands);
if (which_alternative >= 2)
- return \"b%T1\";
+ {
+ if (rs6000_speculate_indirect_jumps)
+ return \"b%T1\";
+ else
+ /* Can use CR0 since it is volatile across sibcalls. */
+ return \"crset eq\;beq%T1-\;b .\";
+ }
else if (DEFAULT_ABI == ABI_V4 && flag_pic)
{
gcc_assert (!TARGET_SECURE_PLT);
@@ -10949,7 +11055,28 @@
return \"b %z1\";
}"
[(set_attr "type" "branch")
- (set_attr "length" "4,8,4,8")])
+ (set (attr "length")
+ (cond [(eq (symbol_ref "which_alternative") (const_int 0))
+ (const_string "4")
+ (eq (symbol_ref "which_alternative") (const_int 1))
+ (const_string "8")
+ (and (eq (symbol_ref "which_alternative") (const_int 2))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 1)))
+ (const_string "4")
+ (and (eq (symbol_ref "which_alternative") (const_int 2))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 0)))
+ (const_string "12")
+ (and (eq (symbol_ref "which_alternative") (const_int 3))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 1)))
+ (const_string "8")
+ (and (eq (symbol_ref "which_alternative") (const_int 3))
+ (eq (symbol_ref "rs6000_speculate_indirect_jumps")
+ (const_int 0)))
+ (const_string "16")]
+ (const_string "4")))])
;; AIX ABI sibling call patterns.
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 346cdc0..f710c15 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,5 +1,12 @@
+2018-01-17 Bill Schmidt <wschmidt@linux.vnet.ibm.com>
+
+ * gcc.target/powerpc/safe-indirect-jump-1.c: Remove endian
+ restriction, but still restrict to 64-bit.
+ * gcc.target/powerpc/safe-indirect-jump-7.c: New file.
+ * gcc.target/powerpc/safe-indirect-jump-8.c: New file.
+
2018-01-17 Harald Anlauf <anlauf@gmx.de>
-
+
PR fortran/83874
* gfortran.dg/pr83874.f90: New test.
diff --git a/gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-1.c b/gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-1.c
index 1a0cc88..d66e9c3 100644
--- a/gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-1.c
+++ b/gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-1.c
@@ -1,7 +1,7 @@
-/* { dg-do compile { target { powerpc64le-*-* } } } */
+/* { dg-do compile { target { lp64 } } } */
/* { dg-additional-options "-mno-speculate-indirect-jumps" } */
-/* Test for deliberate misprediction of indirect calls for ELFv2. */
+/* Test for deliberate misprediction of indirect calls. */
extern int (*f)();
diff --git a/gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-7.c b/gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-7.c
new file mode 100644
index 0000000..d19245e
--- /dev/null
+++ b/gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-7.c
@@ -0,0 +1,14 @@
+/* { dg-do compile } */
+/* { dg-additional-options "-mno-speculate-indirect-jumps" } */
+
+/* Test for deliberate misprediction of indirect calls. */
+
+extern int (*f)();
+
+int bar ()
+{
+ return (*f) () * 53;
+}
+
+/* { dg-final { scan-assembler "crset eq" } } */
+/* { dg-final { scan-assembler "beqctrl-" } } */
diff --git a/gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-8.c b/gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-8.c
new file mode 100644
index 0000000..be2150e
--- /dev/null
+++ b/gcc/testsuite/gcc.target/powerpc/safe-indirect-jump-8.c
@@ -0,0 +1,15 @@
+/* { dg-do compile { target { ilp32 } } } */
+/* { dg-additional-options "-O2 -mno-speculate-indirect-jumps" } */
+
+/* Test for deliberate misprediction of -m32 sibcalls. */
+
+extern int (*f)();
+
+int bar ()
+{
+ return (*f) ();
+}
+
+/* { dg-final { scan-assembler "crset eq" } } */
+/* { dg-final { scan-assembler "beqctr-" } } */
+/* { dg-final { scan-assembler "b ." } } */