On Tue, Aug 11, 2026 at 1:13 PM H.J. Lu <[email protected]> wrote: > > "(type) minmax ((wide_type) a, (wide_type) b) to minmax (a, b)" is limited > to the single use of the result. It doesn't support: > > typedef int v2si __attribute__((vector_size (8))); > typedef long long v2di __attribute__((vector_size (16))); > > v2si > func (v2si a, v2si b, v2di *p) > { > v2di x = __builtin_convertvector (a, v2di); > v2di y = __builtin_convertvector (b, v2di); > v2di z = x < y ? x : y; > *p = z; > return __builtin_convertvector (z, v2si); > } > > Change it to > > minmax ((wide_type) a, (wide_type) b) -> (wide_type) minmax (a, b) > > instead and add "(type) ((wide_type) a) -> a" for integer types. Now > we generate > > pminsd %xmm1, %xmm0 > pmovsxdq %xmm0, %xmm1 > movaps %xmm1, (%rdi) > > instead of > > pmovsxdq %xmm0, %xmm2 > pmovsxdq %xmm1, %xmm1 > movdqa %xmm2, %xmm0 > movdqa %xmm2, %xmm3 > pcmpgtq %xmm1, %xmm0 > pblendvb %xmm0, %xmm1, %xmm3 > movdqa %xmm3, %xmm0 > movaps %xmm3, (%rdi) > shufps $232, %xmm3, %xmm0 > > gcc/
(simplify - (convert (minmax:c@4 (convert@2 @0) (convert@3 @1))) + (minmax:c (convert@2 @0) (convert@3 @1)) no need for :c on minmax (if (ANY_INTEGRAL_TYPE_P (type) - && ANY_INTEGRAL_TYPE_P (TREE_TYPE (@2)) - && types_match (type, TREE_TYPE (@0)) - && types_match (type, TREE_TYPE (@1)) - && types_match (TREE_TYPE (@2), TREE_TYPE (@3)) - && element_precision (TREE_TYPE (@2)) > element_precision (type) - && TYPE_UNSIGNED (TREE_TYPE (@2)) == TYPE_UNSIGNED (type) + && ANY_INTEGRAL_TYPE_P (TREE_TYPE (@0)) + && types_match (type, TREE_TYPE (@2)) + && types_match (type, TREE_TYPE (@3)) the last two are redundant + && types_match (TREE_TYPE (@0), TREE_TYPE (@1)) + && element_precision (TREE_TYPE (@0)) < element_precision (type) + && TYPE_UNSIGNED (TREE_TYPE (@0)) == TYPE_UNSIGNED (type) +/* (type) ((wide_type) a) -> a. */ +(simplify + (convert (convert@1 @0)) + (if (ANY_INTEGRAL_TYPE_P (type) + && ANY_INTEGRAL_TYPE_P (TREE_TYPE (@1)) + && types_match (type, TREE_TYPE (@0)) + && element_precision (type) < element_precision (TREE_TYPE (@1))) + @0)) two-level conversions are already handled elsewhere, no need to add a new pattern. Richard. > PR middle-end/126784 > * match.pd ((type) minmax ((wide_type) a, (wide_type) b)): Changed > to ... > (minmax ((wide_type) a, (wide_type) b)): This. > ((type) ((wide_type) a) -> a) New. > > gcc/testsuite/ > > PR middle-end/126784 > * g++.dg/tree-ssa/vec-narrow-1.C: Use -msse4 and require int128 > for x86. > * g++.dg/tree-ssa/vec-narrow-minmax-2.C: Likewise. > * g++.target/i386/pr126784-1.C: New test. > * g++.target/i386/pr126784-2.C: Likewise. > * gcc.target/i386/pr126784-1.c: Likewise. > * gcc.target/i386/pr126784-2.c: Likewise. > * gcc.target/i386/pr126788-1.c: Likewise. > > -- > H.J.
