aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorYvan Roux <yvan.roux@linaro.org>2017-07-05 09:15:40 +0200
committerYvan Roux <yvan.roux@linaro.org>2017-07-05 09:15:40 +0200
commitf83d498336b6609abc5606f7763fdfb4fb19c720 (patch)
treeb74155faf7c49c317002438fbf88c05f9cf05a3c /gcc
parent6de476b31d17787d4a7eae2c5f3e22f5bf519205 (diff)
gcc/
Backport from trunk r248870. 2017-06-05 Kyrylo Tkachov <kyrylo.tkachov@arm.com> * config/aarch64/aarch64.md (sub<mode>3_compare1_imm): New define_insn. (peephole2): New peephole2 to emit the above. * config/aarch64/predicates.md (aarch64_sub_immediate): New predicate. gcc/testsuite/ Backport from trunk r248870. 2017-06-05 Kyrylo Tkachov <kyrylo.tkachov@arm.com> * gcc.target/aarch64/subs_compare_2.c: New test. Change-Id: I2c563b493aaba9a179d7048427ba5fcb444ec89b
Diffstat (limited to 'gcc')
-rw-r--r--gcc/config/aarch64/aarch64.md31
-rw-r--r--gcc/config/aarch64/predicates.md4
-rw-r--r--gcc/testsuite/gcc.target/aarch64/subs_compare_2.c15
3 files changed, 50 insertions, 0 deletions
diff --git a/gcc/config/aarch64/aarch64.md b/gcc/config/aarch64/aarch64.md
index edf9373ac13..2e9331fd72b 100644
--- a/gcc/config/aarch64/aarch64.md
+++ b/gcc/config/aarch64/aarch64.md
@@ -2234,6 +2234,19 @@
[(set_attr "type" "alus_sreg")]
)
+(define_insn "sub<mode>3_compare1_imm"
+ [(set (reg:CC CC_REGNUM)
+ (compare:CC
+ (match_operand:GPI 1 "register_operand" "r")
+ (match_operand:GPI 3 "const_int_operand" "n")))
+ (set (match_operand:GPI 0 "register_operand" "=r")
+ (plus:GPI (match_dup 1)
+ (match_operand:GPI 2 "aarch64_sub_immediate" "J")))]
+ "INTVAL (operands[3]) == -INTVAL (operands[2])"
+ "subs\\t%<w>0, %<w>1, #%n2"
+ [(set_attr "type" "alus_sreg")]
+)
+
(define_peephole2
[(set (match_operand:GPI 0 "register_operand")
(minus:GPI (match_operand:GPI 1 "aarch64_reg_or_zero")
@@ -2252,6 +2265,24 @@
}
)
+(define_peephole2
+ [(set (match_operand:GPI 0 "register_operand")
+ (plus:GPI (match_operand:GPI 1 "register_operand")
+ (match_operand:GPI 2 "aarch64_sub_immediate")))
+ (set (reg:CC CC_REGNUM)
+ (compare:CC
+ (match_dup 1)
+ (match_operand:GPI 3 "const_int_operand")))]
+ "!reg_overlap_mentioned_p (operands[0], operands[1])
+ && INTVAL (operands[3]) == -INTVAL (operands[2])"
+ [(const_int 0)]
+ {
+ emit_insn (gen_sub<mode>3_compare1_imm (operands[0], operands[1],
+ operands[2], operands[3]));
+ DONE;
+ }
+)
+
(define_insn "*sub_<shift>_<mode>"
[(set (match_operand:GPI 0 "register_operand" "=r")
(minus:GPI (match_operand:GPI 3 "register_operand" "r")
diff --git a/gcc/config/aarch64/predicates.md b/gcc/config/aarch64/predicates.md
index 8e3ea9b4696..cd7ded98663 100644
--- a/gcc/config/aarch64/predicates.md
+++ b/gcc/config/aarch64/predicates.md
@@ -77,6 +77,10 @@
(define_predicate "aarch64_fp_vec_pow2"
(match_test "aarch64_vec_fpconst_pow_of_2 (op) > 0"))
+(define_predicate "aarch64_sub_immediate"
+ (and (match_code "const_int")
+ (match_test "aarch64_uimm12_shift (-INTVAL (op))")))
+
(define_predicate "aarch64_plus_immediate"
(and (match_code "const_int")
(ior (match_test "aarch64_uimm12_shift (INTVAL (op))")
diff --git a/gcc/testsuite/gcc.target/aarch64/subs_compare_2.c b/gcc/testsuite/gcc.target/aarch64/subs_compare_2.c
new file mode 100644
index 00000000000..60c6d9e5ccd
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/subs_compare_2.c
@@ -0,0 +1,15 @@
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+
+int
+foo (int a, int b)
+{
+ int x = a - 4;
+ if (a < 4)
+ return x;
+ else
+ return 0;
+}
+
+/* { dg-final { scan-assembler-times "subs\\tw\[0-9\]+, w\[0-9\]+, #4" 1 } } */
+/* { dg-final { scan-assembler-not "cmp\\tw\[0-9\]+, w\[0-9\]+" } } */