diff options
author | Heejin Ahn <aheejin@gmail.com> | 2018-05-17 20:52:03 +0000 |
---|---|---|
committer | Heejin Ahn <aheejin@gmail.com> | 2018-05-17 20:52:03 +0000 |
commit | b4be38fcdd219d4d2c70776d6279c18e532572f8 (patch) | |
tree | d1cf851b7ffacf329e888453bc28ce0eb0fa4395 | |
parent | ecb3e50041d15de76af12a8fbb4d118e8f85a8c0 (diff) | |
download | bcm5719-llvm-b4be38fcdd219d4d2c70776d6279c18e532572f8.tar.gz bcm5719-llvm-b4be38fcdd219d4d2c70776d6279c18e532572f8.zip |
[WebAssembly] Add Wasm personality and isScopedEHPersonality()
Summary:
- Add wasm personality function
- Re-categorize the existing `isFuncletEHPersonality()` function into
two different functions: `isFuncletEHPersonality()` and
`isScopedEHPersonality(). This becomes necessary as wasm EH uses scoped
EH instructions (catchswitch, catchpad/ret, and cleanuppad/ret) but not
outlined funclets.
- Changed some callsites of `isFuncletEHPersonality()` to
`isScopedEHPersonality()` if they are related to scoped EH IR-level
stuff.
Reviewers: majnemer, dschuff, rnk
Subscribers: jfb, sbc100, jgravelle-google, eraman, JDevlieghere, sunfish, llvm-commits
Differential Revision: https://reviews.llvm.org/D45559
llvm-svn: 332667
-rw-r--r-- | llvm/include/llvm/Analysis/EHPersonalities.h | 19 | ||||
-rw-r--r-- | llvm/lib/Analysis/EHPersonalities.cpp | 30 | ||||
-rw-r--r-- | llvm/lib/Analysis/MustExecute.cpp | 2 | ||||
-rw-r--r-- | llvm/lib/CodeGen/DwarfEHPrepare.cpp | 4 | ||||
-rw-r--r-- | llvm/lib/CodeGen/MachineVerifier.cpp | 2 | ||||
-rw-r--r-- | llvm/lib/CodeGen/WinEHPrepare.cpp | 6 | ||||
-rw-r--r-- | llvm/lib/Transforms/InstCombine/InstructionCombining.cpp | 1 | ||||
-rw-r--r-- | llvm/lib/Transforms/Instrumentation/GCOVProfiling.cpp | 12 | ||||
-rw-r--r-- | llvm/lib/Transforms/ObjCARC/ObjCARCContract.cpp | 2 | ||||
-rw-r--r-- | llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp | 2 | ||||
-rw-r--r-- | llvm/lib/Transforms/Utils/EscapeEnumerator.cpp | 4 | ||||
-rw-r--r-- | llvm/lib/Transforms/Utils/InlineFunction.cpp | 2 |
12 files changed, 53 insertions, 33 deletions
diff --git a/llvm/include/llvm/Analysis/EHPersonalities.h b/llvm/include/llvm/Analysis/EHPersonalities.h index cb8092e26c2..fe0e65b828c 100644 --- a/llvm/include/llvm/Analysis/EHPersonalities.h +++ b/llvm/include/llvm/Analysis/EHPersonalities.h @@ -32,7 +32,8 @@ enum class EHPersonality { MSVC_Win64SEH, MSVC_CXX, CoreCLR, - Rust + Rust, + Wasm_CXX }; /// See if the given exception handling personality function is one @@ -74,6 +75,22 @@ inline bool isFuncletEHPersonality(EHPersonality Pers) { llvm_unreachable("invalid enum"); } +/// Returns true if this personality uses scope-style EH IR instructions: +/// catchswitch, catchpad/ret, and cleanuppad/ret. +inline bool isScopedEHPersonality(EHPersonality Pers) { + switch (Pers) { + case EHPersonality::MSVC_CXX: + case EHPersonality::MSVC_X86SEH: + case EHPersonality::MSVC_Win64SEH: + case EHPersonality::CoreCLR: + case EHPersonality::Wasm_CXX: + return true; + default: + return false; + } + llvm_unreachable("invalid enum"); +} + /// Return true if this personality may be safely removed if there /// are no invoke instructions remaining in the current function. inline bool isNoOpWithoutInvoke(EHPersonality Pers) { diff --git a/llvm/lib/Analysis/EHPersonalities.cpp b/llvm/lib/Analysis/EHPersonalities.cpp index b12ae9884e3..2d35a3fa911 100644 --- a/llvm/lib/Analysis/EHPersonalities.cpp +++ b/llvm/lib/Analysis/EHPersonalities.cpp @@ -25,20 +25,21 @@ EHPersonality llvm::classifyEHPersonality(const Value *Pers) { if (!F) return EHPersonality::Unknown; return StringSwitch<EHPersonality>(F->getName()) - .Case("__gnat_eh_personality", EHPersonality::GNU_Ada) - .Case("__gxx_personality_v0", EHPersonality::GNU_CXX) - .Case("__gxx_personality_seh0",EHPersonality::GNU_CXX) - .Case("__gxx_personality_sj0", EHPersonality::GNU_CXX_SjLj) - .Case("__gcc_personality_v0", EHPersonality::GNU_C) - .Case("__gcc_personality_seh0",EHPersonality::GNU_C) - .Case("__gcc_personality_sj0", EHPersonality::GNU_C_SjLj) - .Case("__objc_personality_v0", EHPersonality::GNU_ObjC) - .Case("_except_handler3", EHPersonality::MSVC_X86SEH) - .Case("_except_handler4", EHPersonality::MSVC_X86SEH) - .Case("__C_specific_handler", EHPersonality::MSVC_Win64SEH) - .Case("__CxxFrameHandler3", EHPersonality::MSVC_CXX) - .Case("ProcessCLRException", EHPersonality::CoreCLR) - .Case("rust_eh_personality", EHPersonality::Rust) + .Case("__gnat_eh_personality", EHPersonality::GNU_Ada) + .Case("__gxx_personality_v0", EHPersonality::GNU_CXX) + .Case("__gxx_personality_seh0", EHPersonality::GNU_CXX) + .Case("__gxx_personality_sj0", EHPersonality::GNU_CXX_SjLj) + .Case("__gcc_personality_v0", EHPersonality::GNU_C) + .Case("__gcc_personality_seh0", EHPersonality::GNU_C) + .Case("__gcc_personality_sj0", EHPersonality::GNU_C_SjLj) + .Case("__objc_personality_v0", EHPersonality::GNU_ObjC) + .Case("_except_handler3", EHPersonality::MSVC_X86SEH) + .Case("_except_handler4", EHPersonality::MSVC_X86SEH) + .Case("__C_specific_handler", EHPersonality::MSVC_Win64SEH) + .Case("__CxxFrameHandler3", EHPersonality::MSVC_CXX) + .Case("ProcessCLRException", EHPersonality::CoreCLR) + .Case("rust_eh_personality", EHPersonality::Rust) + .Case("__gxx_wasm_personality_v0", EHPersonality::Wasm_CXX) .Default(EHPersonality::Unknown); } @@ -55,6 +56,7 @@ StringRef llvm::getEHPersonalityName(EHPersonality Pers) { case EHPersonality::MSVC_CXX: return "__CxxFrameHandler3"; case EHPersonality::CoreCLR: return "ProcessCLRException"; case EHPersonality::Rust: return "rust_eh_personality"; + case EHPersonality::Wasm_CXX: return "__gxx_wasm_personality_v0"; case EHPersonality::Unknown: llvm_unreachable("Unknown EHPersonality!"); } diff --git a/llvm/lib/Analysis/MustExecute.cpp b/llvm/lib/Analysis/MustExecute.cpp index 677b5a28222..d8bc7fa19ae 100644 --- a/llvm/lib/Analysis/MustExecute.cpp +++ b/llvm/lib/Analysis/MustExecute.cpp @@ -52,7 +52,7 @@ void llvm::computeLoopSafetyInfo(LoopSafetyInfo *SafetyInfo, Loop *CurLoop) { Function *Fn = CurLoop->getHeader()->getParent(); if (Fn->hasPersonalityFn()) if (Constant *PersonalityFn = Fn->getPersonalityFn()) - if (isFuncletEHPersonality(classifyEHPersonality(PersonalityFn))) + if (isScopedEHPersonality(classifyEHPersonality(PersonalityFn))) SafetyInfo->BlockColors = colorEHFunclets(*Fn); } diff --git a/llvm/lib/CodeGen/DwarfEHPrepare.cpp b/llvm/lib/CodeGen/DwarfEHPrepare.cpp index 13bedc45921..64ed2f70887 100644 --- a/llvm/lib/CodeGen/DwarfEHPrepare.cpp +++ b/llvm/lib/CodeGen/DwarfEHPrepare.cpp @@ -195,9 +195,9 @@ bool DwarfEHPrepare::InsertUnwindResumeCalls(Function &Fn) { if (Resumes.empty()) return false; - // Check the personality, don't do anything if it's funclet-based. + // Check the personality, don't do anything if it's scope-based. EHPersonality Pers = classifyEHPersonality(Fn.getPersonalityFn()); - if (isFuncletEHPersonality(Pers)) + if (isScopedEHPersonality(Pers)) return false; LLVMContext &Ctx = Fn.getContext(); diff --git a/llvm/lib/CodeGen/MachineVerifier.cpp b/llvm/lib/CodeGen/MachineVerifier.cpp index 03b5e8c7779..c2f5a9d4313 100644 --- a/llvm/lib/CodeGen/MachineVerifier.cpp +++ b/llvm/lib/CodeGen/MachineVerifier.cpp @@ -646,7 +646,7 @@ MachineVerifier::visitMachineBasicBlockBefore(const MachineBasicBlock *MBB) { !(AsmInfo && AsmInfo->getExceptionHandlingType() == ExceptionHandling::SjLj && BB && isa<SwitchInst>(BB->getTerminator())) && - !isFuncletEHPersonality(classifyEHPersonality(F.getPersonalityFn()))) + !isScopedEHPersonality(classifyEHPersonality(F.getPersonalityFn()))) report("MBB has more than one landing pad successor", MBB); // Call AnalyzeBranch. If it succeeds, there several more conditions to check. diff --git a/llvm/lib/CodeGen/WinEHPrepare.cpp b/llvm/lib/CodeGen/WinEHPrepare.cpp index 199e7228a8a..74ddf09974b 100644 --- a/llvm/lib/CodeGen/WinEHPrepare.cpp +++ b/llvm/lib/CodeGen/WinEHPrepare.cpp @@ -41,7 +41,7 @@ using namespace llvm; static cl::opt<bool> DisableDemotion( "disable-demotion", cl::Hidden, cl::desc( - "Clone multicolor basic blocks but do not demote cross funclet values"), + "Clone multicolor basic blocks but do not demote cross scopes"), cl::init(false)); static cl::opt<bool> DisableCleanups( @@ -106,8 +106,8 @@ bool WinEHPrepare::runOnFunction(Function &Fn) { // Classify the personality to see what kind of preparation we need. Personality = classifyEHPersonality(Fn.getPersonalityFn()); - // Do nothing if this is not a funclet-based personality. - if (!isFuncletEHPersonality(Personality)) + // Do nothing if this is not a scope-based personality. + if (!isScopedEHPersonality(Personality)) return false; DL = &Fn.getParent()->getDataLayout(); diff --git a/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp b/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp index 6c48db5d225..7ccb65d6531 100644 --- a/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp +++ b/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp @@ -2567,6 +2567,7 @@ static bool isCatchAll(EHPersonality Personality, Constant *TypeInfo) { case EHPersonality::MSVC_Win64SEH: case EHPersonality::MSVC_CXX: case EHPersonality::CoreCLR: + case EHPersonality::Wasm_CXX: return TypeInfo->isNullValue(); } llvm_unreachable("invalid enum"); diff --git a/llvm/lib/Transforms/Instrumentation/GCOVProfiling.cpp b/llvm/lib/Transforms/Instrumentation/GCOVProfiling.cpp index c8eb680bbdf..5e05aab7716 100644 --- a/llvm/lib/Transforms/Instrumentation/GCOVProfiling.cpp +++ b/llvm/lib/Transforms/Instrumentation/GCOVProfiling.cpp @@ -504,11 +504,11 @@ static bool functionHasLines(Function &F) { return false; } -static bool isUsingFuncletBasedEH(Function &F) { +static bool isUsingScopeBasedEH(Function &F) { if (!F.hasPersonalityFn()) return false; EHPersonality Personality = classifyEHPersonality(F.getPersonalityFn()); - return isFuncletEHPersonality(Personality); + return isScopedEHPersonality(Personality); } static bool shouldKeepInEntry(BasicBlock::iterator It) { @@ -551,8 +551,8 @@ void GCOVProfiler::emitProfileNotes() { DISubprogram *SP = F.getSubprogram(); if (!SP) continue; if (!functionHasLines(F)) continue; - // TODO: Functions using funclet-based EH are currently not supported. - if (isUsingFuncletBasedEH(F)) continue; + // TODO: Functions using scope-based EH are currently not supported. + if (isUsingScopeBasedEH(F)) continue; // gcov expects every function to start with an entry block that has a // single successor, so split the entry block to make sure of that. @@ -630,8 +630,8 @@ bool GCOVProfiler::emitProfileArcs() { DISubprogram *SP = F.getSubprogram(); if (!SP) continue; if (!functionHasLines(F)) continue; - // TODO: Functions using funclet-based EH are currently not supported. - if (isUsingFuncletBasedEH(F)) continue; + // TODO: Functions using scope-based EH are currently not supported. + if (isUsingScopeBasedEH(F)) continue; if (!Result) Result = true; unsigned Edges = 0; diff --git a/llvm/lib/Transforms/ObjCARC/ObjCARCContract.cpp b/llvm/lib/Transforms/ObjCARC/ObjCARCContract.cpp index 55881b01b45..1f1ea9f5873 100644 --- a/llvm/lib/Transforms/ObjCARC/ObjCARCContract.cpp +++ b/llvm/lib/Transforms/ObjCARC/ObjCARCContract.cpp @@ -550,7 +550,7 @@ bool ObjCARCContract::runOnFunction(Function &F) { DenseMap<BasicBlock *, ColorVector> BlockColors; if (F.hasPersonalityFn() && - isFuncletEHPersonality(classifyEHPersonality(F.getPersonalityFn()))) + isScopedEHPersonality(classifyEHPersonality(F.getPersonalityFn()))) BlockColors = colorEHFunclets(F); LLVM_DEBUG(llvm::dbgs() << "**** ObjCARC Contract ****\n"); diff --git a/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp b/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp index 8d657f8b258..21e2848030f 100644 --- a/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp +++ b/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp @@ -722,7 +722,7 @@ void ObjCARCOpt::OptimizeIndividualCalls(Function &F) { DenseMap<BasicBlock *, ColorVector> BlockColors; if (F.hasPersonalityFn() && - isFuncletEHPersonality(classifyEHPersonality(F.getPersonalityFn()))) + isScopedEHPersonality(classifyEHPersonality(F.getPersonalityFn()))) BlockColors = colorEHFunclets(F); // Visit all objc_* calls in F. diff --git a/llvm/lib/Transforms/Utils/EscapeEnumerator.cpp b/llvm/lib/Transforms/Utils/EscapeEnumerator.cpp index cd3d01e0d61..7530b35ef65 100644 --- a/llvm/lib/Transforms/Utils/EscapeEnumerator.cpp +++ b/llvm/lib/Transforms/Utils/EscapeEnumerator.cpp @@ -73,8 +73,8 @@ IRBuilder<> *EscapeEnumerator::Next() { F.setPersonalityFn(PersFn); } - if (isFuncletEHPersonality(classifyEHPersonality(F.getPersonalityFn()))) { - report_fatal_error("Funclet EH not supported"); + if (isScopedEHPersonality(classifyEHPersonality(F.getPersonalityFn()))) { + report_fatal_error("Scoped EH not supported"); } LandingPadInst *LPad = diff --git a/llvm/lib/Transforms/Utils/InlineFunction.cpp b/llvm/lib/Transforms/Utils/InlineFunction.cpp index 761c368508b..1e15a4b5d51 100644 --- a/llvm/lib/Transforms/Utils/InlineFunction.cpp +++ b/llvm/lib/Transforms/Utils/InlineFunction.cpp @@ -1569,7 +1569,7 @@ bool llvm::InlineFunction(CallSite CS, InlineFunctionInfo &IFI, Instruction *CallSiteEHPad = nullptr; if (CallerPersonality) { EHPersonality Personality = classifyEHPersonality(CallerPersonality); - if (isFuncletEHPersonality(Personality)) { + if (isScopedEHPersonality(Personality)) { Optional<OperandBundleUse> ParentFunclet = CS.getOperandBundle(LLVMContext::OB_funclet); if (ParentFunclet) |