aboutsummaryrefslogtreecommitdiff
path: root/lib/Target/Alpha/AlphaISelLowering.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lib/Target/Alpha/AlphaISelLowering.cpp')
-rw-r--r--lib/Target/Alpha/AlphaISelLowering.cpp27
1 files changed, 27 insertions, 0 deletions
diff --git a/lib/Target/Alpha/AlphaISelLowering.cpp b/lib/Target/Alpha/AlphaISelLowering.cpp
index 9b2fce2c1a..8d2ffa7177 100644
--- a/lib/Target/Alpha/AlphaISelLowering.cpp
+++ b/lib/Target/Alpha/AlphaISelLowering.cpp
@@ -104,6 +104,11 @@ AlphaTargetLowering::AlphaTargetLowering(TargetMachine &TM) : TargetLowering(TM)
setOperationAction(ISD::LOCATION, MVT::Other, Expand);
setOperationAction(ISD::DEBUG_LOC, MVT::Other, Expand);
+ // We want to legalize GlobalAddress and ConstantPool nodes into the
+ // appropriate instructions to materialize the address.
+ setOperationAction(ISD::GlobalAddress, MVT::i64, Custom);
+ setOperationAction(ISD::ConstantPool, MVT::i64, Custom);
+
addLegalFPImmediate(+0.0); //F31
addLegalFPImmediate(-0.0); //-F31
@@ -434,6 +439,28 @@ SDOperand AlphaTargetLowering::LowerOperation(SDOperand Op, SelectionDAG &DAG) {
return DAG.getLoad(MVT::i64, ST, FI, DAG.getSrcValue(0));
}
}
+ case ISD::ConstantPool: {
+ Constant *C = cast<ConstantPoolSDNode>(Op)->get();
+ SDOperand CPI = DAG.getTargetConstantPool(C, MVT::i64);
+
+ SDOperand Hi = DAG.getNode(AlphaISD::GPRelHi, MVT::i64, CPI,
+ DAG.getNode(AlphaISD::GlobalBaseReg, MVT::i64));
+ SDOperand Lo = DAG.getNode(AlphaISD::GPRelLo, MVT::i64, CPI, Hi);
+ return Lo;
+ }
+ case ISD::GlobalAddress: {
+ GlobalAddressSDNode *GSDN = cast<GlobalAddressSDNode>(Op);
+ GlobalValue *GV = GSDN->getGlobal();
+ SDOperand GA = DAG.getTargetGlobalAddress(GV, MVT::i64, GSDN->getOffset());
+
+ if (!GV->hasWeakLinkage() && !GV->isExternal()) {
+ SDOperand Hi = DAG.getNode(AlphaISD::GPRelHi, MVT::i64, GA,
+ DAG.getNode(AlphaISD::GlobalBaseReg, MVT::i64));
+ SDOperand Lo = DAG.getNode(AlphaISD::GPRelLo, MVT::i64, GA, Hi);
+ return Lo;
+ } else
+ return GA;
+ }
}