From cd04e2b8e2de6ce305208f597ce415dbbd732803 Mon Sep 17 00:00:00 2001 From: Akira Hatanaka Date: Fri, 21 Sep 2012 01:08:16 +0000 Subject: [PATCH] Properly save and restore RA and Mips16 callee save registers S0,S1 Patch by Reed Kotler. llvm-svn: 164349 --- llvm/lib/Target/Mips/Mips16FrameLowering.cpp | 40 +++++++++++++++++++++++++++- llvm/lib/Target/Mips/Mips16FrameLowering.h | 5 ++++ llvm/lib/Target/Mips/Mips16InstrInfo.td | 13 +++++---- 3 files changed, 52 insertions(+), 6 deletions(-) diff --git a/llvm/lib/Target/Mips/Mips16FrameLowering.cpp b/llvm/lib/Target/Mips/Mips16FrameLowering.cpp index 030042f..b2583f7 100644 --- a/llvm/lib/Target/Mips/Mips16FrameLowering.cpp +++ b/llvm/lib/Target/Mips/Mips16FrameLowering.cpp @@ -66,7 +66,42 @@ spillCalleeSavedRegisters(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI, const std::vector &CSI, const TargetRegisterInfo *TRI) const { - // FIXME: implement. + MachineFunction *MF = MBB.getParent(); + MachineBasicBlock *EntryBlock = MF->begin(); + const TargetInstrInfo &TII = *MF->getTarget().getInstrInfo(); + + // + // Registers RA, S0,S1 are the callee saved registers and they + // will be saved with the "save" instruction + // during emitPrologue + // + for (unsigned i = 0, e = CSI.size(); i != e; ++i) { + // Add the callee-saved register as live-in. Do not add if the register is + // RA and return address is taken, because it has already been added in + // method MipsTargetLowering::LowerRETURNADDR. + // It's killed at the spill, unless the register is RA and return address + // is taken. + unsigned Reg = CSI[i].getReg(); + bool IsRAAndRetAddrIsTaken = (Reg == Mips::RA) + && MF->getFrameInfo()->isReturnAddressTaken(); + if (!IsRAAndRetAddrIsTaken) + EntryBlock->addLiveIn(Reg); + } + + return true; +} + +bool Mips16FrameLowering::restoreCalleeSavedRegisters(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MI, + const std::vector &CSI, + const TargetRegisterInfo *TRI) const { + // + // Registers RA,S0,S1 are the callee saved registers and they will be restored + // with the restore instruction during emitEpilogue. + // We need to override this virtual function, otherwise llvm will try and + // restore the registers on it's on from the stack. + // + return true; } @@ -79,6 +114,9 @@ Mips16FrameLowering::hasReservedCallFrame(const MachineFunction &MF) const { void Mips16FrameLowering:: processFunctionBeforeCalleeSavedScan(MachineFunction &MF, RegScavenger *RS) const { + MF.getRegInfo().setPhysRegUsed(Mips::RA); + MF.getRegInfo().setPhysRegUsed(Mips::S0); + MF.getRegInfo().setPhysRegUsed(Mips::S1); } const MipsFrameLowering * diff --git a/llvm/lib/Target/Mips/Mips16FrameLowering.h b/llvm/lib/Target/Mips/Mips16FrameLowering.h index 25cc37b..01db71e 100644 --- a/llvm/lib/Target/Mips/Mips16FrameLowering.h +++ b/llvm/lib/Target/Mips/Mips16FrameLowering.h @@ -32,6 +32,11 @@ public: const std::vector &CSI, const TargetRegisterInfo *TRI) const; + bool restoreCalleeSavedRegisters(MachineBasicBlock &MBB, + MachineBasicBlock::iterator MI, + const std::vector &CSI, + const TargetRegisterInfo *TRI) const; + bool hasReservedCallFrame(const MachineFunction &MF) const; void processFunctionBeforeCalleeSavedScan(MachineFunction &MF, diff --git a/llvm/lib/Target/Mips/Mips16InstrInfo.td b/llvm/lib/Target/Mips/Mips16InstrInfo.td index e48e9e4..b0ab464 100644 --- a/llvm/lib/Target/Mips/Mips16InstrInfo.td +++ b/llvm/lib/Target/Mips/Mips16InstrInfo.td @@ -254,10 +254,12 @@ def OrRxRxRy16: FRxRxRy16_ins<0b01101, "or", IIAlu>, ArithLogic16Defs<1>; // for direct object emitter, encoding needs to be adjusted for the // frame size // -let ra=1, s=0,s0=0,s1=0 in +let ra=1, s=0,s0=1,s1=1 in def RestoreRaF16: FI8_SVRS16<0b1, (outs), (ins uimm16:$frame_size), - "restore \t$$ra, $frame_size", [], IILoad >; + "restore \t$$ra, $$s0, $$s1, $frame_size", [], IILoad > { + let isCodeGenOnly = 1; +} // // Format: SAVE {ra,}{s0/s1/s0-1,}{framesize} (All arguments are optional) @@ -266,11 +268,12 @@ def RestoreRaF16: // To set up a stack frame on entry to a subroutine, // saving return address and static registers, and adjusting stack // -let ra=1, s=1,s0=0,s1=0 in +let ra=1, s=1,s0=1,s1=1 in def SaveRaF16: FI8_SVRS16<0b1, (outs), (ins uimm16:$frame_size), - "save \t$$ra, $frame_size", [], IILoad >; - + "save \t$$ra, $$s0, $$s1, $frame_size", [], IILoad > { + let isCodeGenOnly = 1; +} // // Format: SB ry, offset(rx) MIPS16e // Purpose: Store Byte (Extended) -- 2.7.4