diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfo.td b/llvm/lib/Target/RISCV/RISCVInstrInfo.td --- a/llvm/lib/Target/RISCV/RISCVInstrInfo.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfo.td @@ -1195,43 +1195,35 @@ let Uses = Regs; } -class WriteSysReg Regs> - : Pseudo<(outs), (ins GPR:$val), - [(riscv_write_csr (XLenVT SR.Encoding), GPR:$val)]>, - PseudoInstExpansion<(CSRRW X0, SR.Encoding, GPR:$val)> { - let hasSideEffects = 0; - let Defs = Regs; -} - -class WriteSysRegImm Regs> - : Pseudo<(outs), (ins uimm5:$val), - [(riscv_write_csr (XLenVT SR.Encoding), uimm5:$val)]>, - PseudoInstExpansion<(CSRRWI X0, SR.Encoding, uimm5:$val)> { - let hasSideEffects = 0; - let Defs = Regs; -} - -class SwapSysReg Regs> - : Pseudo<(outs GPR:$rd), (ins GPR:$val), - [(set GPR:$rd, (riscv_swap_csr (XLenVT SR.Encoding), GPR:$val))]>, - PseudoInstExpansion<(CSRRW GPR:$rd, SR.Encoding, GPR:$val)> { - let hasSideEffects = 0; - let Uses = Regs; - let Defs = Regs; +// Need to use GPRNoX0 for $val to prevent X0 copies coalescing into this +// causing it to become CSRRW x0, x0 which is a NOP. +multiclass WriteSysReg Regs> { + let hasSideEffects = 0, Defs = Regs in { + def NAME : Pseudo<(outs), (ins GPRNoX0:$val), + [(riscv_write_csr (XLenVT SR.Encoding), GPRNoX0:$val)]>, + PseudoInstExpansion<(CSRRW X0, SR.Encoding, GPR:$val)>; + def Imm : Pseudo<(outs), (ins uimm5:$val), + [(riscv_write_csr (XLenVT SR.Encoding), uimm5:$val)]>, + PseudoInstExpansion<(CSRRWI X0, SR.Encoding, uimm5:$val)>; + } } -class SwapSysRegImm Regs> - : Pseudo<(outs GPR:$rd), (ins uimm5:$val), - [(set GPR:$rd, (riscv_swap_csr (XLenVT SR.Encoding), uimm5:$val))]>, - PseudoInstExpansion<(CSRRWI GPR:$rd, SR.Encoding, uimm5:$val)> { - let hasSideEffects = 0; - let Uses = Regs; - let Defs = Regs; +// Need to use GPRNoX0 for $val to prevent copies from X0 coalescing into this +// causing it to become CSRRW rd, x0 which will not write the CSR. +multiclass SwapSysReg Regs> { + let hasSideEffects = 0, Uses = Regs, Defs = Regs in { + def NAME : Pseudo<(outs GPR:$rd), (ins GPRNoX0:$val), + [(set GPR:$rd, + (riscv_swap_csr (XLenVT SR.Encoding), GPRNoX0:$val))]>, + PseudoInstExpansion<(CSRRW GPR:$rd, SR.Encoding, GPR:$val)>; + def Imm : Pseudo<(outs GPR:$rd), (ins uimm5:$val), + [(set GPR:$rd, + (riscv_swap_csr (XLenVT SR.Encoding), uimm5:$val))]>; + } } def ReadFRM : ReadSysReg; -def WriteFRM : WriteSysReg; -def WriteFRMImm : WriteSysRegImm; +defm WriteFRM : WriteSysReg; /// Other pseudo-instructions