OK I went with a simpler approach.
// This pseudo is either converted to a regular store or a push which clobbers
// SP.
let Defs = [SP], Uses = [SP], hasSideEffects = 0 in
def STDSPQRr : StorePseudo<(outs), (ins memspi:$dst, GPR8NOZ:$src),
"stdstk\t$dst, $src", [(store i8:$src, addr:$dst)]>;
// This pseudo is either converted to a regular store or a push which clobbers
// SP.
let Defs = [SP], Uses = [SP], hasSideEffects = 0 in
def STDWSPQRr : StorePseudo<(outs), (ins memspi:$dt, DREGSNOZ:$src),
"stdwstk\t$dt, $src", [(store i16:$src, addr:$dt)]>;
Not changed much, defs and uses SP. The main change is I created new register classes for the source input that don’t allow the compiler to use the Z register or its components. Seems to work.
I’ll create a PR shortly. I’ve also raised an issue we can use for tracking it: [AVR] fix issue with PEI pass prolog rewrite under register pressure · Issue #163015 · llvm/llvm-project · GitHub if that’s helpful. If it’s not helpful I’ll just close the issue, otherwise I’ll mark it as closed if/when we get a successfully merged PR that fixes it.
Carl