[PATCH] D51114: [WebAssembly] Don't write SP back when prolog is generated only for EH
Heejin Ahn via Phabricator via llvm-commits
llvm-commits at lists.llvm.org
Wed Aug 22 11:17:08 PDT 2018
aheejin created this revision.
aheejin added reviewers: dschuff, jgravelle-google.
Herald added subscribers: llvm-commits, sunfish, sbc100.
When we don't actually have stack-allocated variables but needs SP only
to support EH, we don't need to write SP back in the epilog, because we
don't bump down the stack pointer.
Repository:
rL LLVM
https://reviews.llvm.org/D51114
Files:
lib/Target/WebAssembly/WebAssemblyEHRestoreStackPointer.cpp
lib/Target/WebAssembly/WebAssemblyFrameLowering.cpp
test/CodeGen/WebAssembly/exception.ll
Index: test/CodeGen/WebAssembly/exception.ll
===================================================================
--- test/CodeGen/WebAssembly/exception.ll
+++ test/CodeGen/WebAssembly/exception.ll
@@ -217,6 +217,35 @@
cleanupret from %8 unwind to caller
}
+; When a function does not have stack-allocated objects, it does not need to
+; store SP back to __stack_pointer global at the epilog.
+
+; CHECK-LABEL: no_sp_writeback
+; CHECK: try
+; CHECK: call foo at FUNCTION
+; CHECK: end_try
+; CHECK-NOT: set_global __stack_pointer at GLOBAL
+; CHECK: return
+define void @no_sp_writeback() personality i8* bitcast (i32 (...)* @__gxx_wasm_personality_v0 to i8*) {
+entry:
+ invoke void @foo()
+ to label %try.cont unwind label %catch.dispatch
+
+catch.dispatch: ; preds = %entry
+ %0 = catchswitch within none [label %catch.start] unwind to caller
+
+catch.start: ; preds = %catch.dispatch
+ %1 = catchpad within %0 [i8* null]
+ %2 = call i8* @llvm.wasm.get.exception(token %1)
+ %3 = call i32 @llvm.wasm.get.ehselector(token %1)
+ %4 = call i8* @__cxa_begin_catch(i8* %2) #2 [ "funclet"(token %1) ]
+ call void @__cxa_end_catch() [ "funclet"(token %1) ]
+ catchret from %1 to label %try.cont
+
+try.cont: ; preds = %entry, %catch.start
+ ret void
+}
+
declare void @foo()
declare void @bar(i32*)
declare i32 @__gxx_wasm_personality_v0(...)
Index: lib/Target/WebAssembly/WebAssemblyFrameLowering.cpp
===================================================================
--- lib/Target/WebAssembly/WebAssemblyFrameLowering.cpp
+++ lib/Target/WebAssembly/WebAssemblyFrameLowering.cpp
@@ -105,8 +105,17 @@
bool WebAssemblyFrameLowering::needsSPWriteback(
const MachineFunction &MF, const MachineFrameInfo &MFI) const {
assert(needsSP(MF, MFI));
- return MFI.getStackSize() > RedZoneSize || MFI.hasCalls() ||
- MF.getFunction().hasFnAttribute(Attribute::NoRedZone);
+ // When we don't actually have stack-allocated variables but needs SP only to
+ // support EH, we don't need to write SP back in the epilog, because we don't
+ // bump down the stack pointer. We need to write SP back in the epilog only if
+ // 1. We need SP not only for EH support but also because we actually use
+ // stack or we have a frame address taken.
+ // 2. We cannot use the red zone.
+ bool NeedsSPOnlyForEH = !MFI.getStackSize() && !MFI.adjustsStack() &&
+ !hasFP(MF) && needsPrologForEH(MF);
+ bool CanUseRedZone = MFI.getStackSize() <= RedZoneSize && !MFI.hasCalls() &&
+ !MF.getFunction().hasFnAttribute(Attribute::NoRedZone);
+ return !NeedsSPOnlyForEH && !CanUseRedZone;
}
void WebAssemblyFrameLowering::writeSPToGlobal(
Index: lib/Target/WebAssembly/WebAssemblyEHRestoreStackPointer.cpp
===================================================================
--- lib/Target/WebAssembly/WebAssemblyEHRestoreStackPointer.cpp
+++ lib/Target/WebAssembly/WebAssemblyEHRestoreStackPointer.cpp
@@ -68,6 +68,11 @@
// pad, after the catch instruction. (Catch instructions may have been
// reordered, and catch_all instructions have not been inserted yet, but
// those cases are handled in LateEHPrepare).
+ //
+ // Here it is safe to assume that SP32 holds the latest value of
+ // __stack_poiner, because the only exception for this case is when a
+ // function uses the red zone, but that only happens with leaf functions,
+ // and leaf functions can't catch exceptions anyway.
auto InsertPos = MBB.begin();
if (WebAssembly::isCatch(*MBB.begin()))
InsertPos++;
-------------- next part --------------
A non-text attachment was scrubbed...
Name: D51114.162006.patch
Type: text/x-patch
Size: 3692 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20180822/74424394/attachment.bin>
More information about the llvm-commits
mailing list