summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Target/WebAssembly
diff options
context:
space:
mode:
authorHeejin Ahn <aheejin@gmail.com>2019-03-13 00:37:31 +0000
committerHeejin Ahn <aheejin@gmail.com>2019-03-13 00:37:31 +0000
commit8b49b6bed6e922b6f5474db0f3841b31cf77f3cd (patch)
treeaec72514d6ad9d25f955b33f52687bb93e1221bb /llvm/lib/Target/WebAssembly
parent72db2abcc794feccfb482d4ae9e500c91c8bcb45 (diff)
downloadbcm5719-llvm-8b49b6bed6e922b6f5474db0f3841b31cf77f3cd.tar.gz
bcm5719-llvm-8b49b6bed6e922b6f5474db0f3841b31cf77f3cd.zip
[WebAssembly] Place 'try' and 'catch' correctly wrt EH_LABELs
Summary: After instruction selection phase, possibly-throwing calls, which were previously invoke, are wrapped in `EH_LABEL` instructions. For example: ``` EH_LABEL <mcsymbol .Ltmp0> CALL_VOID @foo ... EH_LABEL <mcsymbol .Ltmp1> ``` `EH_LABEL` is placed also in the beginning of EH pads: ``` bb.1 (landing-pad): EH_LABEL <mcsymbol .Ltmp2> ... ``` And we'd like to maintian this relationship, so when we place a `try`, ``` TRY ... EH_LABEL <mcsymbol .Ltmp0> CALL_VOID @foo ... EH_LABEL <mcsymbol .Ltmp1> ``` When we place a `catch`, ``` bb.1 (landing-pad): EH_LABEL <mcsymbol .Ltmp2> %0:except_ref = CATCH ... ... ``` Previously we didn't treat EH_LABELs specially, so `try` was placed right before a call, and `catch` was placed in the beginning of an EH pad. Reviewers: dschuff Subscribers: sbc100, jgravelle-google, sunfish, llvm-commits Tags: #llvm Differential Revision: https://reviews.llvm.org/D58914 llvm-svn: 355996
Diffstat (limited to 'llvm/lib/Target/WebAssembly')
-rw-r--r--llvm/lib/Target/WebAssembly/WebAssemblyCFGStackify.cpp5
-rw-r--r--llvm/lib/Target/WebAssembly/WebAssemblyLateEHPrepare.cpp19
2 files changed, 19 insertions, 5 deletions
diff --git a/llvm/lib/Target/WebAssembly/WebAssemblyCFGStackify.cpp b/llvm/lib/Target/WebAssembly/WebAssemblyCFGStackify.cpp
index 6002885b9e9..65cc088cd27 100644
--- a/llvm/lib/Target/WebAssembly/WebAssemblyCFGStackify.cpp
+++ b/llvm/lib/Target/WebAssembly/WebAssemblyCFGStackify.cpp
@@ -543,6 +543,11 @@ void WebAssemblyCFGStackify::placeTryMarker(MachineBasicBlock &MBB) {
for (const auto &MI : reverse(*Header)) {
if (MI.isCall()) {
AfterSet.insert(&MI);
+ // Possibly throwing calls are usually wrapped by EH_LABEL
+ // instructions. We don't want to split them and the call.
+ if (MI.getIterator() != Header->begin() &&
+ std::prev(MI.getIterator())->isEHLabel())
+ AfterSet.insert(&*std::prev(MI.getIterator()));
break;
}
}
diff --git a/llvm/lib/Target/WebAssembly/WebAssemblyLateEHPrepare.cpp b/llvm/lib/Target/WebAssembly/WebAssemblyLateEHPrepare.cpp
index 6cda1cc64dd..603b717812e 100644
--- a/llvm/lib/Target/WebAssembly/WebAssemblyLateEHPrepare.cpp
+++ b/llvm/lib/Target/WebAssembly/WebAssemblyLateEHPrepare.cpp
@@ -21,7 +21,7 @@
#include "llvm/MC/MCAsmInfo.h"
using namespace llvm;
-#define DEBUG_TYPE "wasm-exception-prepare"
+#define DEBUG_TYPE "wasm-late-eh-prepare"
namespace {
class WebAssemblyLateEHPrepare final : public MachineFunctionPass {
@@ -185,9 +185,12 @@ bool WebAssemblyLateEHPrepare::addCatches(MachineFunction &MF) {
for (auto &MBB : MF) {
if (MBB.isEHPad()) {
Changed = true;
+ auto InsertPos = MBB.begin();
+ if (InsertPos->isEHLabel()) // EH pad starts with an EH label
+ ++InsertPos;
unsigned DstReg =
MRI.createVirtualRegister(&WebAssembly::EXCEPT_REFRegClass);
- BuildMI(MBB, MBB.begin(), MBB.begin()->getDebugLoc(),
+ BuildMI(MBB, InsertPos, MBB.begin()->getDebugLoc(),
TII.get(WebAssembly::CATCH), DstReg);
}
}
@@ -255,7 +258,11 @@ bool WebAssemblyLateEHPrepare::addExceptionExtraction(MachineFunction &MF) {
for (auto *Extract : ExtractInstrs) {
MachineBasicBlock *EHPad = getMatchingEHPad(Extract);
assert(EHPad && "No matching EH pad for extract_exception");
- MachineInstr *Catch = &*EHPad->begin();
+ auto CatchPos = EHPad->begin();
+ if (CatchPos->isEHLabel()) // EH pad starts with an EH label
+ ++CatchPos;
+ MachineInstr *Catch = &*CatchPos;
+
if (Catch->getNextNode() != Extract)
EHPad->insert(Catch->getNextNode(), Extract->removeFromParent());
@@ -359,8 +366,10 @@ bool WebAssemblyLateEHPrepare::restoreStackPointer(MachineFunction &MF) {
// with leaf functions, and we don't restore __stack_pointer in leaf
// functions anyway.
auto InsertPos = MBB.begin();
- if (MBB.begin()->getOpcode() == WebAssembly::CATCH)
- InsertPos++;
+ if (InsertPos->isEHLabel()) // EH pad starts with an EH label
+ ++InsertPos;
+ if (InsertPos->getOpcode() == WebAssembly::CATCH)
+ ++InsertPos;
FrameLowering->writeSPToGlobal(WebAssembly::SP32, MF, MBB, InsertPos,
MBB.begin()->getDebugLoc());
}
OpenPOWER on IntegriCloud