aarch64: Fix -mtrack-speculation for irreversible conditions [PR93341]

We can't yet represent the inverse of all conditions in rtl
(see g:865257c447cc50f5819e), triggering an ICE in the pass
that handles -mtrack-speculation.  Since we don't expect these
insns to be optimised in any way, the easiest fix seemed to be
to add an insn that reverses the condition internally.

2020-01-23  Richard Sandiford  <richard.sandiford@arm.com>

gcc/
	PR target/93341
	* config/aarch64/aarch64.md (UNSPEC_SPECULATION_TRACKER_REV): New
	unspec.
	(speculation_tracker_rev): New pattern.
	* config/aarch64/aarch64-speculation.cc (aarch64_do_track_speculation):
	Use speculation_tracker_rev to track the inverse condition.

gcc/testsuite/
	PR target/93341
	* gcc.target/aarch64/pr93341.c: New test.
This commit is contained in:
Richard Sandiford 2020-01-21 10:31:13 +00:00
parent d16db16edd
commit 2214053f9d
5 changed files with 48 additions and 12 deletions

View File

@ -1,3 +1,12 @@
2020-01-23 Richard Sandiford <richard.sandiford@arm.com>
PR target/93341
* config/aarch64/aarch64.md (UNSPEC_SPECULATION_TRACKER_REV): New
unspec.
(speculation_tracker_rev): New pattern.
* config/aarch64/aarch64-speculation.cc (aarch64_do_track_speculation):
Use speculation_tracker_rev to track the inverse condition.
2020-01-23 Richard Biener <rguenther@suse.de> 2020-01-23 Richard Biener <rguenther@suse.de>
PR tree-optimization/93381 PR tree-optimization/93381

View File

@ -215,20 +215,13 @@ aarch64_do_track_speculation ()
&& REG_P (XEXP (cond, 0)) && REG_P (XEXP (cond, 0))
&& REGNO (XEXP (cond, 0)) == CC_REGNUM && REGNO (XEXP (cond, 0)) == CC_REGNUM
&& XEXP (cond, 1) == const0_rtx); && XEXP (cond, 1) == const0_rtx);
enum rtx_code inv_cond_code rtx branch_tracker = gen_speculation_tracker (copy_rtx (cond));
= reversed_comparison_code (cond, insn); rtx fallthru_tracker = gen_speculation_tracker_rev (cond);
/* We should be able to reverse all conditions. */
gcc_assert (inv_cond_code != UNKNOWN);
rtx inv_cond = gen_rtx_fmt_ee (inv_cond_code, GET_MODE (cond),
copy_rtx (XEXP (cond, 0)),
copy_rtx (XEXP (cond, 1)));
if (inverted) if (inverted)
std::swap (cond, inv_cond); std::swap (branch_tracker, fallthru_tracker);
insert_insn_on_edge (gen_speculation_tracker (cond), insert_insn_on_edge (branch_tracker, BRANCH_EDGE (bb));
BRANCH_EDGE (bb)); insert_insn_on_edge (fallthru_tracker, FALLTHRU_EDGE (bb));
insert_insn_on_edge (gen_speculation_tracker (inv_cond),
FALLTHRU_EDGE (bb));
needs_tracking = true; needs_tracking = true;
} }
else if (GET_CODE (PATTERN (insn)) == RETURN) else if (GET_CODE (PATTERN (insn)) == RETURN)

View File

@ -262,6 +262,7 @@
UNSPEC_REV_SUBREG UNSPEC_REV_SUBREG
UNSPEC_REINTERPRET UNSPEC_REINTERPRET
UNSPEC_SPECULATION_TRACKER UNSPEC_SPECULATION_TRACKER
UNSPEC_SPECULATION_TRACKER_REV
UNSPEC_COPYSIGN UNSPEC_COPYSIGN
UNSPEC_TTEST ; Represent transaction test. UNSPEC_TTEST ; Represent transaction test.
UNSPEC_UPDATE_FFR UNSPEC_UPDATE_FFR
@ -7219,6 +7220,20 @@
[(set_attr "type" "csel")] [(set_attr "type" "csel")]
) )
;; Like speculation_tracker, but track the inverse condition.
(define_insn "speculation_tracker_rev"
[(set (reg:DI SPECULATION_TRACKER_REGNUM)
(unspec:DI [(reg:DI SPECULATION_TRACKER_REGNUM) (match_operand 0)]
UNSPEC_SPECULATION_TRACKER_REV))]
""
{
operands[1] = gen_rtx_REG (DImode, SPECULATION_TRACKER_REGNUM);
output_asm_insn ("csel\\t%1, %1, xzr, %M0", operands);
return "";
}
[(set_attr "type" "csel")]
)
;; BTI <target> instructions ;; BTI <target> instructions
(define_insn "bti_noarg" (define_insn "bti_noarg"
[(unspec_volatile [(const_int 0)] UNSPECV_BTI_NOARG)] [(unspec_volatile [(const_int 0)] UNSPECV_BTI_NOARG)]

View File

@ -1,3 +1,8 @@
2020-01-23 Richard Sandiford <richard.sandiford@arm.com>
PR target/93341
* gcc.target/aarch64/pr93341.c: New test.
2020-01-23 David Malcolm <dmalcolm@redhat.com> 2020-01-23 David Malcolm <dmalcolm@redhat.com>
* gcc.dg/analyzer/data-model-3.c: Remove hardcoded "-O2" and move * gcc.dg/analyzer/data-model-3.c: Remove hardcoded "-O2" and move

View File

@ -0,0 +1,14 @@
/* { dg-do compile } */
/* { dg-options "-mtrack-speculation" } */
int synths_ ( float * rc)
{
float r1, r2;
int i;
for (i = 0; i < 128; ++i)
{
r2 = rc[i];
r1 = ((r2) <= (.99f) ? (r2) : (.99f));
rc[i] = ((r1) >= (-.99f) ? (r1) : (-.99f));
}
}