1. Since
(set (reg:TI 111 [ _11 ])
(xor:TI (reg:TI 112 [ a ])
(mem/c:TI (symbol_ref:DI ("b") [flags 0x40] <var_decl
0x7fffe97d6ed8 b>) [1 b+0 S16 A128])))
reduces a memory access, comparing against
(set (reg:TI 110 [ _10 ])
(xor:TI (reg:TI 114 [ _13 ])
(reg:TI 107 [ x ])))
it should have an additional gain of COSTS_N_INSNS (1).
2. Don't subtract ix86_cost->sse_to_integer for store since
(set (mem/c:TI (symbol_ref:DI ("m0") [flags 0x2] <var_decl
0x7fffe94e4e40 m0>) [1 m0+0 S16 A128])
(zero_extend:TI (reg/v:DI 99 [ x ])))
it is a store, not an SSE to integer register move.
gcc/
PR target/127020
* config/i386/i386-features.cc
(timode_scalar_chain::compute_convert_gain): Update memory
operand check.
gcc/testsuite/
PR target/127020
* gcc.target/i386/sse4_1-stv-15.c: New test.
* gcc.target/i386/sse4_1-stv-16.c: Likewise.
--
H.J.
From b24f5ab5b1773943a7a4284ba74eedceb648944c Mon Sep 17 00:00:00 2001
From: "H.J. Lu" <[email protected]>
Date: Tue, 25 Aug 2026 04:13:54 +0800
Subject: [PATCH] x86-64: Update memory operand check in TImode STV
1. Since
(set (reg:TI 111 [ _11 ])
(xor:TI (reg:TI 112 [ a ])
(mem/c:TI (symbol_ref:DI ("b") [flags 0x40] <var_decl 0x7fffe97d6ed8 b>) [1 b+0 S16 A128])))
reduces a memory access, comparing against
(set (reg:TI 110 [ _10 ])
(xor:TI (reg:TI 114 [ _13 ])
(reg:TI 107 [ x ])))
it should have an additional gain of COSTS_N_INSNS (1).
2. Don't subtract ix86_cost->sse_to_integer for store since
(set (mem/c:TI (symbol_ref:DI ("m0") [flags 0x2] <var_decl 0x7fffe94e4e40 m0>) [1 m0+0 S16 A128])
(zero_extend:TI (reg/v:DI 99 [ x ])))
it is a store, not an SSE to integer register move.
gcc/
PR target/127020
* config/i386/i386-features.cc
(timode_scalar_chain::compute_convert_gain): Update memory
operand check.
gcc/testsuite/
PR target/127020
* gcc.target/i386/sse4_1-stv-15.c: New test.
* gcc.target/i386/sse4_1-stv-16.c: Likewise.
Signed-off-by: H.J. Lu <[email protected]>
---
gcc/config/i386/i386-features.cc | 18 ++++++++++++++----
gcc/testsuite/gcc.target/i386/sse4_1-stv-15.c | 15 +++++++++++++++
gcc/testsuite/gcc.target/i386/sse4_1-stv-16.c | 14 ++++++++++++++
3 files changed, 43 insertions(+), 4 deletions(-)
create mode 100644 gcc/testsuite/gcc.target/i386/sse4_1-stv-15.c
create mode 100644 gcc/testsuite/gcc.target/i386/sse4_1-stv-16.c
diff --git a/gcc/config/i386/i386-features.cc b/gcc/config/i386/i386-features.cc
index eb5f82e42cb..09558c4504d 100644
--- a/gcc/config/i386/i386-features.cc
+++ b/gcc/config/i386/i386-features.cc
@@ -1745,7 +1745,11 @@ timode_scalar_chain::compute_convert_gain ()
break;
}
if (!MEM_P (dst))
- igain = COSTS_N_INSNS (1);
+ {
+ igain = COSTS_N_INSNS (1);
+ if (MEM_P (XEXP (src, 1)))
+ igain += COSTS_N_INSNS (1);
+ }
if (CONST_SCALAR_INT_P (XEXP (src, 1)))
igain += timode_immed_const_gain (XEXP (src, 1), bb);
break;
@@ -1917,9 +1921,15 @@ timode_scalar_chain::compute_convert_gain ()
case ZERO_EXTEND:
if (GET_MODE (XEXP (src, 0)) == DImode)
- /* xor (2 bytes) vs. vmovq (5 bytes). */
- igain = speed_p ? COSTS_N_INSNS (1) - ix86_cost->sse_to_integer
- : -COSTS_N_BYTES (3);
+ {
+ if (MEM_P (dst))
+ /* 2 x movq vs movdqa. */
+ igain = speed_p ? COSTS_N_INSNS (1) : -COSTS_N_BYTES (3);
+ else
+ /* xor (2 bytes) vs. vmovq (5 bytes). */
+ igain = speed_p ? COSTS_N_INSNS (1) - ix86_cost->sse_to_integer
+ : -COSTS_N_BYTES (3);
+ }
break;
default:
diff --git a/gcc/testsuite/gcc.target/i386/sse4_1-stv-15.c b/gcc/testsuite/gcc.target/i386/sse4_1-stv-15.c
new file mode 100644
index 00000000000..1f51887780e
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/sse4_1-stv-15.c
@@ -0,0 +1,15 @@
+/* PR target/127020. */
+/* { dg-do compile { target int128 } } */
+/* { dg-options "-O2 -march=x86-64" } */
+
+extern __int128 a, b, c, z;
+
+__int128
+func (__int128 x)
+{
+ return (x ^ a ^ b ^ c ^ z);
+}
+
+/* { dg-final { scan-assembler-times "pxor" 4 } } */
+/* { dg-final { scan-assembler-times "punpcklqdq" 1 } } */
+/* { dg-final { scan-assembler-times "movhlps" 1 } } */
diff --git a/gcc/testsuite/gcc.target/i386/sse4_1-stv-16.c b/gcc/testsuite/gcc.target/i386/sse4_1-stv-16.c
new file mode 100644
index 00000000000..a8d864960c2
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/sse4_1-stv-16.c
@@ -0,0 +1,14 @@
+/* { dg-do compile { target int128 } } */
+/* { dg-options "-O2 -march=cascadelake -mstv -mno-stackrealign" } */
+
+extern __int128 m0,m1,m2,m3;
+void foo(unsigned long x)
+{
+ __int128 m = x;
+ m0 = m;
+ m1 = m;
+ m2 = m;
+ m3 = m;
+}
+
+/* { dg-final { scan-assembler-times "vmovdqa" 4 } } */
--
2.55.0