25#include "llvm/IR/IntrinsicInst.h"
26#include "llvm/IR/Intrinsics.h"
27#include "llvm/IR/IntrinsicsWebAssembly.h"
28#include "llvm/Support/SaveAndRestore.h"
31using namespace CodeGen;
36 llvm::FunctionType *FTy =
43 llvm::FunctionType *FTy =
44 llvm::FunctionType::get(CGM.
VoidTy,
false);
49 llvm::FunctionType *FTy =
50 llvm::FunctionType::get(CGM.
VoidTy,
false);
57 llvm::FunctionType *FTy =
66 llvm::FunctionType *FTy =
67 llvm::FunctionType::get(
VoidTy,
false);
74 name =
"_ZSt9terminatev";
78 name =
"__std_terminate";
80 name =
"?terminate@@YAXXZ";
83 name =
"objc_terminate";
91 llvm::FunctionType *FTy =
135 const llvm::Triple &
T =
Target.getTriple();
136 if (
T.isWindowsMSVCEnvironment())
150 const llvm::Triple &
T =
Target.getTriple();
151 if (
T.isWindowsMSVCEnvironment())
175 llvm_unreachable(
"bad runtime kind");
180 const llvm::Triple &
T =
Target.getTriple();
181 if (
T.isWindowsMSVCEnvironment())
203 if (
Target.getTriple().isWindowsMSVCEnvironment())
230 llvm_unreachable(
"bad runtime kind");
234 if (
T.getArch() == llvm::Triple::x86)
263 return get(CGF.
CGM, dyn_cast_or_null<FunctionDecl>(FD));
270 llvm::AttributeList(),
true);
276 return cast<llvm::Constant>(Fn.getCallee());
281 for (
unsigned I = 0,
E = LPI->getNumClauses(); I !=
E; ++I) {
284 llvm::Value *Val = LPI->getClause(I)->stripPointerCasts();
285 if (LPI->isCatch(I)) {
287 if (llvm::GlobalVariable *GV = dyn_cast<llvm::GlobalVariable>(Val))
290 if (GV->getName().starts_with(
"OBJC_EHTYPE"))
294 llvm::Constant *CVal = cast<llvm::Constant>(Val);
295 for (llvm::User::op_iterator
296 II = CVal->op_begin(), IE = CVal->op_end(); II != IE; ++II) {
297 if (llvm::GlobalVariable *GV =
298 cast<llvm::GlobalVariable>((*II)->stripPointerCasts()))
301 if (GV->getName().starts_with(
"OBJC_EHTYPE"))
312 for (llvm::User *
U : Fn->users()) {
314 if (llvm::ConstantExpr *CE = dyn_cast<llvm::ConstantExpr>(
U)) {
315 if (CE->getOpcode() != llvm::Instruction::BitCast)
return false;
322 llvm::Function *F = dyn_cast<llvm::Function>(
U);
323 if (!F)
return false;
325 for (llvm::BasicBlock &BB : *F) {
326 if (BB.isLandingPad())
339void CodeGenModule::SimplifyPersonality() {
341 if (!LangOpts.CPlusPlus || !LangOpts.ObjC || !LangOpts.Exceptions)
354 assert(std::strcmp(
ObjCXX.PersonalityFn,
CXX.PersonalityFn) != 0 &&
355 "Different EHPersonalities using the same personality function.");
360 if (!Fn ||
Fn->use_empty())
return;
370 if (
Fn->getType() != CXXFn.getCallee()->getType())
373 Fn->replaceAllUsesWith(CXXFn.getCallee());
374 Fn->eraseFromParent();
381 return llvm::ConstantPointerNull::get(CGF.
Int8PtrTy);
389 FreeException(llvm::Value *exn) : exn(exn) {}
423 cleanup, cast<llvm::Instruction>(typedAddr.
emitRawPointer(*
this)));
447 bool KeepInsertionPoint) {
452 const llvm::Triple &
T =
Target.getTriple();
453 if (
CGM.
getLangOpts().OpenMPIsTargetDevice && (
T.isNVPTX() ||
T.isAMDGCN())) {
457 if (
const Expr *SubExpr =
E->getSubExpr()) {
458 QualType ThrowType = SubExpr->getType();
460 const Stmt *ThrowStmt =
E->getSubExpr();
472 if (KeepInsertionPoint)
483 if (
const CapturedDecl* CD = dyn_cast_or_null<CapturedDecl>(
D)) {
511 diag::warn_wasm_dynamic_exception_spec_ignored)
525 diag::warn_wasm_dynamic_exception_spec_ignored)
531 for (
unsigned I = 0; I != NumExceptions; ++I) {
536 Filter->setFilter(I, EHType);
549 if (!dispatchBlock)
return;
550 if (dispatchBlock->use_empty()) {
551 delete dispatchBlock;
564 llvm::Value *zero = CGF.
Builder.getInt32(0);
565 llvm::Value *failsFilter =
566 CGF.
Builder.CreateICmpSLT(selector, zero,
"ehspec.fails");
567 CGF.
Builder.CreateCondBr(failsFilter, unexpectedBB,
579 ->setDoesNotReturn();
580 CGF.
Builder.CreateUnreachable();
590 if (
const CapturedDecl* CD = dyn_cast_or_null<CapturedDecl>(
D)) {
626 const llvm::Triple &
T =
Target.getTriple();
629 const bool IsTargetDevice =
639 unsigned NumHandlers = S.getNumHandlers();
642 for (
unsigned I = 0; I != NumHandlers; ++I) {
646 if (
C->getExceptionDecl()) {
655 C->getCaughtType().getNonReferenceType(), CaughtTypeQuals);
662 CaughtType,
C->getCaughtType());
689 if (!dispatchBlock) {
719 return dispatchBlock;
734 return DispatchBlock;
744 DispatchBlock->setName(
"catch.dispatch");
748 DispatchBlock->setName(
"ehcleanup");
752 llvm_unreachable(
"exception specifications not handled yet!");
755 DispatchBlock->setName(
"terminate");
759 return DispatchBlock;
766 switch (S.getKind()) {
768 return !cast<EHCleanupScope>(S).isEHCleanup();
775 llvm_unreachable(
"Invalid EHScope Kind!");
787 if (!LO.Exceptions || LO.IgnoreExceptions) {
788 if (!LO.Borland && !LO.MicrosoftExt)
795 if (LO.CUDA && LO.CUDAIsDevice)
805 if (!
CurFn->hasPersonalityFn())
821 ir->setCachedLandingPad(LP);
831 "LandingPad should not be emitted when -fignore-exceptions are in "
834 switch (innermostEHScope.
getKind()) {
846 CGBuilderTy::InsertPoint savedIP =
Builder.saveAndClearIP();
853 llvm::LandingPadInst *LPadInst =
856 llvm::Value *LPadExn =
Builder.CreateExtractValue(LPadInst, 0);
858 llvm::Value *LPadSel =
Builder.CreateExtractValue(LPadInst, 1);
867 bool hasCatchAll =
false;
868 bool hasCleanup =
false;
869 bool hasFilter =
false;
875 switch (I->getKind()) {
878 hasCleanup = (hasCleanup || cast<EHCleanupScope>(*I).isEHCleanup());
882 assert(I.next() ==
EHStack.
end() &&
"EH filter is not end of EH stack");
883 assert(!hasCatchAll &&
"EH filter reached after catch-all");
890 for (
unsigned i = 0, e = filter.
getNumFilters(); i != e; ++i)
891 filterTypes.push_back(filter.
getFilter(i));
897 assert(!hasCatchAll);
906 for (
unsigned hi = 0, he = catchScope.
getNumHandlers(); hi != he; ++hi) {
909 "landingpads do not support catch handler flags");
913 assert(!hasCatchAll);
919 if (catchTypes.insert(handler.
Type.
RTTI).second)
921 LPadInst->addClause(handler.
Type.
RTTI);
927 assert(!(hasCatchAll && hasFilter));
933 }
else if (hasFilter) {
938 llvm::ArrayType *AType =
939 llvm::ArrayType::get(!filterTypes.empty() ?
943 for (llvm::Value *filterType : filterTypes)
944 Filters.push_back(cast<llvm::Constant>(filterType));
945 llvm::Constant *FilterArray = llvm::ConstantArray::get(AType, Filters);
946 LPadInst->addClause(FilterArray);
950 LPadInst->setCleanup(
true);
953 }
else if (hasCleanup) {
954 LPadInst->setCleanup(
true);
957 assert((LPadInst->getNumClauses() > 0 || LPadInst->isCleanup()) &&
958 "landingpad instruction has no clauses!");
971 assert(DispatchBlock);
973 CGBuilderTy::InsertPoint SavedIP = CGF.
Builder.saveIP();
979 llvm::BasicBlock *UnwindBB =
983 llvm::CatchSwitchInst *CatchSwitch =
984 CGF.
Builder.CreateCatchSwitch(ParentPad, UnwindBB, NumHandlers);
987 for (
unsigned I = 0; I < NumHandlers; ++I) {
999 llvm::Constant::getNullValue(CGF.
VoidPtrTy)});
1004 CatchSwitch->addHandler(Handler.
Block);
1006 CGF.
Builder.restoreIP(SavedIP);
1015 assert(DispatchBlock);
1017 CGBuilderTy::InsertPoint SavedIP = CGF.
Builder.saveIP();
1023 llvm::BasicBlock *UnwindBB =
1027 llvm::CatchSwitchInst *CatchSwitch =
1028 CGF.
Builder.CreateCatchSwitch(ParentPad, UnwindBB, NumHandlers);
1032 llvm::BasicBlock *WasmCatchStartBlock = CGF.
createBasicBlock(
"catch.start");
1033 CatchSwitch->addHandler(WasmCatchStartBlock);
1038 for (
unsigned I = 0,
E = NumHandlers; I <
E; ++I) {
1043 CatchTypes.push_back(
TypeInfo.RTTI);
1045 auto *CPI = CGF.
Builder.CreateCatchPad(CatchSwitch, CatchTypes);
1050 llvm::Function *GetExnFn =
1052 llvm::Function *GetSelectorFn =
1054 llvm::CallInst *Exn = CGF.
Builder.CreateCall(GetExnFn, CPI);
1056 llvm::CallInst *
Selector = CGF.
Builder.CreateCall(GetSelectorFn, CPI);
1058 llvm::Function *TypeIDFn =
1065 CGF.
Builder.restoreIP(SavedIP);
1070 for (
unsigned I = 0,
E = NumHandlers;; ++I) {
1071 assert(I <
E &&
"ran off end of handlers!");
1078 llvm::BasicBlock *NextBlock;
1080 bool EmitNextBlock =
false, NextIsEnd =
false;
1087 EmitNextBlock =
true;
1099 EmitNextBlock =
true;
1103 llvm::CallInst *TypeIndex = CGF.
Builder.CreateCall(TypeIDFn,
TypeInfo.RTTI);
1104 TypeIndex->setDoesNotThrow();
1106 llvm::Value *MatchesTypeIndex =
1108 CGF.
Builder.CreateCondBr(MatchesTypeIndex, Handler.
Block, NextBlock);
1116 CGF.
Builder.restoreIP(SavedIP);
1129 assert(dispatchBlock);
1139 CGBuilderTy::InsertPoint savedIP = CGF.
Builder.saveIP();
1143 llvm::Function *llvm_eh_typeid_for =
1145 llvm::Type *argTy = llvm_eh_typeid_for->getArg(0)->getType();
1153 assert(i < e &&
"ran off end of handlers!");
1156 llvm::Value *typeValue = handler.
Type.
RTTI;
1158 "landingpads do not support catch handler flags");
1159 assert(typeValue &&
"fell into catch-all case!");
1161 if (typeValue->getType() != argTy)
1167 llvm::BasicBlock *nextBlock;
1188 llvm::CallInst *typeIndex =
1189 CGF.
Builder.CreateCall(llvm_eh_typeid_for, typeValue);
1190 typeIndex->setDoesNotThrow();
1192 llvm::Value *matchesTypeIndex =
1193 CGF.
Builder.CreateICmpEQ(selector, typeIndex,
"matches");
1194 CGF.
Builder.CreateCondBr(matchesTypeIndex, handler.
Block, nextBlock);
1198 CGF.
Builder.restoreIP(savedIP);
1214 unsigned NumHandlers = S.getNumHandlers();
1232 CatchScope.
begin(), CatchScope.
begin() + NumHandlers);
1245 bool doImplicitRethrow =
false;
1247 doImplicitRethrow = isa<CXXDestructorDecl>(
CurCodeDecl) ||
1254 llvm::BasicBlock *WasmCatchStartBlock =
nullptr;
1257 cast<llvm::CatchSwitchInst>(DispatchBlock->getFirstNonPHIIt());
1258 WasmCatchStartBlock = CatchSwitch->hasUnwindDest()
1259 ? CatchSwitch->getSuccessor(1)
1260 : CatchSwitch->getSuccessor(0);
1262 cast<llvm::CatchPadInst>(WasmCatchStartBlock->getFirstNonPHIIt());
1273 bool HasCatchAll =
false;
1274 for (
unsigned I = NumHandlers; I != 0; --I) {
1275 HasCatchAll |= Handlers[I - 1].isCatchAll();
1276 llvm::BasicBlock *CatchBlock = Handlers[I-1].Block;
1308 Builder.ClearInsertionPoint();
1324 assert(WasmCatchStartBlock);
1329 llvm::BasicBlock *RethrowBlock = WasmCatchStartBlock;
1330 while (llvm::Instruction *TI = RethrowBlock->getTerminator()) {
1331 auto *BI = cast<llvm::BranchInst>(TI);
1332 assert(BI->isConditional());
1333 RethrowBlock = BI->getSuccessor(1);
1335 assert(RethrowBlock != WasmCatchStartBlock && RethrowBlock->empty());
1336 Builder.SetInsertPoint(RethrowBlock);
1337 llvm::Function *RethrowInCatchFn =
1348 llvm::Value *ForEHVar;
1349 llvm::FunctionCallee EndCatchFn;
1350 CallEndCatchForFinally(llvm::Value *ForEHVar,
1351 llvm::FunctionCallee EndCatchFn)
1352 : ForEHVar(ForEHVar), EndCatchFn(EndCatchFn) {}
1356 llvm::BasicBlock *CleanupContBB =
1359 llvm::Value *ShouldEndCatch =
1361 CGF.
Builder.CreateCondBr(ShouldEndCatch, EndCatchBB, CleanupContBB);
1370 llvm::Value *ForEHVar;
1371 llvm::FunctionCallee EndCatchFn;
1372 llvm::FunctionCallee RethrowFn;
1373 llvm::Value *SavedExnVar;
1375 PerformFinally(
const Stmt *Body, llvm::Value *ForEHVar,
1376 llvm::FunctionCallee EndCatchFn,
1377 llvm::FunctionCallee RethrowFn, llvm::Value *SavedExnVar)
1378 : Body(Body), ForEHVar(ForEHVar), EndCatchFn(EndCatchFn),
1379 RethrowFn(RethrowFn), SavedExnVar(SavedExnVar) {}
1385 ForEHVar, EndCatchFn);
1389 llvm::Value *SavedCleanupDest =
1391 "cleanup.dest.saved");
1402 llvm::Value *ShouldRethrow =
1404 CGF.
Builder.CreateCondBr(ShouldRethrow, RethrowBB, ContBB);
1414 CGF.
Builder.CreateUnreachable();
1427 CGBuilderTy::InsertPoint SavedIP = CGF.
Builder.saveAndClearIP();
1429 CGF.
Builder.restoreIP(SavedIP);
1443 llvm::FunctionCallee beginCatchFn,
1444 llvm::FunctionCallee endCatchFn,
1445 llvm::FunctionCallee rethrowFn) {
1446 assert((!!beginCatchFn) == (!!endCatchFn) &&
1447 "begin/end catch functions not paired");
1448 assert(rethrowFn &&
"rethrow function is required");
1450 BeginCatchFn = beginCatchFn;
1458 llvm::FunctionType *rethrowFnTy = rethrowFn.getFunctionType();
1459 SavedExnVar =
nullptr;
1460 if (rethrowFnTy->getNumParams())
1486 ForEHVar, endCatchFn,
1487 rethrowFn, SavedExnVar);
1503 if (catchBB->use_empty()) {
1506 CGBuilderTy::InsertPoint savedIP = CGF.
Builder.saveAndClearIP();
1509 llvm::Value *exn =
nullptr;
1529 CGF.
Builder.restoreIP(savedIP);
1537 if (TerminateLandingPad)
1538 return TerminateLandingPad;
1540 CGBuilderTy::InsertPoint SavedIP =
Builder.saveAndClearIP();
1544 Builder.SetInsertPoint(TerminateLandingPad);
1549 if (!
CurFn->hasPersonalityFn())
1552 llvm::LandingPadInst *LPadInst =
1556 llvm::Value *Exn =
nullptr;
1558 Exn =
Builder.CreateExtractValue(LPadInst, 0);
1559 llvm::CallInst *terminateCall =
1561 terminateCall->setDoesNotReturn();
1567 return TerminateLandingPad;
1571 if (TerminateHandler)
1572 return TerminateHandler;
1577 CGBuilderTy::InsertPoint SavedIP =
Builder.saveAndClearIP();
1578 Builder.SetInsertPoint(TerminateHandler);
1580 llvm::Value *Exn =
nullptr;
1583 llvm::CallInst *terminateCall =
1585 terminateCall->setDoesNotReturn();
1591 return TerminateHandler;
1596 "use getTerminateLandingPad for non-funclet EH");
1599 if (TerminateFunclet)
1600 return TerminateFunclet;
1602 CGBuilderTy::InsertPoint SavedIP =
Builder.saveAndClearIP();
1607 Builder.SetInsertPoint(TerminateFunclet);
1618 llvm::CallInst *terminateCall =
1620 terminateCall->setDoesNotReturn();
1626 return TerminateFunclet;
1632 CGBuilderTy::InsertPoint SavedIP =
Builder.saveIP();
1643 if (RethrowName !=
nullptr && !isCleanup) {
1655 llvm::Type *LPadType = llvm::StructType::get(Exn->getType(), Sel->getType());
1656 llvm::Value *LPadVal = llvm::PoisonValue::get(LPadType);
1657 LPadVal =
Builder.CreateInsertValue(LPadVal, Exn, 0,
"lpad.val");
1658 LPadVal =
Builder.CreateInsertValue(LPadVal, Sel, 1,
"lpad.val");
1660 Builder.CreateResume(LPadVal);
1672 llvm::BasicBlock *TryBB =
nullptr;
1677 TryBB =
Builder.GetInsertBlock();
1690 if (!TryExit.
getBlock()->use_empty())
1703 !
V.insert(BB).second ||
1704 !BB->getParent() || BB->empty())
1707 if (!BB->isEHPad()) {
1708 for (llvm::BasicBlock::iterator J = BB->begin(), JE = BB->end(); J != JE;
1710 if (
auto LI = dyn_cast<llvm::LoadInst>(J)) {
1711 LI->setVolatile(
true);
1712 }
else if (
auto SI = dyn_cast<llvm::StoreInst>(J)) {
1713 SI->setVolatile(
true);
1714 }
else if (
auto* MCI = dyn_cast<llvm::MemIntrinsic>(J)) {
1715 MCI->setVolatile(llvm::ConstantInt::get(
Builder.getInt1Ty(), 1));
1719 const llvm::Instruction *TI = BB->getTerminator();
1721 unsigned N = TI->getNumSuccessors();
1722 for (
unsigned I = 0; I < N; I++)
1729 llvm::Function *OutlinedFinally;
1730 PerformSEHFinally(llvm::Function *OutlinedFinally)
1731 : OutlinedFinally(OutlinedFinally) {}
1741 llvm::Value *FP =
nullptr;
1744 FP = &CGF.
CurFn->arg_begin()[1];
1746 llvm::Function *LocalAddrFn =
1748 FP = CGF.
Builder.CreateCall(LocalAddrFn);
1751 llvm::Value *IsForEH =
1752 llvm::ConstantInt::get(CGF.
ConvertType(ArgTys[0]), F.isForEHCleanup());
1759 if (!F.isForEHCleanup() && F.hasExitSwitch()) {
1762 llvm::Value *
Zero = llvm::Constant::getNullValue(CGM.
Int32Ty);
1787 : ParentCGF(ParentCGF), ParentThis(ParentThis) {}
1790 bool foundCaptures() {
1791 return !Captures.empty() || SEHCodeSlot.
isValid();
1794 void Visit(
const Stmt *S) {
1797 for (
const Stmt *Child : S->children())
1804 if (
E->refersToEnclosingVariableOrCapture())
1805 Captures.insert(ParentThis);
1807 const auto *
D = dyn_cast<VarDecl>(
E->getDecl());
1808 if (
D &&
D->isLocalVarDeclOrParm() &&
D->hasLocalStorage())
1813 Captures.insert(ParentThis);
1821 unsigned ID =
E->getBuiltinCallee();
1823 case Builtin::BI__exception_code:
1824 case Builtin::BI_exception_code:
1838 llvm::Value *ParentFP) {
1839 llvm::CallInst *RecoverCall =
nullptr;
1841 if (
auto *ParentAlloca =
1842 dyn_cast_or_null<llvm::AllocaInst>(ParentVar.
getBasePointer())) {
1845 auto InsertPair =
ParentCGF.EscapedLocals.insert(
1846 std::make_pair(ParentAlloca,
ParentCGF.EscapedLocals.size()));
1847 int FrameEscapeIdx = InsertPair.first->second;
1849 llvm::Function *FrameRecoverFn = llvm::Intrinsic::getOrInsertDeclaration(
1851 RecoverCall =
Builder.CreateCall(
1853 llvm::ConstantInt::get(
Int32Ty, FrameEscapeIdx)});
1859 auto *ParentRecover = cast<llvm::IntrinsicInst>(
1861 assert(ParentRecover->getIntrinsicID() == llvm::Intrinsic::localrecover &&
1862 "expected alloca or localrecover in parent LocalDeclMap");
1863 RecoverCall = cast<llvm::CallInst>(ParentRecover->clone());
1864 RecoverCall->setArgOperand(1, ParentFP);
1869 llvm::Value *ChildVar =
1871 ChildVar->setName(ParentVar.
getName());
1876 const Stmt *OutlinedStmt,
1880 Finder.Visit(OutlinedStmt);
1884 if (!Finder.foundCaptures() &&
1891 llvm::Value *EntryFP =
nullptr;
1899 {Builder.getInt32(1)});
1903 auto AI =
CurFn->arg_begin();
1908 llvm::Value *ParentFP = EntryFP;
1913 llvm::Function *RecoverFPIntrin =
1927 llvm::AllocaInst *FramePtrAddrAlloca =
nullptr;
1928 for (
auto &I :
ParentCGF.LocalDeclMap) {
1929 const VarDecl *
D = cast<VarDecl>(I.first);
1930 if (isa<ImplicitParamDecl>(
D) &&
1932 assert(
D->getName().starts_with(
"frame_pointer"));
1933 FramePtrAddrAlloca =
1934 cast<llvm::AllocaInst>(I.second.getBasePointer());
1938 assert(FramePtrAddrAlloca);
1939 auto InsertPair =
ParentCGF.EscapedLocals.insert(
1940 std::make_pair(FramePtrAddrAlloca,
ParentCGF.EscapedLocals.size()));
1941 int FrameEscapeIdx = InsertPair.first->second;
1948 llvm::Function *FrameRecoverFn = llvm::Intrinsic::getOrInsertDeclaration(
1950 ParentFP =
Builder.CreateCall(
1952 llvm::ConstantInt::get(
Int32Ty, FrameEscapeIdx)});
1959 for (
const VarDecl *VD : Finder.Captures) {
1965 "captured non-local variable");
1975 auto I =
ParentCGF.LocalDeclMap.find(VD);
1979 Address ParentVar = I->second;
1982 setAddrOfLocalVar(VD, Recovered);
1984 if (isa<ImplicitParamDecl>(VD)) {
1985 CXXABIThisAlignment =
ParentCGF.CXXABIThisAlignment;
1986 CXXThisAlignment =
ParentCGF.CXXThisAlignment;
2001 CXXThisValue = CXXABIThisValue;
2006 if (Finder.SEHCodeSlot.isValid()) {
2020 const Stmt *OutlinedStmt) {
2026 llvm::raw_svector_ostream OS(Name);
2028 assert(ParentSEHFn &&
"No CurSEHParent!");
2043 &
getContext().Idents.get(
"exception_pointers"),
2048 &
getContext().Idents.get(
"abnormal_termination"),
2063 llvm::Function *Fn = llvm::Function::Create(
2064 FnTy, llvm::GlobalValue::InternalLinkage, Name.str(), &
CGM.
getModule());
2111 llvm::Value *ParentFP,
2112 llvm::Value *EntryFP) {
2138 llvm::Type *RecordTy = llvm::PointerType::getUnqual(
getLLVMContext());
2139 llvm::Type *PtrsTy = llvm::StructType::get(RecordTy,
CGM.
VoidPtrTy);
2143 assert(!
SEHCodeSlotStack.empty() &&
"emitting EH code outside of __except");
2151 return llvm::PoisonValue::get(
Int8PtrTy);
2157 assert(!
SEHCodeSlotStack.empty() &&
"emitting EH code outside of __except");
2164 auto AI =
CurFn->arg_begin();
2169 llvm::Function *FinallyFunc) {
2170 EHStack.pushCleanup<PerformSEHFinally>(Kind, FinallyFunc);
2178 llvm::Function *FinallyFunc =
2207 llvm::Function *FilterFunc =
2214 if (S.getFinallyHandler()) {
2227 assert(Except &&
"__try must have __finally xor __except");
2258 llvm::CatchPadInst *CPI =
2259 cast<llvm::CatchPadInst>(CatchPadBB->getFirstNonPHIIt());
2261 Builder.CreateCatchRet(CPI, ExceptBB);
2266 llvm::Function *SEHCodeIntrin =
2268 llvm::Value *Code =
Builder.CreateCall(SEHCodeIntrin, {CPI});
2295 Builder.ClearInsertionPoint();
static llvm::FunctionCallee getUnexpectedFn(CodeGenModule &CGM)
static const EHPersonality & getSEHPersonalityMSVC(const llvm::Triple &T)
static const EHPersonality & getObjCPersonality(const TargetInfo &Target, const CodeGenOptions &CGOpts, const LangOptions &L)
static llvm::FunctionCallee getPersonalityFn(CodeGenModule &CGM, const EHPersonality &Personality)
static void emitFilterDispatchBlock(CodeGenFunction &CGF, EHFilterScope &filterScope)
Emit the dispatch block for a filter scope if necessary.
static void emitCatchPadBlock(CodeGenFunction &CGF, EHCatchScope &CatchScope)
static llvm::FunctionCallee getFreeExceptionFn(CodeGenModule &CGM)
static const EHPersonality & getCXXPersonality(const TargetInfo &Target, const CodeGenOptions &CGOpts)
static llvm::FunctionCallee getSehTryEndFn(CodeGenModule &CGM)
static bool LandingPadHasOnlyCXXUses(llvm::LandingPadInst *LPI)
Check whether a landingpad instruction only uses C++ features.
static bool PersonalityHasOnlyCXXUses(llvm::Constant *Fn)
Check whether a personality function could reasonably be swapped for a C++ personality function.
static const EHPersonality & getCPersonality(const TargetInfo &Target, const CodeGenOptions &CGOpts)
static void emitCatchDispatchBlock(CodeGenFunction &CGF, EHCatchScope &catchScope)
Emit the structure of the dispatch block for the given catch scope.
static llvm::Constant * getOpaquePersonalityFn(CodeGenModule &CGM, const EHPersonality &Personality)
static bool isNonEHScope(const EHScope &S)
Check whether this is a non-EH scope, i.e.
static llvm::FunctionCallee getCatchallRethrowFn(CodeGenModule &CGM, StringRef Name)
static llvm::FunctionCallee getSehTryBeginFn(CodeGenModule &CGM)
static llvm::Constant * getCatchAllValue(CodeGenFunction &CGF)
Returns the value to inject into a selector to indicate the presence of a catch-all.
static void emitWasmCatchPadBlock(CodeGenFunction &CGF, EHCatchScope &CatchScope)
static const EHPersonality & getObjCXXPersonality(const TargetInfo &Target, const CodeGenOptions &CGOpts, const LangOptions &L)
Determines the personality function to use when both C++ and Objective-C exceptions are being caught.
llvm::DenseSet< const void * > Visited
llvm::MachO::Target Target
Defines the Objective-C statement AST node classes.
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
CanQualType UnsignedCharTy
QualType getUnqualifiedArrayType(QualType T, Qualifiers &Quals) const
Return this type as a completely-unqualified array type, capturing the qualifiers in Quals.
CXXCatchStmt - This represents a C++ catch block.
Represents the this expression in C++.
A C++ throw-expression (C++ [except.throw]).
CXXTryStmt - A C++ try block, including all handlers.
CallExpr - Represents a function call (C99 6.5.2.2, C++ [expr.call]).
Represents the body of a CapturedStmt, and serves as its DeclContext.
static CharUnits fromQuantity(QuantityType Quantity)
fromQuantity - Construct a CharUnits quantity from a raw integer type.
CodeGenOptions - Track various options which control how the code is optimized and passed to the back...
bool hasDWARFExceptions() const
bool hasWasmExceptions() const
bool hasSjLjExceptions() const
bool hasSEHExceptions() const
Like RawAddress, an abstract representation of an aligned address, but the pointer contained in this ...
llvm::Value * getBasePointer() const
llvm::Value * emitRawPointer(CodeGenFunction &CGF) const
Return the pointer contained in this class after authenticating it and adding offset to it if necessa...
Address withPointer(llvm::Value *NewPointer, KnownNonNull_t IsKnownNonNull) const
Return address with different pointer, but same element type and alignment.
Address withElementType(llvm::Type *ElemTy) const
Return address with different element type, but same pointer and alignment.
llvm::StringRef getName() const
Return the IR name of the pointer value.
llvm::PointerType * getType() const
Return the type of the pointer value.
static ApplyDebugLocation CreateDefaultArtificial(CodeGenFunction &CGF, SourceLocation TemporaryLocation)
Apply TemporaryLocation if it is valid.
llvm::StoreInst * CreateFlagStore(bool Value, llvm::Value *Addr)
Emit a store to an i1 flag variable.
llvm::StoreInst * CreateStore(llvm::Value *Val, Address Addr, bool IsVolatile=false)
llvm::StoreInst * CreateAlignedStore(llvm::Value *Val, llvm::Value *Addr, CharUnits Align, bool IsVolatile=false)
Address CreateStructGEP(Address Addr, unsigned Index, const llvm::Twine &Name="")
llvm::LoadInst * CreateLoad(Address Addr, const llvm::Twine &Name="")
llvm::LoadInst * CreateFlagLoad(llvm::Value *Addr, const llvm::Twine &Name="")
Emit a load from an i1 flag variable.
llvm::LoadInst * CreateAlignedLoad(llvm::Type *Ty, llvm::Value *Addr, CharUnits Align, const llvm::Twine &Name="")
virtual void emitBeginCatch(CodeGenFunction &CGF, const CXXCatchStmt *C)=0
virtual void emitRethrow(CodeGenFunction &CGF, bool isNoReturn)=0
virtual llvm::CallInst * emitTerminateForUnexpectedException(CodeGenFunction &CGF, llvm::Value *Exn)
virtual CatchTypeInfo getCatchAllTypeInfo()
virtual void emitThrow(CodeGenFunction &CGF, const CXXThrowExpr *E)=0
virtual CatchTypeInfo getAddrOfCXXCatchHandlerType(QualType Ty, QualType CatchHandlerType)=0
MangleContext & getMangleContext()
Gets the mangle context.
static CGCallee forDirect(llvm::Constant *functionPtr, const CGCalleeInfo &abstractInfo=CGCalleeInfo())
CGFunctionInfo - Class to encapsulate the information about a function definition.
virtual llvm::Constant * GetEHType(QualType T)=0
Get the type constant to catch for the given ObjC pointer type.
virtual void EmitThrowStmt(CodeGen::CodeGenFunction &CGF, const ObjCAtThrowStmt &S, bool ClearInsertionPoint=true)=0
CallArgList - Type for representing both the value and type of arguments in a call.
void add(RValue rvalue, QualType type)
void exit(CodeGenFunction &CGF)
void enter(CodeGenFunction &CGF, const Stmt *Finally, llvm::FunctionCallee beginCatchFn, llvm::FunctionCallee endCatchFn, llvm::FunctionCallee rethrowFn)
Enters a finally block for an implementation using zero-cost exceptions.
Enters a new scope for capturing cleanups, all of which will be executed once the scope is exited.
void ForceCleanup(std::initializer_list< llvm::Value ** > ValuesToReload={})
Force the emission of cleanups now, instead of waiting until this object is destroyed.
CodeGenFunction - This class organizes the per-function state that is used while generating LLVM code...
void EmitCXXTryStmt(const CXXTryStmt &S)
llvm::BasicBlock * getFuncletEHDispatchBlock(EHScopeStack::stable_iterator scope)
JumpDest getJumpDestInCurrentScope(llvm::BasicBlock *Target)
The given basic block lies in the current EH scope, but may be a target of a potentially scope-crossi...
bool IsOutlinedSEHHelper
True if the current function is an outlined SEH helper.
llvm::Value * getSelectorFromSlot()
llvm::Value * getExceptionFromSlot()
Returns the contents of the function's exception object and selector slots.
SmallVector< Address, 1 > SEHCodeSlotStack
A stack of exception code slots.
void VolatilizeTryBlocks(llvm::BasicBlock *BB, llvm::SmallPtrSet< llvm::BasicBlock *, 10 > &V)
llvm::BasicBlock * getInvokeDestImpl()
llvm::Type * ConvertType(QualType T)
FieldDecl * LambdaThisCaptureField
Address recoverAddrOfEscapedLocal(CodeGenFunction &ParentCGF, Address ParentVar, llvm::Value *ParentFP)
Recovers the address of a local in a parent function.
void EmitNoreturnRuntimeCallOrInvoke(llvm::FunctionCallee callee, ArrayRef< llvm::Value * > args)
Emits a call or invoke to the given noreturn runtime function.
llvm::CallBase * EmitRuntimeCallOrInvoke(llvm::FunctionCallee callee, ArrayRef< llvm::Value * > args, const Twine &name="")
Emits a call or invoke instruction to the given runtime function.
llvm::Value * EmitSEHAbnormalTermination()
void EmitCXXThrowExpr(const CXXThrowExpr *E, bool KeepInsertionPoint=true)
bool isSEHTryScope() const
Returns true inside SEH __try blocks.
llvm::BasicBlock * createBasicBlock(const Twine &name="", llvm::Function *parent=nullptr, llvm::BasicBlock *before=nullptr)
createBasicBlock - Create an LLVM basic block.
const LangOptions & getLangOpts() const
llvm::BasicBlock * EHResumeBlock
EHResumeBlock - Unified block containing a call to llvm.eh.resume.
llvm::AllocaInst * EHSelectorSlot
The selector slot.
llvm::BasicBlock * EmitLandingPad()
Emits a landing pad for the current EH stack.
void EmitBlockAfterUses(llvm::BasicBlock *BB)
EmitBlockAfterUses - Emit the given block somewhere hopefully near its uses, and leave the insertion ...
void EmitBranchThroughCleanup(JumpDest Dest)
EmitBranchThroughCleanup - Emit a branch from the current insert block through the normal cleanup han...
const Decl * CurCodeDecl
CurCodeDecl - This is the inner-most code context, which includes blocks.
llvm::BasicBlock * getUnreachableBlock()
llvm::AssertingVH< llvm::Instruction > AllocaInsertPt
AllocaInsertPoint - This is an instruction in the entry block before which we prefer to insert alloca...
bool currentFunctionUsesSEHTry() const
llvm::SmallVector< const JumpDest *, 2 > SEHTryEpilogueStack
CodeGenFunction * ParentCGF
void EmitSEHExceptionCodeSave(CodeGenFunction &ParentCGF, llvm::Value *ParentFP, llvm::Value *EntryEBP)
llvm::Value * ExceptionSlot
The exception slot.
void EmitAnyExprToExn(const Expr *E, Address Addr)
llvm::BasicBlock * getEHResumeBlock(bool isCleanup)
const TargetInfo & getTarget() const
llvm::BasicBlock * getTerminateHandler()
getTerminateHandler - Return a handler (not a landing pad, just a catch handler) that just calls term...
void EnterSEHTryStmt(const SEHTryStmt &S)
RValue EmitLoadOfLValue(LValue V, SourceLocation Loc)
EmitLoadOfLValue - Given an expression that represents a value lvalue, this method emits the address ...
void DeactivateCleanupBlock(EHScopeStack::stable_iterator Cleanup, llvm::Instruction *DominatingIP)
DeactivateCleanupBlock - Deactivates the given cleanup block.
void StartFunction(GlobalDecl GD, QualType RetTy, llvm::Function *Fn, const CGFunctionInfo &FnInfo, const FunctionArgList &Args, SourceLocation Loc=SourceLocation(), SourceLocation StartLoc=SourceLocation())
Emit code for the start of a function.
Address getExceptionSlot()
Returns a pointer to the function's exception object and selector slot, which is assigned in every la...
bool HaveInsertPoint() const
HaveInsertPoint - True if an insertion point is defined.
llvm::BasicBlock * getTerminateFunclet()
getTerminateLandingPad - Return a cleanup funclet that just calls terminate.
llvm::BasicBlock * getTerminateLandingPad()
getTerminateLandingPad - Return a landing pad that just calls terminate.
llvm::Function * GenerateSEHFinallyFunction(CodeGenFunction &ParentCGF, const SEHFinallyStmt &Finally)
void EmitStartEHSpec(const Decl *D)
EmitStartEHSpec - Emit the start of the exception spec.
void popCatchScope()
popCatchScope - Pops the catch scope at the top of the EHScope stack, emitting any required code (oth...
llvm::Value * EmitSEHExceptionCode()
llvm::AllocaInst * CreateTempAlloca(llvm::Type *Ty, const Twine &Name="tmp", llvm::Value *ArraySize=nullptr)
CreateTempAlloca - This creates an alloca and inserts it into the entry block if ArraySize is nullptr...
void startOutlinedSEHHelper(CodeGenFunction &ParentCGF, bool IsFilter, const Stmt *OutlinedStmt)
Arrange a function prototype that can be called by Windows exception handling personalities.
void EmitSehTryScopeBegin()
RValue EmitCall(const CGFunctionInfo &CallInfo, const CGCallee &Callee, ReturnValueSlot ReturnValue, const CallArgList &Args, llvm::CallBase **CallOrInvoke, bool IsMustTail, SourceLocation Loc, bool IsVirtualFunctionPointerThunk=false)
EmitCall - Generate a call of the given function, expecting the given result type,...
const TargetCodeGenInfo & getTargetHooks() const
void EmitSEHLeaveStmt(const SEHLeaveStmt &S)
void incrementProfileCounter(const Stmt *S, llvm::Value *StepV=nullptr)
Increment the profiler's counter for the given statement by StepV.
void EmitCapturedLocals(CodeGenFunction &ParentCGF, const Stmt *OutlinedStmt, bool IsFilter)
Scan the outlined statement for captures from the parent function.
void pushSEHCleanup(CleanupKind kind, llvm::Function *FinallyFunc)
llvm::CallInst * EmitNounwindRuntimeCall(llvm::FunctionCallee callee, const Twine &name="")
ASTContext & getContext() const
void EmitStopPoint(const Stmt *S)
EmitStopPoint - Emit a debug stoppoint if we are emitting debug info.
llvm::Value * SEHInfo
Value returned by __exception_info intrinsic.
RawAddress getNormalCleanupDestSlot()
void EmitAnyExprToMem(const Expr *E, Address Location, Qualifiers Quals, bool IsInitializer)
EmitAnyExprToMem - Emits the code necessary to evaluate an arbitrary expression into the given memory...
void EmitStmt(const Stmt *S, ArrayRef< const Attr * > Attrs={})
EmitStmt - Emit the code for the statement.
llvm::DenseMap< const ValueDecl *, FieldDecl * > LambdaCaptureFields
llvm::CallInst * EmitRuntimeCall(llvm::FunctionCallee callee, const Twine &name="")
llvm::Type * ConvertTypeForMem(QualType T)
void EmitEndEHSpec(const Decl *D)
EmitEndEHSpec - Emit the end of the exception spec.
void ExitSEHTryStmt(const SEHTryStmt &S)
LValue EmitLValueForLambdaField(const FieldDecl *Field)
void ExitCXXTryStmt(const CXXTryStmt &S, bool IsFnTryBlock=false)
llvm::BasicBlock * getEHDispatchBlock(EHScopeStack::stable_iterator scope)
RawAddress CreateMemTemp(QualType T, const Twine &Name="tmp", RawAddress *Alloca=nullptr)
CreateMemTemp - Create a temporary memory object of the given type, with appropriate alignmen and cas...
llvm::Value * EmitScalarExpr(const Expr *E, bool IgnoreResultAssign=false)
EmitScalarExpr - Emit the computation of the specified expression of LLVM scalar type,...
llvm::CallInst * EmitTrapCall(llvm::Intrinsic::ID IntrID)
Emit a call to trap or debugtrap and attach function attribute "trap-func-name" if specified.
void FinishFunction(SourceLocation EndLoc=SourceLocation())
FinishFunction - Complete IR generation of the current function.
void EnterCXXTryStmt(const CXXTryStmt &S, bool IsFnTryBlock=false)
Address ReturnValue
ReturnValue - The temporary alloca to hold the return value.
llvm::Instruction * CurrentFuncletPad
void EnsureInsertPoint()
EnsureInsertPoint - Ensure that an insertion point is defined so that emitted IR has a place to go.
llvm::LLVMContext & getLLVMContext()
llvm::Value * EmitSEHExceptionInfo()
void EmitSEHTryStmt(const SEHTryStmt &S)
void PopCleanupBlock(bool FallThroughIsBranchThrough=false, bool ForDeactivation=false)
PopCleanupBlock - Will pop the cleanup entry on the stack and process all branch fixups.
Address getEHSelectorSlot()
llvm::Function * GenerateSEHFilterFunction(CodeGenFunction &ParentCGF, const SEHExceptStmt &Except)
Create a stub filter function that will ultimately hold the code of the filter expression.
void EmitBlock(llvm::BasicBlock *BB, bool IsFinished=false)
EmitBlock - Emit the given block.
This class organizes the cross-function state that is used while generating LLVM code.
void SetInternalFunctionAttributes(GlobalDecl GD, llvm::Function *F, const CGFunctionInfo &FI)
Set the attributes on the LLVM function for the given decl and function info.
llvm::Module & getModule() const
llvm::FunctionCallee CreateRuntimeFunction(llvm::FunctionType *Ty, StringRef Name, llvm::AttributeList ExtraAttrs=llvm::AttributeList(), bool Local=false, bool AssumeConvergent=false)
Create or return a runtime function declaration with the specified type and name.
llvm::Constant * GetAddrOfRTTIDescriptor(QualType Ty, bool ForEH=false)
Get the address of the RTTI descriptor for the given type.
DiagnosticsEngine & getDiags() const
void ErrorUnsupported(const Stmt *S, const char *Type)
Print out an error that codegen doesn't support the specified stmt yet.
const LangOptions & getLangOpts() const
CodeGenTypes & getTypes()
const TargetInfo & getTarget() const
CGCXXABI & getCXXABI() const
ASTContext & getContext() const
const CodeGenOptions & getCodeGenOpts() const
llvm::FunctionCallee getTerminateFn()
Get the declaration of std::terminate for the platform.
llvm::LLVMContext & getLLVMContext()
llvm::Function * getIntrinsic(unsigned IID, ArrayRef< llvm::Type * > Tys={})
CGObjCRuntime & getObjCRuntime()
Return a reference to the configured Objective-C runtime.
LangAS GetGlobalVarAddressSpace(const VarDecl *D)
Return the AST address space of the underlying global variable for D, as determined by its declaratio...
llvm::FunctionType * GetFunctionType(const CGFunctionInfo &Info)
GetFunctionType - Get the LLVM function type for.
const CGFunctionInfo & arrangeBuiltinFunctionDeclaration(QualType resultType, const FunctionArgList &args)
A builtin function is a freestanding function using the default C conventions.
const CGFunctionInfo & arrangeBuiltinFunctionCall(QualType resultType, const CallArgList &args)
llvm::Constant * tryEmitAbstract(const Expr *E, QualType T)
Try to emit the result of the given expression as an abstract constant.
A scope which attempts to handle some, possibly all, types of exceptions.
const Handler & getHandler(unsigned I) const
void setHandler(unsigned I, llvm::Constant *Type, llvm::BasicBlock *Block)
void setCatchAllHandler(unsigned I, llvm::BasicBlock *Block)
void clearHandlerBlocks()
unsigned getNumHandlers() const
An exceptions scope which filters exceptions thrown through it.
llvm::Value * getFilter(unsigned i) const
unsigned getNumFilters() const
Information for lazily generating a cleanup.
A non-stable pointer into the scope stack.
A saved depth on the scope stack.
class EHFilterScope * pushFilter(unsigned NumFilters)
Push an exceptions filter on the stack.
stable_iterator stable_begin() const
Create a stable reference to the top of the EH stack.
stable_iterator getInnermostEHScope() const
bool requiresLandingPad() const
bool empty() const
Determines whether the exception-scopes stack is empty.
iterator end() const
Returns an iterator pointing to the outermost EH scope.
void popFilter()
Pops an exceptions filter off the stack.
iterator begin() const
Returns an iterator pointing to the innermost EH scope.
void popCatch()
Pops a catch scope off the stack. This is private to CGException.cpp.
class EHCatchScope * pushCatch(unsigned NumHandlers)
Push a set of catch handlers on the stack.
iterator find(stable_iterator save) const
Turn a stable reference to a scope depth into a unstable pointer to the EH stack.
static stable_iterator stable_end()
Create a stable reference to the bottom of the EH stack.
void popTerminate()
Pops a terminate handler off the stack.
void pushTerminate()
Push a terminate handler on the stack.
A protected scope for zero-cost EH handling.
llvm::BasicBlock * getCachedLandingPad() const
EHScopeStack::stable_iterator getEnclosingEHScope() const
llvm::BasicBlock * getCachedEHDispatchBlock() const
void setCachedEHDispatchBlock(llvm::BasicBlock *block)
bool hasEHBranches() const
FunctionArgList - Type for representing both the decl and type of parameters to a function.
LValue - This represents an lvalue references.
Address getAddress() const
static RValue get(llvm::Value *V)
llvm::Value * getScalarVal() const
getScalarVal() - Return the Value* of this scalar value.
ReturnValueSlot - Contains the address where the return value of a function can be stored,...
Address performAddrSpaceCast(CodeGen::CodeGenFunction &CGF, Address Addr, LangAS SrcAddr, llvm::Type *DestTy, bool IsNonNull=false) const
ConstStmtVisitor - This class implements a simple visitor for Stmt subclasses.
A reference to a declared variable, function, enum, etc.
Decl - This represents one declaration (or definition), e.g.
SourceLocation getLocation() const
DiagnosticBuilder Report(SourceLocation Loc, unsigned DiagID)
Issue the message to the client.
This represents one expression.
SourceLocation getExprLoc() const LLVM_READONLY
getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...
Represents a function declaration or definition.
bool usesSEHTry() const
Indicates the function uses __try.
SourceRange getExceptionSpecSourceRange() const
Attempt to compute an informative source range covering the function exception specification,...
Represents a prototype with parameter type info, e.g.
ExceptionSpecificationType getExceptionSpecType() const
Get the kind of exception specification on this function.
QualType getExceptionType(unsigned i) const
Return the ith exception type, where 0 <= i < getNumExceptions().
unsigned getNumExceptions() const
Return the number of types in the exception specification.
CanThrowResult canThrow() const
Determine whether this function type has a non-throwing exception specification.
GlobalDecl - represents a global declaration.
const Decl * getDecl() const
static ImplicitParamDecl * Create(ASTContext &C, DeclContext *DC, SourceLocation IdLoc, IdentifierInfo *Id, QualType T, ImplicitParamKind ParamKind)
Create implicit parameter.
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
clang::ObjCRuntime ObjCRuntime
MangleContext - Context for tracking state which persists across multiple calls to the C++ name mangl...
virtual void mangleSEHFilterExpression(GlobalDecl EnclosingDecl, raw_ostream &Out)=0
virtual void mangleSEHFinallyBlock(GlobalDecl EnclosingDecl, raw_ostream &Out)=0
Represents Objective-C's @throw statement.
The basic abstraction for the target Objective-C runtime.
bool hasTerminate() const
Does this runtime provide an objc_terminate function?
bool isNeXTFamily() const
Is this runtime basically of the NeXT family of runtimes?
const VersionTuple & getVersion() const
@ MacOSX
'macosx' is the Apple-provided NeXT-derived runtime on Mac OS X platforms that use the non-fragile AB...
@ FragileMacOSX
'macosx-fragile' is the Apple-provided NeXT-derived runtime on Mac OS X platforms that use the fragil...
@ GNUstep
'gnustep' is the modern non-fragile GNUstep runtime.
@ ObjFW
'objfw' is the Objective-C runtime included in ObjFW
@ iOS
'ios' is the Apple-provided NeXT-derived runtime on iOS or the iOS simulator; it is always non-fragil...
@ GCC
'gcc' is the Objective-C runtime shipped with GCC, implementing a fragile Objective-C ABI
@ WatchOS
'watchos' is a variant of iOS for Apple's watchOS.
A (possibly-)qualified type.
Qualifiers getQualifiers() const
Retrieve the set of qualifiers applied to this type.
QualType getNonReferenceType() const
If Type is a reference type (e.g., const int&), returns the type that the reference refers to ("const...
QualType getUnqualifiedType() const
Retrieve the unqualified variant of the given type, removing as little sugar as possible.
The collection of all-type qualifiers we support.
CompoundStmt * getBlock() const
Expr * getFilterExpr() const
CompoundStmt * getBlock() const
Represents a __leave statement.
Smart pointer class that efficiently represents Objective-C method names.
Encodes a location in the source.
Stmt - This represents one statement.
SourceLocation getEndLoc() const LLVM_READONLY
SourceLocation getBeginLoc() const LLVM_READONLY
bool isMicrosoft() const
Is this ABI an MSVC-compatible ABI?
Exposes information about the current target.
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
TargetCXXABI getCXXABI() const
Get the C++ ABI currently in use.
bool isSignedIntegerType() const
Return true if this is an integer type that is signed, according to C99 6.2.5p4 [char,...
bool isPointerType() const
bool isVariablyModifiedType() const
Whether this type is a variably-modified type (C99 6.7.5).
bool isObjCObjectPointerType() const
const T * getAs() const
Member-template getAs<specific type>'.
Represents a variable declaration or definition.
bool isLocalVarDeclOrParm() const
Similar to isLocalVarDecl but also includes parameters.
@ NormalCleanup
Denotes a cleanup that should run when a scope is exited using normal control flow (falling off the e...
@ EHCleanup
Denotes a cleanup that should run when a scope is exited using exceptional control flow (a throw stat...
bool Load(InterpState &S, CodePtr OpPC)
The JSON file list parser is used to communicate input to InstallAPI.
LangAS
Defines the address space values used by the address space qualifier of QualType.
const FunctionProtoType * T
@ Other
Other implicit parameter.
ExceptionSpecificationType
The various types of exception specifications that exist in C++11.
@ EST_Dynamic
throw(T1, T2)
The MS C++ ABI needs a pointer to RTTI data plus some flags to describe the type of a catch handler,...
A jump destination is an abstract label, branching to which may require a jump out through normal cle...
llvm::BasicBlock * getBlock() const
llvm::PointerType * VoidPtrTy
CharUnits getIntAlign() const
llvm::IntegerType * Int8Ty
i8, i16, i32, and i64
llvm::IntegerType * Int32Ty
llvm::IntegerType * IntTy
int
llvm::PointerType * Int8PtrTy
CharUnits getPointerAlign() const
llvm::PointerType * AllocaInt8PtrTy
CatchTypeInfo Type
A type info value, or null (C++ null, not an LLVM null pointer) for a catch-all.
llvm::BasicBlock * Block
The catch handler for this type.
The exceptions personality for a function.
static const EHPersonality & get(CodeGenModule &CGM, const FunctionDecl *FD)
static const EHPersonality XL_CPlusPlus
static const EHPersonality GNU_ObjC_SJLJ
bool isWasmPersonality() const
static const EHPersonality ZOS_CPlusPlus
static const EHPersonality GNUstep_ObjC
static const EHPersonality MSVC_CxxFrameHandler3
bool usesFuncletPads() const
Does this personality use landingpads or the family of pad instructions designed to form funclets?
static const EHPersonality MSVC_C_specific_handler
static const EHPersonality GNU_CPlusPlus_SEH
static const EHPersonality GNU_ObjC
static const EHPersonality GNU_CPlusPlus_SJLJ
static const EHPersonality GNU_C_SJLJ
static const EHPersonality GNU_C
static const EHPersonality NeXT_ObjC
const char * CatchallRethrowFn
static const EHPersonality GNU_CPlusPlus
static const EHPersonality GNU_ObjCXX
static const EHPersonality GNU_C_SEH
static const EHPersonality MSVC_except_handler
static const EHPersonality GNU_ObjC_SEH
const char * PersonalityFn
static const EHPersonality GNU_Wasm_CPlusPlus