| Message ID | 003f01dd3a3e$2aa73f10$7ff5bd30$@nextmovesoftware.com |
|---|---|
| State | New |
| Headers | show |
| Series | [AArch64] Use any_or_plus in movk define_insn pattern. | expand |
> On 1 Sep 2026, at 20:17, Roger Sayle <roger@nextmovesoftware.com> wrote: > > > Many thanks to Linaroo's CI tester (and the folks that run it) for > pointing out that my (upcoming) patch to introduce aop_optab triggers > a testsuite failure on aarch64. The issue is a missed optimization: > the aarch.md backend recognizes the IOR form of movk, but not the > PLUS (or XOR) forms. Easily fixed/avoided with the small change > below. > > As a motivating example, consider the function: > > unsigned int foo(unsigned int x) > { > return (x & ~0xffff) + 0x02; > } > > Currently with gcc -O2, we generate: > > foo: and w0, w0, -65536 > add w0, w0, 2 > ret > > with this patch, we instead generate: > > foo: movk w0, #0x2, lsl 0 > ret > > > This patch has been tested on aarch64-apple-darwin24.3.0 (using > iains' fork) with make bootstrap and make -k check with no new > failures. Ok for mainline? > Nice, ok. Thanks, Kyrill > > 2026-09-01 Roger Sayle <roger@nextmovesoftware.com> > > gcc/ChangeLog > * config/aarch64/aarch64.md (*aarch_movk<mode>): Prepend asterisk. > Use any_or_plus iterator to also recognize PLUS and XOR forms. > > gcc/testsuite/ChangeLog > * gcc.target/aarch64/movk_4.c: New test case. > > > Thank in advance, > Roger > -- > > <patchaa.txt>
diff --git a/gcc/config/aarch64/aarch64.md b/gcc/config/aarch64/aarch64.md index 8e844beaee9..b3452d89989 100644 --- a/gcc/config/aarch64/aarch64.md +++ b/gcc/config/aarch64/aarch64.md @@ -1915,11 +1915,12 @@ ) ;; Match MOVK as a normal AND and IOR operation. -(define_insn "aarch64_movk<mode>" +(define_insn "*aarch64_movk<mode>" [(set (match_operand:GPI 0 "register_operand" "=r") - (ior:GPI (and:GPI (match_operand:GPI 1 "register_operand" "0") - (match_operand:GPI 2 "const_int_operand")) - (match_operand:GPI 3 "const_int_operand")))] + (any_or_plus:GPI + (and:GPI (match_operand:GPI 1 "register_operand" "0") + (match_operand:GPI 2 "const_int_operand")) + (match_operand:GPI 3 "const_int_operand")))] "aarch64_movk_shift (rtx_mode_t (operands[2], <MODE>mode), rtx_mode_t (operands[3], <MODE>mode)) >= 0" { diff --git a/gcc/testsuite/gcc.target/aarch64/movk_4.c b/gcc/testsuite/gcc.target/aarch64/movk_4.c new file mode 100644 index 00000000000..1173e58cf0f --- /dev/null +++ b/gcc/testsuite/gcc.target/aarch64/movk_4.c @@ -0,0 +1,12 @@ +/* { dg-do compile } */ +/* { dg-options "-O2" } */ + +unsigned int iorhi(unsigned int x) { return (x & 0xffff) | 0x20000; } +unsigned int xorhi(unsigned int x) { return (x & 0xffff) ^ 0x20000; } +unsigned int addhi(unsigned int x) { return (x & 0xffff) + 0x20000; } + +unsigned int iorlo(unsigned int x) { return (x & ~0xffff) | 0x02; } +unsigned int xorlo(unsigned int x) { return (x & ~0xffff) ^ 0x02; } +unsigned int addlo(unsigned int x) { return (x & ~0xffff) + 0x02; } + +/* { dg-final { scan-assembler-times "movk\t" 6 } } */
Many thanks to Linaroo's CI tester (and the folks that run it) for pointing out that my (upcoming) patch to introduce aop_optab triggers a testsuite failure on aarch64. The issue is a missed optimization: the aarch.md backend recognizes the IOR form of movk, but not the PLUS (or XOR) forms. Easily fixed/avoided with the small change below. As a motivating example, consider the function: unsigned int foo(unsigned int x) { return (x & ~0xffff) + 0x02; } Currently with gcc -O2, we generate: foo: and w0, w0, -65536 add w0, w0, 2 ret with this patch, we instead generate: foo: movk w0, #0x2, lsl 0 ret This patch has been tested on aarch64-apple-darwin24.3.0 (using iains' fork) with make bootstrap and make -k check with no new failures. Ok for mainline? 2026-09-01 Roger Sayle <roger@nextmovesoftware.com> gcc/ChangeLog * config/aarch64/aarch64.md (*aarch_movk<mode>): Prepend asterisk. Use any_or_plus iterator to also recognize PLUS and XOR forms. gcc/testsuite/ChangeLog * gcc.target/aarch64/movk_4.c: New test case. Thank in advance, Roger --