[PATCH 0/2] match.pd: recognise abs-difference, plain and promoted
Dominic P <[email protected]>
| Newsgroups | gmane.comp.gcc.patches |
|---|---|
| Message-ID | <[email protected]> |
Two patches recognising the conditional spelling of absolute difference. Patch 1 folds A > B ? A - B : B - A (and the lt/le forms) to abs (A - B) for signed non-wrapping operands: on aarch64 the scalar becomes subs+csneg, and the diamond no longer blocks further simplification. With this series every testcase in the long-open PR50856 folds to abs: both functions from the original report (the promoted-byte one needs patch 2) and all four from comment 4 (f and f3 already fold today; f1 and f2 need patch 1). The PR's Bugzilla dependencies PR111910 and PR114999 concern the general negation-detection and comparison-simplification infrastructure and stand on their own; none of the PR's own testcases needs them once this series is in. Patch 2 extends it to the promoted spelling, which is what C actually produces for sub-int types: the front end narrows the promoted comparison back to the original type, so the compare tests A' and B' while the arms compute (int) A' - (int) B', and patch 1's same-operand pattern cannot match. A strictly widening conversion to the signed result type preserves the comparison's order and the widened difference cannot overflow, so the fold carries over. This is the scalar shape of every byte sum-of-absolute-differences loop: with it, such a loop vectorises through the abd patterns -- on aarch64 the loop body becomes uabdl/uabdl2 where it previously was a compare, two widening-subtract pairs and a select. A same-width conversion is excluded, since reinterpretation changes the comparison's order. Testing. Bootstrapped as a series on x86_64-pc-linux-gnu at trunk 844c665f170 with the stage2/stage3 comparison successful, and a full make -k check run: 228036 gcc, 278459 g++ and 20095 libstdc++ expected passes. Every unexpected result was also present or reproducible with the series reverted, including a pre-existing mdspan dg-error regression (23_containers/mdspan layouts/submdspan, 14 checks over two files) that reproduces with an unpatched compiler at the same revision. The three new tests were additionally run with an arm-none-eabi cross of this exact series: all eleven checks pass, including the five ARM-specific assembler scans. With patch 2's fold reverted and its test kept, the ABS_EXPR scans fail (0 instead of 4). These patches were prepared with the assistance of an AI coding tool, recorded per-patch with Assisted-by:. I reviewed and verified every line, and take responsibility for the result. Dominic P (2): match.pd: recognise A > B ? A - B : B - A as abs (A - B) [PR50856] match.pd: fold the promoted spelling of abs-difference [PR50856] gcc/match.pd | 58 +++++++++++++++++++ gcc/testsuite/gcc.dg/tree-ssa/absdiff-1.c | 12 ++++ .../gcc.dg/tree-ssa/absdiff-widen-1.c | 20 +++++++ gcc/testsuite/gcc.target/arm/pr50856.c | 35 +++++++++++ 4 files changed, 125 insertions(+) create mode 100644 gcc/testsuite/gcc.dg/tree-ssa/absdiff-1.c create mode 100644 gcc/testsuite/gcc.dg/tree-ssa/absdiff-widen-1.c create mode 100644 gcc/testsuite/gcc.target/arm/pr50856.c -- 2.55.0