https://gcc.gnu.org/g:88752b86ff1af4589c61d5bd8592b17e481ab596
commit r17-2159-g88752b86ff1af4589c61d5bd8592b17e481ab596 Author: Roger Sayle <[email protected]> Date: Sun Jul 5 21:19:17 2026 +0100 aarch64: [PR126094] Update aarch64_cmtst* patterns for new simplifications. The recent patch to simplify/canonicalize (not (neg (eq x y))) as (neg (ne x y)) [when the relevant STORE_FLAG_VALUE is 1] causes aarch64's aarch64_cmtst* patterns to fail as they were expecting the old canonical RTL. This patch adds the new canonical forms to aarch64-simd.md which corrects the testsuite failure of gcc.target/aarch64/mvn-cmeq0-1.c. Sorry for any inconvenience. 2026-07-05 Roger Sayle <[email protected]> gcc/ChangeLog PR target/126094 * config/aarch64/aarch64-simd.md (aarch64_cmtst<mode><vczle><vczbe>): Update pattern to match recent RTL simplification. (*aarch64_cmtst<mode><vczle><vczbe>): Preserve the original. (*aarch64_cmtst_same_<mode><vczle><vczbe>): Additional variant. Diff: --- gcc/config/aarch64/aarch64-simd.md | 36 +++++++++++++++++++++++++++++++----- 1 file changed, 31 insertions(+), 5 deletions(-) diff --git a/gcc/config/aarch64/aarch64-simd.md b/gcc/config/aarch64/aarch64-simd.md index 94fb49a338b3..23a8a47263ae 100644 --- a/gcc/config/aarch64/aarch64-simd.md +++ b/gcc/config/aarch64/aarch64-simd.md @@ -8002,13 +8002,23 @@ ;; cmtst +(define_insn "aarch64_cmtst<mode><vczle><vczbe>" + [(set (match_operand:<V_INT_EQUIV> 0 "register_operand" "=w") + (neg:<V_INT_EQUIV> + (ne:<V_INT_EQUIV> + (and:VDQ_I + (match_operand:VDQ_I 1 "register_operand" "w") + (match_operand:VDQ_I 2 "register_operand" "w")) + (match_operand:VDQ_I 3 "aarch64_simd_imm_zero")))) + ] + "TARGET_SIMD" + "cmtst\t%<v>0<Vmtype>, %<v>1<Vmtype>, %<v>2<Vmtype>" + [(set_attr "type" "neon_tst<q>")] +) ;; Although neg (ne (and x y) 0) is the natural way of expressing a cmtst, -;; we don't have any insns using ne, and aarch64_vcond outputs -;; not (neg (eq (and x y) 0)) -;; which is rewritten by simplify_rtx as -;; plus (eq (and x y) 0) -1. +;; earlier versions of GCC simplified this as plus (eq (and x y) 0) -1. -(define_insn "aarch64_cmtst<mode><vczle><vczbe>" +(define_insn "*aarch64_cmtst<mode><vczle><vczbe>" [(set (match_operand:<V_INT_EQUIV> 0 "register_operand" "=w") (plus:<V_INT_EQUIV> (eq:<V_INT_EQUIV> @@ -8023,6 +8033,22 @@ [(set_attr "type" "neon_tst<q>")] ) +;; One can also get a cmtsts by having to combine a +;; neg (ne x 0) in which case you rewrite it to +;; a comparison against itself + +(define_insn "*aarch64_cmtst_same_<mode><vczle><vczbe>" + [(set (match_operand:<V_INT_EQUIV> 0 "register_operand" "=w") + (neg:<V_INT_EQUIV> + (ne:<V_INT_EQUIV> + (match_operand:VDQ_I 1 "register_operand" "w") + (match_operand:VDQ_I 2 "aarch64_simd_imm_zero")))) + ] + "TARGET_SIMD" + "cmtst\t%<v>0<Vmtype>, %<v>1<Vmtype>, %<v>1<Vmtype>" + [(set_attr "type" "neon_tst<q>")] +) + ;; One can also get a cmtsts by having to combine a ;; not (neq (eq x 0)) in which case you rewrite it to ;; a comparison against itself
