On 8/5/2026 9:59 AM, Matt Turner wrote:
exception_receiver and builtin_setjmp_receiver split into an ldah/lda
pair that shares a !gpdisp relocation sequence number, so the two insns
have to stay in 1-1 correspondence. The first half is an unspec_volatile
(*ldgp_er_1), but the second half was a plain unspec (*ldgp_er_2), which
makes the halves unequally deletable: once the landing pad turns out not
to use $29, the DCE run at the start of the peephole2 pass removes the
lda and leaves the ldah behind. The assembler then rejects the result:
Error: No lda !gpdisp!1188 was found
Compiling C++ with -fassume-sane-operators-new-delete, which is the
default, makes this much easier to hit, since it lets more of the cleanup
code in a landing pad be optimized away.
Add an unspec_volatile variant of *ldgp_er_2 and use it for both
receivers. The gpdisp pair emitted after a call needs no such treatment:
there the ldah is part of the call insn and both halves are plain
unspecs, so they are deleted together.
gcc/ChangeLog:
PR target/124495
* config/alpha/alpha.md (UNSPECV_LDGP2): New unspec_volatile.
(*ldgp_er_2_v): New insn.
(*builtin_setjmp_receiver_1): Split the second half of the gpdisp
pair to it instead of *ldgp_er_2.
(*exception_receiver_1): Ditto.
gcc/testsuite/ChangeLog:
PR target/124495
* g++.target/alpha/pr124495.C: New test.
Oh the irony given I'm looking at a RISC-V patch that at first glance
seems to have some of the same kinds of problems that this patch is
trying to fix on the Alpha :-) At least i this case it's limited in scope.
I'll push this momentarily. THanks.
jeff