Am 09.07.25 um 15:48 schrieb Stefan Schulze Frielinghaus:
This is a follow-up to
https://gcc.gnu.org/pipermail/gcc-patches/2025-May/684181.html
I added the last missing pieces namely changelogs, and bootstrapped and
regtested on
aarch64-unknown-linux-gnu
powerpc64le-unknown-linux-gnu
s390x-ibm-linux-gnu
x86_64-pc-linux-gnu
Hi Stefan,
In there additional work needed on the backend side in order to
make HRCs work?
What I am trying is the get rid of the explicit hard regs in
the avr backend, but using HRCs runs into ICE with the attached
patch for
long do_swap32 (long x)
{
return __builtin_bswap32 (x);
}
$ avr-gcc asm.c -S -Os -dp -mmcu=avr4
asm.c: In function 'do_swap32':
asm.c:4:1: error: unable to find a register to spill
4 | }
| ^
asm.c:4:1: error: this is the insn:
(insn 6 17 16 2 (set (reg:SI 50 [orig:44 _2 ] [44])
(bswap:SI (reg:SI 51 [orig:48 x ] [48]))) "asm.c":3:12 1052
{bswapsi2}
(expr_list:REG_DEAD (reg:SI 51 [orig:48 x ] [48])
(nil)))
during RTL pass: reload
asm.c:4:1: internal compiler error: in lra_split_hard_reg_for, at
lra-assigns.cc:1863
Similarly, inline asm with HRCs runs into ICE, too:
// x comes in in r22..r25.
char foo (long x)
{
char y;
// x occupies r22..r25.
// y occupies r24.
__asm ("; %0 = inline_asm(%1)" : "={r24}" (y) : "{r22}" (x));
// Return in r24.
return y;
}
$ avr-gcc asm.c -S -Os -dp -mmcu=avr4
asm.c: In function 'foo':
asm.c:7:5: error: 'asm' operand has impossible constraints or there are
not enough registers
7 | __asm ("; %0 = inline_asm(%1)" : "={r24}" (y) : "{r22}" (x));
| ^~~~~
With "int x" instead of "long x" it compiles fine.
Johann
Via cross compilers I verified the new tests for
arm-linux-gnueabi
i686-linux-gnueabi
powerpc-linux-gnu
riscv32-linux-gnu
riscv64-linux-gnu
Despite that I removed overloads for parse_{input,output}_constraint()
by passing a null pointer explicitly. Furthermore, in case of register
pairs, if two constraints of operands overlap, error out and report the
overlapped register. For example, on aarch64
svuint32x2_t x, y;
asm ("" : "={z5}" (x), "={z6}" (y));
previously I used the register as is of the first constraint in the
error message which is imprecise/misleading. Now, I error out reporting
multiple outputs to register z6/v6, i.e., the actual overlapped one, and
not z5/v5 as previously.
Although I found a lot of corner cases during development via
-fdemote-register-asm I removed it from this patch series. I
compiled and used the Linux kernel and glibc successfully with it for
s390x. For x86_64, the Linux kernel compiles fine, too, except of one
small manual change. For powerpc64le, I ran into an odd case compiling
glibc which I would like to understand in more detail. Since register
asm is not as strict as hard register constraints, for a full fledged
implementation I need to consider more corner cases. Therefore, I would
like to spend some more time on this before I push this new feature.
In total no huge changes. Still ok for mainline?
Stefan Schulze Frielinghaus (3):
Hard register constraints
Error handling for hard register constraints
genoutput: Verify hard register constraints
gcc/ada/gcc-interface/trans.cc | 9 +-
gcc/analyzer/region-model-asm.cc | 7 +-
gcc/c/c-typeck.cc | 6 +-
gcc/cfgexpand.cc | 53 +---
gcc/config/cris/cris.cc | 6 +-
gcc/config/i386/i386.cc | 6 +
gcc/config/s390/s390.cc | 11 +-
gcc/cp/semantics.cc | 6 +-
gcc/d/toir.cc | 6 +-
gcc/doc/extend.texi | 162 ++++++++++
gcc/doc/md.texi | 6 +
gcc/function.cc | 116 ++++++++
gcc/genoutput.cc | 60 ++++
gcc/genpreds.cc | 4 +-
gcc/gimple-walk.cc | 11 +-
gcc/gimplify-me.cc | 5 +-
gcc/gimplify.cc | 142 ++++++++-
gcc/gimplify_reg_info.h | 182 ++++++++++++
gcc/ira.cc | 84 +++++-
gcc/lra-constraints.cc | 13 +
gcc/output.h | 2 +
gcc/recog.cc | 11 +-
gcc/stmt.cc | 277 +++++++++++++++++-
gcc/stmt.h | 9 +-
gcc/testsuite/gcc.dg/asm-hard-reg-1.c | 85 ++++++
gcc/testsuite/gcc.dg/asm-hard-reg-2.c | 33 +++
gcc/testsuite/gcc.dg/asm-hard-reg-3.c | 25 ++
gcc/testsuite/gcc.dg/asm-hard-reg-4.c | 50 ++++
gcc/testsuite/gcc.dg/asm-hard-reg-5.c | 36 +++
gcc/testsuite/gcc.dg/asm-hard-reg-6.c | 60 ++++
gcc/testsuite/gcc.dg/asm-hard-reg-7.c | 41 +++
gcc/testsuite/gcc.dg/asm-hard-reg-8.c | 49 ++++
gcc/testsuite/gcc.dg/asm-hard-reg-error-1.c | 83 ++++++
gcc/testsuite/gcc.dg/asm-hard-reg-error-2.c | 26 ++
gcc/testsuite/gcc.dg/asm-hard-reg-error-3.c | 27 ++
gcc/testsuite/gcc.dg/asm-hard-reg-error-4.c | 21 ++
gcc/testsuite/gcc.dg/asm-hard-reg-error-5.c | 13 +
gcc/testsuite/gcc.dg/pr87600-2.c | 19 --
gcc/testsuite/gcc.dg/pr87600-3.c | 26 ++
.../gcc.target/aarch64/asm-hard-reg-1.c | 55 ++++
.../gcc.target/aarch64/asm-hard-reg-2.c | 17 ++
.../gcc.target/i386/asm-hard-reg-1.c | 80 +++++
.../gcc.target/i386/asm-hard-reg-2.c | 43 +++
.../gcc.target/s390/asm-hard-reg-1.c | 103 +++++++
.../gcc.target/s390/asm-hard-reg-2.c | 43 +++
.../gcc.target/s390/asm-hard-reg-3.c | 42 +++
.../gcc.target/s390/asm-hard-reg-4.c | 6 +
.../gcc.target/s390/asm-hard-reg-5.c | 6 +
.../gcc.target/s390/asm-hard-reg-6.c | 152 ++++++++++
.../gcc.target/s390/asm-hard-reg-7.c | 34 +++
.../gcc.target/s390/asm-hard-reg-longdouble.h | 18 ++
gcc/testsuite/lib/scanasm.exp | 4 +
gcc/toplev.cc | 4 +
gcc/tree-ssa-operands.cc | 4 +-
gcc/tree-ssa-structalias.cc | 4 +-
gcc/varasm.cc | 5 +-
56 files changed, 2283 insertions(+), 125 deletions(-)
create mode 100644 gcc/gimplify_reg_info.h
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-1.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-2.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-3.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-4.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-5.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-6.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-7.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-8.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-error-1.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-error-2.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-error-3.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-error-4.c
create mode 100644 gcc/testsuite/gcc.dg/asm-hard-reg-error-5.c
create mode 100644 gcc/testsuite/gcc.dg/pr87600-3.c
create mode 100644 gcc/testsuite/gcc.target/aarch64/asm-hard-reg-1.c
create mode 100644 gcc/testsuite/gcc.target/aarch64/asm-hard-reg-2.c
create mode 100644 gcc/testsuite/gcc.target/i386/asm-hard-reg-1.c
create mode 100644 gcc/testsuite/gcc.target/i386/asm-hard-reg-2.c
create mode 100644 gcc/testsuite/gcc.target/s390/asm-hard-reg-1.c
create mode 100644 gcc/testsuite/gcc.target/s390/asm-hard-reg-2.c
create mode 100644 gcc/testsuite/gcc.target/s390/asm-hard-reg-3.c
create mode 100644 gcc/testsuite/gcc.target/s390/asm-hard-reg-4.c
create mode 100644 gcc/testsuite/gcc.target/s390/asm-hard-reg-5.c
create mode 100644 gcc/testsuite/gcc.target/s390/asm-hard-reg-6.c
create mode 100644 gcc/testsuite/gcc.target/s390/asm-hard-reg-7.c
create mode 100644 gcc/testsuite/gcc.target/s390/asm-hard-reg-longdouble.h
diff --git a/gcc/config/avr/avr.md b/gcc/config/avr/avr.md
index f8bbdc76608..015cc3b6e4b 100644
--- a/gcc/config/avr/avr.md
+++ b/gcc/config/avr/avr.md
@@ -9619,17 +9619,9 @@ (define_insn "copysignsf3"
;; Swap Bytes (change byte-endianness)
-(define_expand "bswapsi2"
- [(set (reg:SI 22)
- (match_operand:SI 1 "register_operand" ""))
- (set (reg:SI 22)
- (bswap:SI (reg:SI 22)))
- (set (match_operand:SI 0 "register_operand" "")
- (reg:SI 22))])
-
-(define_insn_and_split "*bswapsi2.libgcc_split"
- [(set (reg:SI 22)
- (bswap:SI (reg:SI 22)))]
+(define_insn_and_split "bswapsi2"
+ [(set (match_operand:SI 0 "register_operand" "={r22}")
+ (bswap:SI (match_operand:SI 1 "register_operand" "{r22}")))]
""
"#"
"&& reload_completed"