From: Kong Lingling
gcc/ChangeLog:
* config/i386/i386.md: (addsi_1_zext): Add new alternatives for
NDD and adjust output templates.
(*add_2): Likewise.
(*addsi_2_zext): Likewise.
(*add_3): Likewise.
(*addsi_3_zext): Likewise.
(*adddi_4): Likewise.
(*add_4): Likewise.
(*add_5): Likewise.
(*addv4): Likewise.
(*addv4_1): Likewise.
(*add3_cconly_overflow_1): Likewise.
(*add3_cc_overflow_1): Likewise.
(*addsi3_zext_cc_overflow_1): Likewise.
(*add3_cconly_overflow_2): Likewise.
(*add3_cc_overflow_2): Likewise.
(*addsi3_zext_cc_overflow_2): Likewise.
gcc/testsuite/ChangeLog:
* gcc.target/i386/apx-ndd.c: Add more test.
---
gcc/config/i386/i386.md | 310 +++-
gcc/testsuite/gcc.target/i386/apx-ndd.c | 53 ++--
2 files changed, 232 insertions(+), 131 deletions(-)
diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md
index cb227d19f40..2a73f6dcaec 100644
--- a/gcc/config/i386/i386.md
+++ b/gcc/config/i386/i386.md
@@ -6476,13 +6476,15 @@ (define_insn "*add_1"
;; patterns constructed from addsi_1 to match.
(define_insn "addsi_1_zext"
- [(set (match_operand:DI 0 "register_operand" "=r,r,r")
+ [(set (match_operand:DI 0 "register_operand" "=r,r,r,r,r")
(zero_extend:DI
- (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r,r")
- (match_operand:SI 2 "x86_64_general_operand" "rBMe,0,le"
+ (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r,r,r,rm")
+ (match_operand:SI 2 "x86_64_general_operand"
"rBMe,0,le,rBMe,re"
(clobber (reg:CC FLAGS_REG))]
- "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
+ "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands,
+ TARGET_APX_NDD)"
{
+ bool use_ndd = (which_alternative == 3 || which_alternative == 4);
switch (get_attr_type (insn))
{
case TYPE_LEA:
@@ -6490,11 +6492,13 @@ (define_insn "addsi_1_zext"
case TYPE_INCDEC:
if (operands[2] == const1_rtx)
-return "inc{l}\t%k0";
+return use_ndd ? "inc{l}\t{%1, %k0|%k0, %1}"
+ : "inc{l}\t%k0";
else
{
gcc_assert (operands[2] == constm1_rtx);
- return "dec{l}\t%k0";
+ return use_ndd ? "dec{l}\t{%1, %k0|%k0, %1}"
+: "dec{l}\t%k0";
}
default:
@@ -6504,12 +6508,15 @@ (define_insn "addsi_1_zext"
std::swap (operands[1], operands[2]);
if (x86_maybe_negate_const_int ([2], SImode))
-return "sub{l}\t{%2, %k0|%k0, %2}";
+return use_ndd ? "sub{l}\t{%2 ,%1, %k0|%k0, %1, %2}"
+ : "sub{l}\t{%2, %k0|%k0, %2}";
- return "add{l}\t{%2, %k0|%k0, %2}";
+ return use_ndd ? "add{l}\t{%2 ,%1, %k0|%k0, %1, %2}"
+: "add{l}\t{%2, %k0|%k0, %2}";
}
}
- [(set (attr "type")
+ [(set_attr "isa" "*,*,*,apx_ndd,apx_ndd")
+ (set (attr "type")
(cond [(eq_attr "alternative" "2")
(const_string "lea")
(match_operand:SI 2 "incdec_operand")
@@ -6811,37 +6818,42 @@ (define_insn "*add_2"
[(set (reg FLAGS_REG)
(compare
(plus:SWI
- (match_operand:SWI 1 "nonimmediate_operand" "%0,0,")
- (match_operand:SWI 2 "" ",,0"))
+ (match_operand:SWI 1 "nonimmediate_operand" "%0,0,,rm,r")
+ (match_operand:SWI 2 "" ",,0,r,"))
(const_int 0)))
- (set (match_operand:SWI 0 "nonimmediate_operand" "=m,,")
+ (set (match_operand:SWI 0 "nonimmediate_operand" "=m,,,r,r")
(plus:SWI (match_dup 1) (match_dup 2)))]
"ix86_match_ccmode (insn, CCGOCmode)
- && ix86_binary_operator_ok (PLUS, mode, operands)"
+ && ix86_binary_operator_ok (PLUS, mode, operands, TARGET_APX_NDD)"
{
+ bool use_ndd = (which_alternative == 3 || which_alternative == 4);
switch (get_attr_type (insn))
{
case TYPE_INCDEC:
if (operands[2] == const1_rtx)
-return "inc{}\t%0";
+return use_ndd ? "inc{}\t{%1, %0|%0, %1}"
+ : "inc{}\t%0";
else
{
gcc_assert (operands[2] == constm1_rtx);
- return "dec{}\t%0";
+ return use_ndd ? "dec{}\t{%1, %0|%0, %1}"
+: "dec{}\t%0";
}
default:
if (which_alternative == 2)
std::swap (operands[1], operands[2]);
- gcc_assert (rtx_equal_p (operands[0], operands[1]));
if (x86_maybe_negate_const_int ([2], mode))
-return "sub{}\t{%2, %0|%0, %2}";
+return use_ndd ? "sub{}\t{%2, %1, %0|%0, %1, %2}"
+ : "sub{}\t{%2, %0|%0, %2}";
- return "add{}\t{%2, %0|%0, %2}";
+ return use_ndd ? "add{}\t{%2, %1, %0|%0, %1, %2}"
+: "add{}\t{%2, %0|%0, %2}";
}
}
- [(set (attr "type")
+