[llvm] 668bb96 - [ARM] Implement lowering of the sponentry intrinsic
Martin Storsjö via llvm-commits
llvm-commits at lists.llvm.org
Thu Jun 2 02:31:22 PDT 2022
Author: Martin Storsjö
Date: 2022-06-02T12:29:59+03:00
New Revision: 668bb96379fef1bfa85da699c681265053673987
URL: https://github.com/llvm/llvm-project/commit/668bb96379fef1bfa85da699c681265053673987
DIFF: https://github.com/llvm/llvm-project/commit/668bb96379fef1bfa85da699c681265053673987.diff
LOG: [ARM] Implement lowering of the sponentry intrinsic
This is needed for SEH based setjmp on Windows.
Differential Revision: https://reviews.llvm.org/D126763
Added:
llvm/test/CodeGen/ARM/sponentry.ll
Modified:
llvm/docs/LangRef.rst
llvm/lib/Target/ARM/ARMISelLowering.cpp
llvm/lib/Target/ARM/ARMISelLowering.h
Removed:
################################################################################
diff --git a/llvm/docs/LangRef.rst b/llvm/docs/LangRef.rst
index d5540229a4b2..81341860ca4c 100644
--- a/llvm/docs/LangRef.rst
+++ b/llvm/docs/LangRef.rst
@@ -12685,7 +12685,7 @@ the entry of the current function calling this intrinsic.
Semantics:
""""""""""
-Note this intrinsic is only verified on AArch64.
+Note this intrinsic is only verified on AArch64 and ARM.
'``llvm.frameaddress``' Intrinsic
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
diff --git a/llvm/lib/Target/ARM/ARMISelLowering.cpp b/llvm/lib/Target/ARM/ARMISelLowering.cpp
index eb1a0c55ca9b..a1c1f6aa2ab1 100644
--- a/llvm/lib/Target/ARM/ARMISelLowering.cpp
+++ b/llvm/lib/Target/ARM/ARMISelLowering.cpp
@@ -10315,6 +10315,15 @@ SDValue ARMTargetLowering::LowerFSETCC(SDValue Op, SelectionDAG &DAG) const {
return DAG.getMergeValues({Result, Chain}, dl);
}
+SDValue ARMTargetLowering::LowerSPONENTRY(SDValue Op, SelectionDAG &DAG) const {
+ MachineFrameInfo &MFI = DAG.getMachineFunction().getFrameInfo();
+
+ EVT VT = getPointerTy(DAG.getDataLayout());
+ SDLoc DL(Op);
+ int FI = MFI.CreateFixedObject(4, 0, false);
+ return DAG.getFrameIndex(FI, VT);
+}
+
SDValue ARMTargetLowering::LowerOperation(SDValue Op, SelectionDAG &DAG) const {
LLVM_DEBUG(dbgs() << "Lowering node: "; Op.dump());
switch (Op.getOpcode()) {
@@ -10428,6 +10437,8 @@ SDValue ARMTargetLowering::LowerOperation(SDValue Op, SelectionDAG &DAG) const {
case ISD::FP_EXTEND: return LowerFP_EXTEND(Op, DAG);
case ISD::STRICT_FSETCC:
case ISD::STRICT_FSETCCS: return LowerFSETCC(Op, DAG);
+ case ISD::SPONENTRY:
+ return LowerSPONENTRY(Op, DAG);
case ARMISD::WIN__DBZCHK: return SDValue();
}
}
diff --git a/llvm/lib/Target/ARM/ARMISelLowering.h b/llvm/lib/Target/ARM/ARMISelLowering.h
index 33eb00100331..b6b063ab4f34 100644
--- a/llvm/lib/Target/ARM/ARMISelLowering.h
+++ b/llvm/lib/Target/ARM/ARMISelLowering.h
@@ -846,6 +846,7 @@ class VectorType;
SDValue LowerFP_TO_INT(SDValue Op, SelectionDAG &DAG) const;
SDValue LowerINT_TO_FP(SDValue Op, SelectionDAG &DAG) const;
SDValue LowerFSETCC(SDValue Op, SelectionDAG &DAG) const;
+ SDValue LowerSPONENTRY(SDValue Op, SelectionDAG &DAG) const;
void LowerLOAD(SDNode *N, SmallVectorImpl<SDValue> &Results,
SelectionDAG &DAG) const;
diff --git a/llvm/test/CodeGen/ARM/sponentry.ll b/llvm/test/CodeGen/ARM/sponentry.ll
new file mode 100644
index 000000000000..b98a14591b01
--- /dev/null
+++ b/llvm/test/CodeGen/ARM/sponentry.ll
@@ -0,0 +1,120 @@
+; RUN: llc -mtriple=thumbv7-windows-msvc -frame-pointer=all %s -o - | FileCheck %s
+; RUN: llc -mtriple=thumbv7-windows-msvc -fast-isel -frame-pointer=all %s -o - | FileCheck %s
+; RUN: llc -mtriple=thumbv7-windows-msvc %s -o - | FileCheck %s --check-prefix=NOFP
+; RUN: llc -mtriple=thumbv7-windows-msvc -fast-isel %s -o - | FileCheck %s --check-prefix=NOFP
+
+ at env2 = common dso_local global [24 x i64]* null, align 8
+
+define dso_local void @bar() {
+ %1 = call i8* @llvm.sponentry()
+ %2 = load [24 x i64]*, [24 x i64]** @env2, align 8
+ %3 = getelementptr inbounds [24 x i64], [24 x i64]* %2, i32 0, i32 0
+ %4 = bitcast i64* %3 to i8*
+ %5 = call i32 @_setjmpex(i8* %4, i8* %1) #2
+ ret void
+}
+
+; CHECK: bar:
+; CHECK: push.w {r11, lr}
+; CHECK: mov r11, sp
+; CHECK: add.w r1, r11, #8
+; CHECK: bl _setjmpex
+
+; NOFP: bar:
+; NOFP: push.w {r11, lr}
+; NOFP: add r1, sp, #8
+; NOFP: bl _setjmpex
+
+define dso_local void @foo([24 x i64]*) {
+ %2 = alloca [24 x i64]*, align 8
+ %3 = alloca i32, align 4
+ %4 = alloca [100 x i32], align 4
+ store [24 x i64]* %0, [24 x i64]** %2, align 8
+ %5 = call i8* @llvm.sponentry()
+ %6 = load [24 x i64]*, [24 x i64]** %2, align 8
+ %7 = getelementptr inbounds [24 x i64], [24 x i64]* %6, i32 0, i32 0
+ %8 = bitcast i64* %7 to i8*
+ %9 = call i32 @_setjmpex(i8* %8, i8* %5)
+ store i32 %9, i32* %3, align 4
+ ret void
+}
+
+; CHECK: foo:
+; CHECK: push.w {r11, lr}
+; CHECK: mov r11, sp
+; CHECK: sub sp, #416
+; CHECK: add.w r1, r11, #8
+; CHECK: bl _setjmpex
+
+; NOFP: foo:
+; NOFP: push.w {r11, lr}
+; NOFP: sub sp, #416
+; NOFP: add r1, sp, #424
+; NOFP: bl _setjmpex
+
+define dso_local void @var_args(i8*, ...) {
+ %2 = alloca i8*, align 8
+ %3 = alloca i8*, align 8
+ store i8* %0, i8** %2, align 8
+ %4 = bitcast i8** %3 to i8*
+ call void @llvm.va_start(i8* %4)
+ %5 = load i8*, i8** %3, align 8
+ %6 = getelementptr inbounds i8, i8* %5, i64 8
+ store i8* %6, i8** %3, align 8
+ %7 = bitcast i8* %5 to i32*
+ %8 = load i32, i32* %7, align 8
+ %9 = bitcast i8** %3 to i8*
+ call void @llvm.va_end(i8* %9)
+ %10 = call i8* @llvm.sponentry()
+ %11 = load [24 x i64]*, [24 x i64]** @env2, align 8
+ %12 = getelementptr inbounds [24 x i64], [24 x i64]* %11, i32 0, i32 0
+ %13 = bitcast i64* %12 to i8*
+ %14 = call i32 @_setjmpex(i8* %13, i8* %10) #3
+ ret void
+}
+
+; CHECK: var_args:
+; CHECK: sub sp, #12
+; CHECK: push.w {r11, lr}
+; CHECK: mov r11, sp
+; CHECK: add.w r1, r11, #20
+; CHECK: bl _setjmpex
+
+; NOFP: var_args:
+; NOFP: sub sp, #12
+; NOFP: push.w {r11, lr}
+; NOFP: sub sp, #12
+; NOFP: add r1, sp, #32
+; NOFP: bl _setjmpex
+
+define dso_local void @manyargs(i64 %x1, i64 %x2, i64 %x3, i64 %x4, i64 %x5, i64 %x6, i64 %x7, i64 %x8, i64 %x9, i64 %x10) {
+ %1 = call i8* @llvm.sponentry()
+ %2 = load [24 x i64]*, [24 x i64]** @env2, align 8
+ %3 = getelementptr inbounds [24 x i64], [24 x i64]* %2, i32 0, i32 0
+ %4 = bitcast i64* %3 to i8*
+ %5 = call i32 @_setjmpex(i8* %4, i8* %1) #2
+ ret void
+}
+
+; CHECK: manyargs:
+; CHECK: push.w {r11, lr}
+; CHECK: mov r11, sp
+; CHECK: add.w r1, r11, #8
+; CHECK: bl _setjmpex
+
+; NOFP: manyargs:
+; NOFP: push.w {r11, lr}
+; NOFP: add r1, sp, #8
+; NOFP: bl _setjmpex
+
+; Function Attrs: nounwind readnone
+declare i8* @llvm.sponentry()
+
+; Function Attrs: returns_twice
+declare dso_local i32 @_setjmpex(i8*, i8*)
+
+; Function Attrs: nounwind
+declare void @llvm.va_start(i8*) #1
+
+; Function Attrs: nounwind
+declare void @llvm.va_end(i8*) #1
More information about the llvm-commits
mailing list