https://gcc.gnu.org/g:a3f953f4ca5cb5cfd9591adaf8568ae8f652bc6e

commit r14-12924-ga3f953f4ca5cb5cfd9591adaf8568ae8f652bc6e
Author: Stefan Schulze Frielinghaus <[email protected]>
Date:   Fri Oct 9 08:58:03 2026 +0200

    expand_mult: Look through vector mode
    
    When expand_mult handles a constant vector multiplier where the scalar
    operand is a CONST_WIDE_INT, then also look through the vector mode
    while determining the shift amount since here we need the scalar mode.
    Note, when we call later on into expand_shift we need the vector mode,
    i.e., only for the shift amount we need the scalar mode.
    
            PR middle-end/127474
    
    gcc/ChangeLog:
    
            * expmed.cc (expand_mult): Look through vector mode.
    
    gcc/testsuite/ChangeLog:
    
            * gcc.dg/torture/pr127474.c: New test.
    
    (cherry picked from commit 5dc4ab23e0d01a1fd20c1365bdb2de039d831ff9)

Diff:
---
 gcc/expmed.cc                           |  4 +++-
 gcc/testsuite/gcc.dg/torture/pr127474.c | 11 +++++++++++
 2 files changed, 14 insertions(+), 1 deletion(-)

diff --git a/gcc/expmed.cc b/gcc/expmed.cc
index 941d9d61c4d7..adeae9e99a9d 100644
--- a/gcc/expmed.cc
+++ b/gcc/expmed.cc
@@ -3528,7 +3528,9 @@ expand_mult (machine_mode mode, rtx op0, rtx op1, rtx 
target,
       else if (CONST_DOUBLE_AS_INT_P (scalar_op1))
 #endif
        {
-         int shift = wi::exact_log2 (rtx_mode_t (scalar_op1, mode));
+         machine_mode scalar_mode = VECTOR_MODE_P (mode)
+                                    ? GET_MODE_INNER (mode) : mode;
+         int shift = wi::exact_log2 (rtx_mode_t (scalar_op1, scalar_mode));
          /* Perfect power of 2 (other than 1, which is handled above).  */
          if (shift > 0)
            return expand_shift (LSHIFT_EXPR, mode, op0,
diff --git a/gcc/testsuite/gcc.dg/torture/pr127474.c 
b/gcc/testsuite/gcc.dg/torture/pr127474.c
new file mode 100644
index 000000000000..76cb4a0c1448
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/pr127474.c
@@ -0,0 +1,11 @@
+/* { dg-do compile } */
+/* { dg-require-effective-target int128 } */
+
+/* Previously we ICE'd in expand_mult when dealing with a CONST_WIDE_INT.  */
+
+typedef __int128 v1ti __attribute__ ((vector_size (16)));
+
+v1ti foo (v1ti x)
+{
+  return x * (v1ti){(__int128)123456789 << 64 | (__int128)123456789};
+}

Reply via email to