aboutsummaryrefslogtreecommitdiff
path: root/gcc/config
diff options
context:
space:
mode:
authorHaochen Gui <guihaoc@gcc.gnu.org>2022-08-18 16:23:11 +0800
committerHaochen Gui <guihaoc@gcc.gnu.org>2022-08-18 16:33:21 +0800
commitdefa08a33672d200edbdd7f87ed7afa442249261 (patch)
tree35ff0127c13e38f9b89722c4e796e756ffff3727 /gcc/config
parent4645ce0d00b8e19ea4bbfcd0cef37e91dea3c9f4 (diff)
downloadgcc-defa08a33672d200edbdd7f87ed7afa442249261.zip
gcc-defa08a33672d200edbdd7f87ed7afa442249261.tar.gz
gcc-defa08a33672d200edbdd7f87ed7afa442249261.tar.bz2
rs6000: Add expand pattern for multiply-add (PR103109)
gcc/ PR target/103109 * config/rs6000/rs6000.md (<u>maddditi4): New pattern for multiply-add. (<u>madddi4_highpart): New. (<u>madddi4_highpart_le): New. gcc/testsuite/ PR target/103109 * gcc.target/powerpc/pr103109.h: New. * gcc.target/powerpc/pr103109-1.c: New. * gcc.target/powerpc/pr103109-2.c: New.
Diffstat (limited to 'gcc/config')
-rw-r--r--gcc/config/rs6000/rs6000.md48
1 files changed, 47 insertions, 1 deletions
diff --git a/gcc/config/rs6000/rs6000.md b/gcc/config/rs6000/rs6000.md
index 1367a2c..e9e5cd1 100644
--- a/gcc/config/rs6000/rs6000.md
+++ b/gcc/config/rs6000/rs6000.md
@@ -3217,7 +3217,7 @@
DONE;
})
-(define_insn "*maddld<mode>4"
+(define_insn "maddld<mode>4"
[(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
(plus:GPR (mult:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
(match_operand:GPR 2 "gpc_reg_operand" "r"))
@@ -3226,6 +3226,52 @@
"maddld %0,%1,%2,%3"
[(set_attr "type" "mul")])
+(define_expand "<u>maddditi4"
+ [(set (match_operand:TI 0 "gpc_reg_operand")
+ (plus:TI
+ (mult:TI (any_extend:TI (match_operand:DI 1 "gpc_reg_operand"))
+ (any_extend:TI (match_operand:DI 2 "gpc_reg_operand")))
+ (any_extend:TI (match_operand:DI 3 "gpc_reg_operand"))))]
+ "TARGET_MADDLD && TARGET_POWERPC64"
+{
+ rtx op0_lo = gen_rtx_SUBREG (DImode, operands[0], BYTES_BIG_ENDIAN ? 8 : 0);
+ rtx op0_hi = gen_rtx_SUBREG (DImode, operands[0], BYTES_BIG_ENDIAN ? 0 : 8);
+
+ emit_insn (gen_maddlddi4 (op0_lo, operands[1], operands[2], operands[3]));
+
+ if (BYTES_BIG_ENDIAN)
+ emit_insn (gen_<u>madddi4_highpart (op0_hi, operands[1], operands[2],
+ operands[3]));
+ else
+ emit_insn (gen_<u>madddi4_highpart_le (op0_hi, operands[1], operands[2],
+ operands[3]));
+ DONE;
+})
+
+(define_insn "<u>madddi4_highpart"
+ [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
+ (subreg:DI
+ (plus:TI
+ (mult:TI (any_extend:TI (match_operand:DI 1 "gpc_reg_operand" "r"))
+ (any_extend:TI (match_operand:DI 2 "gpc_reg_operand" "r")))
+ (any_extend:TI (match_operand:DI 3 "gpc_reg_operand" "r")))
+ 0))]
+ "TARGET_MADDLD && BYTES_BIG_ENDIAN && TARGET_POWERPC64"
+ "maddhd<u> %0,%1,%2,%3"
+ [(set_attr "type" "mul")])
+
+(define_insn "<u>madddi4_highpart_le"
+ [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
+ (subreg:DI
+ (plus:TI
+ (mult:TI (any_extend:TI (match_operand:DI 1 "gpc_reg_operand" "r"))
+ (any_extend:TI (match_operand:DI 2 "gpc_reg_operand" "r")))
+ (any_extend:TI (match_operand:DI 3 "gpc_reg_operand" "r")))
+ 8))]
+ "TARGET_MADDLD && !BYTES_BIG_ENDIAN && TARGET_POWERPC64"
+ "maddhd<u> %0,%1,%2,%3"
+ [(set_attr "type" "mul")])
+
(define_insn "udiv<mode>3"
[(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
(udiv:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")