[llvm-commits] [llvm] r160031 - in /llvm/trunk: lib/Target/Mips/MipsFrameLowering.cpp lib/Target/Mips/MipsISelLowering.cpp lib/Target/Mips/MipsISelLowering.h test/CodeGen/Mips/return_address.ll

Akira Hatanaka ahatanaka at mips.com
Tue Jul 10 17:53:32 PDT 2012


Author: ahatanak
Date: Tue Jul 10 19:53:32 2012
New Revision: 160031

URL: http://llvm.org/viewvc/llvm-project?rev=160031&view=rev
Log:
Lower RETURNADDR node in Mips backend.

Patch by Sasa Stankovic.

Added:
    llvm/trunk/test/CodeGen/Mips/return_address.ll
Modified:
    llvm/trunk/lib/Target/Mips/MipsFrameLowering.cpp
    llvm/trunk/lib/Target/Mips/MipsISelLowering.cpp
    llvm/trunk/lib/Target/Mips/MipsISelLowering.h

Modified: llvm/trunk/lib/Target/Mips/MipsFrameLowering.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/MipsFrameLowering.cpp?rev=160031&r1=160030&r2=160031&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/MipsFrameLowering.cpp (original)
+++ llvm/trunk/lib/Target/Mips/MipsFrameLowering.cpp Tue Jul 10 19:53:32 2012
@@ -273,14 +273,21 @@
   const TargetInstrInfo &TII = *MF->getTarget().getInstrInfo();
 
   for (unsigned i = 0, e = CSI.size(); i != e; ++i) {
-    // Add the callee-saved register as live-in.
-    // It's killed at the spill.
-    EntryBlock->addLiveIn(CSI[i].getReg());
+    // 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 || Reg == Mips::RA_64)
+        && MF->getFrameInfo()->isReturnAddressTaken();
+    if (!IsRAAndRetAddrIsTaken)
+      EntryBlock->addLiveIn(Reg);
 
     // Insert the spill to the stack frame.
-    unsigned Reg = CSI[i].getReg();
+    bool IsKill = !IsRAAndRetAddrIsTaken;
     const TargetRegisterClass *RC = TRI->getMinimalPhysRegClass(Reg);
-    TII.storeRegToStackSlot(*EntryBlock, MI, Reg, true,
+    TII.storeRegToStackSlot(*EntryBlock, MI, Reg, IsKill,
                             CSI[i].getFrameIdx(), RC, TRI);
   }
 

Modified: llvm/trunk/lib/Target/Mips/MipsISelLowering.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/MipsISelLowering.cpp?rev=160031&r1=160030&r2=160031&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/MipsISelLowering.cpp (original)
+++ llvm/trunk/lib/Target/Mips/MipsISelLowering.cpp Tue Jul 10 19:53:32 2012
@@ -806,6 +806,7 @@
     case ISD::FCOPYSIGN:          return LowerFCOPYSIGN(Op, DAG);
     case ISD::FABS:               return LowerFABS(Op, DAG);
     case ISD::FRAMEADDR:          return LowerFRAMEADDR(Op, DAG);
+    case ISD::RETURNADDR:         return LowerRETURNADDR(Op, DAG);
     case ISD::MEMBARRIER:         return LowerMEMBARRIER(Op, DAG);
     case ISD::ATOMIC_FENCE:       return LowerATOMIC_FENCE(Op, DAG);
     case ISD::SHL_PARTS:          return LowerShiftLeftParts(Op, DAG);
@@ -2009,6 +2010,23 @@
   return FrameAddr;
 }
 
+SDValue MipsTargetLowering::LowerRETURNADDR(SDValue Op,
+                                            SelectionDAG &DAG) const {
+  // check the depth
+  assert((cast<ConstantSDNode>(Op.getOperand(0))->getZExtValue() == 0) &&
+         "Return address can be determined only for current frame.");
+
+  MachineFunction &MF = DAG.getMachineFunction();
+  MachineFrameInfo *MFI = MF.getFrameInfo();
+  EVT VT = Op.getValueType();
+  unsigned RA = IsN64 ? Mips::RA_64 : Mips::RA;
+  MFI->setReturnAddressIsTaken(true);
+
+  // Return RA, which contains the return address. Mark it an implicit live-in.
+  unsigned Reg = MF.addLiveIn(RA, getRegClassFor(VT));
+  return DAG.getCopyFromReg(DAG.getEntryNode(), Op.getDebugLoc(), Reg, VT);
+}
+
 // TODO: set SType according to the desired memory barrier behavior.
 SDValue
 MipsTargetLowering::LowerMEMBARRIER(SDValue Op, SelectionDAG &DAG) const {

Modified: llvm/trunk/lib/Target/Mips/MipsISelLowering.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/MipsISelLowering.h?rev=160031&r1=160030&r2=160031&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/MipsISelLowering.h (original)
+++ llvm/trunk/lib/Target/Mips/MipsISelLowering.h Tue Jul 10 19:53:32 2012
@@ -143,6 +143,7 @@
     SDValue LowerFCOPYSIGN(SDValue Op, SelectionDAG &DAG) const;
     SDValue LowerFABS(SDValue Op, SelectionDAG &DAG) const;
     SDValue LowerFRAMEADDR(SDValue Op, SelectionDAG &DAG) const;
+    SDValue LowerRETURNADDR(SDValue Op, SelectionDAG &DAG) const;
     SDValue LowerMEMBARRIER(SDValue Op, SelectionDAG& DAG) const;
     SDValue LowerATOMIC_FENCE(SDValue Op, SelectionDAG& DAG) const;
     SDValue LowerShiftLeftParts(SDValue Op, SelectionDAG& DAG) const;

Added: llvm/trunk/test/CodeGen/Mips/return_address.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/Mips/return_address.ll?rev=160031&view=auto
==============================================================================
--- llvm/trunk/test/CodeGen/Mips/return_address.ll (added)
+++ llvm/trunk/test/CodeGen/Mips/return_address.ll Tue Jul 10 19:53:32 2012
@@ -0,0 +1,23 @@
+; RUN: llc -march=mipsel < %s | FileCheck %s
+
+define i8* @f1() nounwind {
+entry:
+  %0 = call i8* @llvm.returnaddress(i32 0)
+  ret i8* %0
+
+; CHECK:    addu    $2, $zero, $ra
+}
+
+define i8* @f2() nounwind {
+entry:
+  call void @g()
+  %0 = call i8* @llvm.returnaddress(i32 0)
+  ret i8* %0
+
+; CHECK:    addu    $[[R0:[0-9]+]], $zero, $ra
+; CHECK:    jal
+; CHECK:    addu    $2,  $zero, $[[R0]]
+}
+
+declare i8* @llvm.returnaddress(i32) nounwind readnone
+declare void @g()





More information about the llvm-commits mailing list