mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-04-06 09:44:39 +00:00
[mips] Rewrite MipsTargetLowering::getAddr functions as template functions.
No intended functionality change. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@191546 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
685707c28e
commit
200a7434f6
@ -474,7 +474,9 @@ getOpndList(SmallVectorImpl<SDValue> &Ops,
|
||||
if (NeedMips16Helper) {
|
||||
RegsToPass.push_front(std::make_pair(V0Reg, Callee));
|
||||
JumpTarget = DAG.getExternalSymbol(Mips16HelperFunction, getPointerTy());
|
||||
JumpTarget = getAddrGlobal(JumpTarget, DAG, MipsII::MO_GOT);
|
||||
JumpTarget = getAddrGlobal(cast<ExternalSymbolSDNode>(JumpTarget),
|
||||
JumpTarget.getValueType(), DAG,
|
||||
MipsII::MO_GOT);
|
||||
} else
|
||||
RegsToPass.push_front(std::make_pair((unsigned)Mips::T9, Callee));
|
||||
}
|
||||
|
@ -80,72 +80,35 @@ SDValue MipsTargetLowering::getGlobalReg(SelectionDAG &DAG, EVT Ty) const {
|
||||
return DAG.getRegister(FI->getGlobalBaseReg(), Ty);
|
||||
}
|
||||
|
||||
static SDValue getTargetNode(SDValue Op, SelectionDAG &DAG, unsigned Flag) {
|
||||
EVT Ty = Op.getValueType();
|
||||
|
||||
if (GlobalAddressSDNode *N = dyn_cast<GlobalAddressSDNode>(Op))
|
||||
return DAG.getTargetGlobalAddress(N->getGlobal(), SDLoc(Op), Ty, 0,
|
||||
Flag);
|
||||
if (ExternalSymbolSDNode *N = dyn_cast<ExternalSymbolSDNode>(Op))
|
||||
return DAG.getTargetExternalSymbol(N->getSymbol(), Ty, Flag);
|
||||
if (BlockAddressSDNode *N = dyn_cast<BlockAddressSDNode>(Op))
|
||||
return DAG.getTargetBlockAddress(N->getBlockAddress(), Ty, 0, Flag);
|
||||
if (JumpTableSDNode *N = dyn_cast<JumpTableSDNode>(Op))
|
||||
return DAG.getTargetJumpTable(N->getIndex(), Ty, Flag);
|
||||
if (ConstantPoolSDNode *N = dyn_cast<ConstantPoolSDNode>(Op))
|
||||
return DAG.getTargetConstantPool(N->getConstVal(), Ty, N->getAlignment(),
|
||||
N->getOffset(), Flag);
|
||||
|
||||
llvm_unreachable("Unexpected node type.");
|
||||
return SDValue();
|
||||
}
|
||||
|
||||
static SDValue getAddrNonPIC(SDValue Op, SelectionDAG &DAG) {
|
||||
SDLoc DL(Op);
|
||||
EVT Ty = Op.getValueType();
|
||||
SDValue Hi = getTargetNode(Op, DAG, MipsII::MO_ABS_HI);
|
||||
SDValue Lo = getTargetNode(Op, DAG, MipsII::MO_ABS_LO);
|
||||
return DAG.getNode(ISD::ADD, DL, Ty,
|
||||
DAG.getNode(MipsISD::Hi, DL, Ty, Hi),
|
||||
DAG.getNode(MipsISD::Lo, DL, Ty, Lo));
|
||||
}
|
||||
|
||||
SDValue MipsTargetLowering::getAddrLocal(SDValue Op, SelectionDAG &DAG,
|
||||
bool HasMips64) const {
|
||||
SDLoc DL(Op);
|
||||
EVT Ty = Op.getValueType();
|
||||
unsigned GOTFlag = HasMips64 ? MipsII::MO_GOT_PAGE : MipsII::MO_GOT;
|
||||
SDValue GOT = DAG.getNode(MipsISD::Wrapper, DL, Ty, getGlobalReg(DAG, Ty),
|
||||
getTargetNode(Op, DAG, GOTFlag));
|
||||
SDValue Load = DAG.getLoad(Ty, DL, DAG.getEntryNode(), GOT,
|
||||
MachinePointerInfo::getGOT(), false, false, false,
|
||||
0);
|
||||
unsigned LoFlag = HasMips64 ? MipsII::MO_GOT_OFST : MipsII::MO_ABS_LO;
|
||||
SDValue Lo = DAG.getNode(MipsISD::Lo, DL, Ty, getTargetNode(Op, DAG, LoFlag));
|
||||
return DAG.getNode(ISD::ADD, DL, Ty, Load, Lo);
|
||||
}
|
||||
|
||||
SDValue MipsTargetLowering::getAddrGlobal(SDValue Op, SelectionDAG &DAG,
|
||||
SDValue MipsTargetLowering::getTargetNode(GlobalAddressSDNode *N, EVT Ty,
|
||||
SelectionDAG &DAG,
|
||||
unsigned Flag) const {
|
||||
SDLoc DL(Op);
|
||||
EVT Ty = Op.getValueType();
|
||||
SDValue Tgt = DAG.getNode(MipsISD::Wrapper, DL, Ty, getGlobalReg(DAG, Ty),
|
||||
getTargetNode(Op, DAG, Flag));
|
||||
return DAG.getLoad(Ty, DL, DAG.getEntryNode(), Tgt,
|
||||
MachinePointerInfo::getGOT(), false, false, false, 0);
|
||||
return DAG.getTargetGlobalAddress(N->getGlobal(), SDLoc(N), Ty, 0, Flag);
|
||||
}
|
||||
|
||||
SDValue MipsTargetLowering::getAddrGlobalLargeGOT(SDValue Op, SelectionDAG &DAG,
|
||||
unsigned HiFlag,
|
||||
unsigned LoFlag) const {
|
||||
SDLoc DL(Op);
|
||||
EVT Ty = Op.getValueType();
|
||||
SDValue Hi = DAG.getNode(MipsISD::Hi, DL, Ty, getTargetNode(Op, DAG, HiFlag));
|
||||
Hi = DAG.getNode(ISD::ADD, DL, Ty, Hi, getGlobalReg(DAG, Ty));
|
||||
SDValue Wrapper = DAG.getNode(MipsISD::Wrapper, DL, Ty, Hi,
|
||||
getTargetNode(Op, DAG, LoFlag));
|
||||
return DAG.getLoad(Ty, DL, DAG.getEntryNode(), Wrapper,
|
||||
MachinePointerInfo::getGOT(), false, false, false, 0);
|
||||
SDValue MipsTargetLowering::getTargetNode(ExternalSymbolSDNode *N, EVT Ty,
|
||||
SelectionDAG &DAG,
|
||||
unsigned Flag) const {
|
||||
return DAG.getTargetExternalSymbol(N->getSymbol(), Ty, Flag);
|
||||
}
|
||||
|
||||
SDValue MipsTargetLowering::getTargetNode(BlockAddressSDNode *N, EVT Ty,
|
||||
SelectionDAG &DAG,
|
||||
unsigned Flag) const {
|
||||
return DAG.getTargetBlockAddress(N->getBlockAddress(), Ty, 0, Flag);
|
||||
}
|
||||
|
||||
SDValue MipsTargetLowering::getTargetNode(JumpTableSDNode *N, EVT Ty,
|
||||
SelectionDAG &DAG,
|
||||
unsigned Flag) const {
|
||||
return DAG.getTargetJumpTable(N->getIndex(), Ty, Flag);
|
||||
}
|
||||
|
||||
SDValue MipsTargetLowering::getTargetNode(ConstantPoolSDNode *N, EVT Ty,
|
||||
SelectionDAG &DAG,
|
||||
unsigned Flag) const {
|
||||
return DAG.getTargetConstantPool(N->getConstVal(), Ty, N->getAlignment(),
|
||||
N->getOffset(), Flag);
|
||||
}
|
||||
|
||||
const char *MipsTargetLowering::getTargetNodeName(unsigned Opcode) const {
|
||||
@ -1478,7 +1441,9 @@ SDValue MipsTargetLowering::lowerGlobalAddress(SDValue Op,
|
||||
SelectionDAG &DAG) const {
|
||||
// FIXME there isn't actually debug info here
|
||||
SDLoc DL(Op);
|
||||
const GlobalValue *GV = cast<GlobalAddressSDNode>(Op)->getGlobal();
|
||||
EVT Ty = Op.getValueType();
|
||||
GlobalAddressSDNode *N = cast<GlobalAddressSDNode>(Op);
|
||||
const GlobalValue *GV = N->getGlobal();
|
||||
|
||||
if (getTargetMachine().getRelocationModel() != Reloc::PIC_ && !IsN64) {
|
||||
const MipsTargetObjectFile &TLOF =
|
||||
@ -1495,26 +1460,29 @@ SDValue MipsTargetLowering::lowerGlobalAddress(SDValue Op,
|
||||
}
|
||||
|
||||
// %hi/%lo relocation
|
||||
return getAddrNonPIC(Op, DAG);
|
||||
return getAddrNonPIC(N, Ty, DAG);
|
||||
}
|
||||
|
||||
if (GV->hasInternalLinkage() || (GV->hasLocalLinkage() && !isa<Function>(GV)))
|
||||
return getAddrLocal(Op, DAG, HasMips64);
|
||||
return getAddrLocal(N, Ty, DAG, HasMips64);
|
||||
|
||||
if (LargeGOT)
|
||||
return getAddrGlobalLargeGOT(Op, DAG, MipsII::MO_GOT_HI16,
|
||||
return getAddrGlobalLargeGOT(N, Ty, DAG, MipsII::MO_GOT_HI16,
|
||||
MipsII::MO_GOT_LO16);
|
||||
|
||||
return getAddrGlobal(Op, DAG,
|
||||
return getAddrGlobal(N, Ty, DAG,
|
||||
HasMips64 ? MipsII::MO_GOT_DISP : MipsII::MO_GOT16);
|
||||
}
|
||||
|
||||
SDValue MipsTargetLowering::lowerBlockAddress(SDValue Op,
|
||||
SelectionDAG &DAG) const {
|
||||
if (getTargetMachine().getRelocationModel() != Reloc::PIC_ && !IsN64)
|
||||
return getAddrNonPIC(Op, DAG);
|
||||
BlockAddressSDNode *N = cast<BlockAddressSDNode>(Op);
|
||||
EVT Ty = Op.getValueType();
|
||||
|
||||
return getAddrLocal(Op, DAG, HasMips64);
|
||||
if (getTargetMachine().getRelocationModel() != Reloc::PIC_ && !IsN64)
|
||||
return getAddrNonPIC(N, Ty, DAG);
|
||||
|
||||
return getAddrLocal(N, Ty, DAG, HasMips64);
|
||||
}
|
||||
|
||||
SDValue MipsTargetLowering::
|
||||
@ -1601,10 +1569,13 @@ lowerGlobalTLSAddress(SDValue Op, SelectionDAG &DAG) const
|
||||
SDValue MipsTargetLowering::
|
||||
lowerJumpTable(SDValue Op, SelectionDAG &DAG) const
|
||||
{
|
||||
if (getTargetMachine().getRelocationModel() != Reloc::PIC_ && !IsN64)
|
||||
return getAddrNonPIC(Op, DAG);
|
||||
JumpTableSDNode *N = cast<JumpTableSDNode>(Op);
|
||||
EVT Ty = Op.getValueType();
|
||||
|
||||
return getAddrLocal(Op, DAG, HasMips64);
|
||||
if (getTargetMachine().getRelocationModel() != Reloc::PIC_ && !IsN64)
|
||||
return getAddrNonPIC(N, Ty, DAG);
|
||||
|
||||
return getAddrLocal(N, Ty, DAG, HasMips64);
|
||||
}
|
||||
|
||||
SDValue MipsTargetLowering::
|
||||
@ -1619,11 +1590,13 @@ lowerConstantPool(SDValue Op, SelectionDAG &DAG) const
|
||||
// SDValue GPRelNode = DAG.getNode(MipsISD::GPRel, MVT::i32, CP);
|
||||
// SDValue GOT = DAG.getGLOBAL_OFFSET_TABLE(MVT::i32);
|
||||
// ResNode = DAG.getNode(ISD::ADD, MVT::i32, GOT, GPRelNode);
|
||||
ConstantPoolSDNode *N = cast<ConstantPoolSDNode>(Op);
|
||||
EVT Ty = Op.getValueType();
|
||||
|
||||
if (getTargetMachine().getRelocationModel() != Reloc::PIC_ && !IsN64)
|
||||
return getAddrNonPIC(Op, DAG);
|
||||
return getAddrNonPIC(N, Ty, DAG);
|
||||
|
||||
return getAddrLocal(Op, DAG, HasMips64);
|
||||
return getAddrLocal(N, Ty, DAG, HasMips64);
|
||||
}
|
||||
|
||||
SDValue MipsTargetLowering::lowerVASTART(SDValue Op, SelectionDAG &DAG) const {
|
||||
@ -2469,18 +2442,19 @@ MipsTargetLowering::LowerCall(TargetLowering::CallLoweringInfo &CLI,
|
||||
bool IsPICCall = (IsN64 || IsPIC); // true if calls are translated to jalr $25
|
||||
bool GlobalOrExternal = false, InternalLinkage = false;
|
||||
SDValue CalleeLo;
|
||||
EVT Ty = Callee.getValueType();
|
||||
|
||||
if (GlobalAddressSDNode *G = dyn_cast<GlobalAddressSDNode>(Callee)) {
|
||||
if (IsPICCall) {
|
||||
InternalLinkage = G->getGlobal()->hasInternalLinkage();
|
||||
|
||||
if (InternalLinkage)
|
||||
Callee = getAddrLocal(Callee, DAG, HasMips64);
|
||||
Callee = getAddrLocal(G, Ty, DAG, HasMips64);
|
||||
else if (LargeGOT)
|
||||
Callee = getAddrGlobalLargeGOT(Callee, DAG, MipsII::MO_CALL_HI16,
|
||||
Callee = getAddrGlobalLargeGOT(G, Ty, DAG, MipsII::MO_CALL_HI16,
|
||||
MipsII::MO_CALL_LO16);
|
||||
else
|
||||
Callee = getAddrGlobal(Callee, DAG, MipsII::MO_GOT_CALL);
|
||||
Callee = getAddrGlobal(G, Ty, DAG, MipsII::MO_GOT_CALL);
|
||||
} else
|
||||
Callee = DAG.getTargetGlobalAddress(G->getGlobal(), DL, getPointerTy(), 0,
|
||||
MipsII::MO_NO_FLAG);
|
||||
@ -2491,10 +2465,10 @@ MipsTargetLowering::LowerCall(TargetLowering::CallLoweringInfo &CLI,
|
||||
Callee = DAG.getTargetExternalSymbol(S->getSymbol(), getPointerTy(),
|
||||
MipsII::MO_NO_FLAG);
|
||||
else if (LargeGOT)
|
||||
Callee = getAddrGlobalLargeGOT(Callee, DAG, MipsII::MO_CALL_HI16,
|
||||
Callee = getAddrGlobalLargeGOT(S, Ty, DAG, MipsII::MO_CALL_HI16,
|
||||
MipsII::MO_CALL_LO16);
|
||||
else // N64 || PIC
|
||||
Callee = getAddrGlobal(Callee, DAG, MipsII::MO_GOT_CALL);
|
||||
Callee = getAddrGlobal(S, Ty, DAG, MipsII::MO_GOT_CALL);
|
||||
|
||||
GlobalOrExternal = true;
|
||||
}
|
||||
|
@ -17,6 +17,7 @@
|
||||
|
||||
#include "Mips.h"
|
||||
#include "MipsSubtarget.h"
|
||||
#include "MCTargetDesc/MipsBaseInfo.h"
|
||||
#include "llvm/CodeGen/CallingConvLower.h"
|
||||
#include "llvm/CodeGen/SelectionDAG.h"
|
||||
#include "llvm/IR/Function.h"
|
||||
@ -248,12 +249,70 @@ namespace llvm {
|
||||
protected:
|
||||
SDValue getGlobalReg(SelectionDAG &DAG, EVT Ty) const;
|
||||
|
||||
SDValue getAddrLocal(SDValue Op, SelectionDAG &DAG, bool HasMips64) const;
|
||||
// This method creates the following nodes, which are necessary for
|
||||
// computing a local symbol's address:
|
||||
//
|
||||
// (add (load (wrapper $gp, %got(sym)), %lo(sym))
|
||||
template<class NodeTy>
|
||||
SDValue getAddrLocal(NodeTy *N, EVT Ty, SelectionDAG &DAG,
|
||||
bool HasMips64) const {
|
||||
SDLoc DL(N);
|
||||
unsigned GOTFlag = HasMips64 ? MipsII::MO_GOT_PAGE : MipsII::MO_GOT;
|
||||
SDValue GOT = DAG.getNode(MipsISD::Wrapper, DL, Ty, getGlobalReg(DAG, Ty),
|
||||
getTargetNode(N, Ty, DAG, GOTFlag));
|
||||
SDValue Load = DAG.getLoad(Ty, DL, DAG.getEntryNode(), GOT,
|
||||
MachinePointerInfo::getGOT(), false, false,
|
||||
false, 0);
|
||||
unsigned LoFlag = HasMips64 ? MipsII::MO_GOT_OFST : MipsII::MO_ABS_LO;
|
||||
SDValue Lo = DAG.getNode(MipsISD::Lo, DL, Ty,
|
||||
getTargetNode(N, Ty, DAG, LoFlag));
|
||||
return DAG.getNode(ISD::ADD, DL, Ty, Load, Lo);
|
||||
}
|
||||
|
||||
SDValue getAddrGlobal(SDValue Op, SelectionDAG &DAG, unsigned Flag) const;
|
||||
// This method creates the following nodes, which are necessary for
|
||||
// computing a global symbol's address:
|
||||
//
|
||||
// (load (wrapper $gp, %got(sym)))
|
||||
template<class NodeTy>
|
||||
SDValue getAddrGlobal(NodeTy *N, EVT Ty, SelectionDAG &DAG,
|
||||
unsigned Flag) const {
|
||||
SDLoc DL(N);
|
||||
SDValue Tgt = DAG.getNode(MipsISD::Wrapper, DL, Ty, getGlobalReg(DAG, Ty),
|
||||
getTargetNode(N, Ty, DAG, Flag));
|
||||
return DAG.getLoad(Ty, DL, DAG.getEntryNode(), Tgt,
|
||||
MachinePointerInfo::getGOT(), false, false, false, 0);
|
||||
}
|
||||
|
||||
SDValue getAddrGlobalLargeGOT(SDValue Op, SelectionDAG &DAG,
|
||||
unsigned HiFlag, unsigned LoFlag) const;
|
||||
// This method creates the following nodes, which are necessary for
|
||||
// computing a global symbol's address in large-GOT mode:
|
||||
//
|
||||
// (load (wrapper (add %hi(sym), $gp), %lo(sym)))
|
||||
template<class NodeTy>
|
||||
SDValue getAddrGlobalLargeGOT(NodeTy *N, EVT Ty, SelectionDAG &DAG,
|
||||
unsigned HiFlag, unsigned LoFlag) const {
|
||||
SDLoc DL(N);
|
||||
SDValue Hi = DAG.getNode(MipsISD::Hi, DL, Ty,
|
||||
getTargetNode(N, Ty, DAG, HiFlag));
|
||||
Hi = DAG.getNode(ISD::ADD, DL, Ty, Hi, getGlobalReg(DAG, Ty));
|
||||
SDValue Wrapper = DAG.getNode(MipsISD::Wrapper, DL, Ty, Hi,
|
||||
getTargetNode(N, Ty, DAG, LoFlag));
|
||||
return DAG.getLoad(Ty, DL, DAG.getEntryNode(), Wrapper,
|
||||
MachinePointerInfo::getGOT(), false, false, false, 0);
|
||||
}
|
||||
|
||||
// This method creates the following nodes, which are necessary for
|
||||
// computing a symbol's address in non-PIC mode:
|
||||
//
|
||||
// (add %hi(sym), %lo(sym))
|
||||
template<class NodeTy>
|
||||
SDValue getAddrNonPIC(NodeTy *N, EVT Ty, SelectionDAG &DAG) const {
|
||||
SDLoc DL(N);
|
||||
SDValue Hi = getTargetNode(N, Ty, DAG, MipsII::MO_ABS_HI);
|
||||
SDValue Lo = getTargetNode(N, Ty, DAG, MipsII::MO_ABS_LO);
|
||||
return DAG.getNode(ISD::ADD, DL, Ty,
|
||||
DAG.getNode(MipsISD::Hi, DL, Ty, Hi),
|
||||
DAG.getNode(MipsISD::Lo, DL, Ty, Lo));
|
||||
}
|
||||
|
||||
/// This function fills Ops, which is the list of operands that will later
|
||||
/// be used when a function call node is created. It also generates
|
||||
@ -369,6 +428,25 @@ namespace llvm {
|
||||
bool HasMips64, IsN64, IsO32;
|
||||
|
||||
private:
|
||||
// Create a TargetGlobalAddress node.
|
||||
SDValue getTargetNode(GlobalAddressSDNode *N, EVT Ty, SelectionDAG &DAG,
|
||||
unsigned Flag) const;
|
||||
|
||||
// Create a TargetExternalSymbol node.
|
||||
SDValue getTargetNode(ExternalSymbolSDNode *N, EVT Ty, SelectionDAG &DAG,
|
||||
unsigned Flag) const;
|
||||
|
||||
// Create a TargetBlockAddress node.
|
||||
SDValue getTargetNode(BlockAddressSDNode *N, EVT Ty, SelectionDAG &DAG,
|
||||
unsigned Flag) const;
|
||||
|
||||
// Create a TargetJumpTable node.
|
||||
SDValue getTargetNode(JumpTableSDNode *N, EVT Ty, SelectionDAG &DAG,
|
||||
unsigned Flag) const;
|
||||
|
||||
// Create a TargetConstantPool node.
|
||||
SDValue getTargetNode(ConstantPoolSDNode *N, EVT Ty, SelectionDAG &DAG,
|
||||
unsigned Flag) const;
|
||||
|
||||
MipsCC::SpecialCallingConvType getSpecialCallingConv(SDValue Callee) const;
|
||||
// Lower Operand helpers
|
||||
|
Loading…
x
Reference in New Issue
Block a user