summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMarcin Koscielnicki <koriakin@0x04.net>2016-05-04 23:31:26 +0000
committerMarcin Koscielnicki <koriakin@0x04.net>2016-05-04 23:31:26 +0000
commit9de88d9bbef514125d0e1bd2f5b9d3a2dd43c631 (patch)
treeb20b7971b91ea576121f3d7b28d755552f65fde5
parent835d927938642c525f13b2750124c521635e9c3f (diff)
downloadbcm5719-llvm-9de88d9bbef514125d0e1bd2f5b9d3a2dd43c631.tar.gz
bcm5719-llvm-9de88d9bbef514125d0e1bd2f5b9d3a2dd43c631.zip
[SystemZ] Implement llvm.get.dynamic.area.offset
To be used for AddressSanitizer. Differential Revision: http://reviews.llvm.org/D19817 llvm-svn: 268572
-rw-r--r--llvm/lib/Target/SystemZ/SystemZISelDAGToDAG.cpp4
-rw-r--r--llvm/lib/Target/SystemZ/SystemZISelLowering.cpp10
-rw-r--r--llvm/lib/Target/SystemZ/SystemZISelLowering.h1
-rw-r--r--llvm/test/CodeGen/SystemZ/dyn-alloca-offset.ll42
4 files changed, 57 insertions, 0 deletions
diff --git a/llvm/lib/Target/SystemZ/SystemZISelDAGToDAG.cpp b/llvm/lib/Target/SystemZ/SystemZISelDAGToDAG.cpp
index a9093094d88..ddf7af73bc2 100644
--- a/llvm/lib/Target/SystemZ/SystemZISelDAGToDAG.cpp
+++ b/llvm/lib/Target/SystemZ/SystemZISelDAGToDAG.cpp
@@ -554,6 +554,10 @@ bool SystemZDAGToDAGISel::selectAddress(SDValue Addr,
expandDisp(AM, true, SDValue(),
cast<ConstantSDNode>(Addr)->getSExtValue()))
;
+ // Also see if it's a bare ADJDYNALLOC.
+ else if (Addr.getOpcode() == SystemZISD::ADJDYNALLOC &&
+ expandAdjDynAlloc(AM, true, SDValue()))
+ ;
else
// Otherwise try expanding each component.
while (expandAddress(AM, true) ||
diff --git a/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp b/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp
index 09701951178..f656a2f00ed 100644
--- a/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp
+++ b/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp
@@ -253,6 +253,7 @@ SystemZTargetLowering::SystemZTargetLowering(const TargetMachine &TM,
// We need to handle dynamic allocations specially because of the
// 160-byte area at the bottom of the stack.
setOperationAction(ISD::DYNAMIC_STACKALLOC, PtrVT, Custom);
+ setOperationAction(ISD::GET_DYNAMIC_AREA_OFFSET, PtrVT, Custom);
// Use custom expanders so that we can force the function to use
// a frame pointer.
@@ -2900,6 +2901,13 @@ lowerDYNAMIC_STACKALLOC(SDValue Op, SelectionDAG &DAG) const {
return DAG.getMergeValues(Ops, DL);
}
+SDValue SystemZTargetLowering::lowerGET_DYNAMIC_AREA_OFFSET(
+ SDValue Op, SelectionDAG &DAG) const {
+ SDLoc DL(Op);
+
+ return DAG.getNode(SystemZISD::ADJDYNALLOC, DL, MVT::i64);
+}
+
SDValue SystemZTargetLowering::lowerSMUL_LOHI(SDValue Op,
SelectionDAG &DAG) const {
EVT VT = Op.getValueType();
@@ -4487,6 +4495,8 @@ SDValue SystemZTargetLowering::LowerOperation(SDValue Op,
return lowerVACOPY(Op, DAG);
case ISD::DYNAMIC_STACKALLOC:
return lowerDYNAMIC_STACKALLOC(Op, DAG);
+ case ISD::GET_DYNAMIC_AREA_OFFSET:
+ return lowerGET_DYNAMIC_AREA_OFFSET(Op, DAG);
case ISD::SMUL_LOHI:
return lowerSMUL_LOHI(Op, DAG);
case ISD::UMUL_LOHI:
diff --git a/llvm/lib/Target/SystemZ/SystemZISelLowering.h b/llvm/lib/Target/SystemZ/SystemZISelLowering.h
index fe6966aafe2..f26e1dc0d66 100644
--- a/llvm/lib/Target/SystemZ/SystemZISelLowering.h
+++ b/llvm/lib/Target/SystemZ/SystemZISelLowering.h
@@ -487,6 +487,7 @@ private:
SDValue lowerVASTART(SDValue Op, SelectionDAG &DAG) const;
SDValue lowerVACOPY(SDValue Op, SelectionDAG &DAG) const;
SDValue lowerDYNAMIC_STACKALLOC(SDValue Op, SelectionDAG &DAG) const;
+ SDValue lowerGET_DYNAMIC_AREA_OFFSET(SDValue Op, SelectionDAG &DAG) const;
SDValue lowerSMUL_LOHI(SDValue Op, SelectionDAG &DAG) const;
SDValue lowerUMUL_LOHI(SDValue Op, SelectionDAG &DAG) const;
SDValue lowerSDIVREM(SDValue Op, SelectionDAG &DAG) const;
diff --git a/llvm/test/CodeGen/SystemZ/dyn-alloca-offset.ll b/llvm/test/CodeGen/SystemZ/dyn-alloca-offset.ll
new file mode 100644
index 00000000000..b9997ac0ec9
--- /dev/null
+++ b/llvm/test/CodeGen/SystemZ/dyn-alloca-offset.ll
@@ -0,0 +1,42 @@
+; RUN: llc < %s -mtriple=s390x-linux-gnu | FileCheck %s
+
+declare i64 @llvm.get.dynamic.area.offset.i64()
+
+declare void @use(i64)
+
+define void @f1() {
+; CHECK-LABEL: f1
+; CHECK: la %r2, 160
+; CHECK: brasl %r14, use
+; CHECK: br %r14
+ %tmp = alloca i64, align 32
+ %dynamic_area_offset = call i64 @llvm.get.dynamic.area.offset.i64()
+ call void @use(i64 %dynamic_area_offset)
+ ret void
+}
+
+define void @f2(i64 %arg) {
+; CHECK-LABEL: f2
+; CHECK: la %r2, 160(%r2)
+; CHECK: brasl %r14, use
+; CHECK: br %r14
+ %tmp = alloca i64, align 32
+ %dynamic_area_offset = call i64 @llvm.get.dynamic.area.offset.i64()
+ %param = add i64 %dynamic_area_offset, %arg
+ call void @use(i64 %param)
+ ret void
+}
+
+declare void @eatsalot(i64, i64, i64, i64, i64, i64)
+
+define void @f3() {
+; CHECK-LABEL: f3
+; CHECK: la %r2, 168
+; CHECK: brasl %r14, use
+; CHECK: br %r14
+ %tmp = alloca i64, align 32
+ call void @eatsalot(i64 0, i64 0, i64 0, i64 0, i64 0, i64 0)
+ %dynamic_area_offset = call i64 @llvm.get.dynamic.area.offset.i64()
+ call void @use(i64 %dynamic_area_offset)
+ ret void
+}
OpenPOWER on IntegriCloud