22 #include "llvm/Support/SaveAndRestore.h"
24 using namespace clang;
25 using namespace CodeGen;
42 return saved_type(V, ScalarLiteral);
48 return saved_type(addr.
getPointer(), ScalarAddress);
54 llvm::StructType::get(V.first->getType(), V.second->getType(),
63 return saved_type(addr.
getPointer(), ComplexAddress);
69 return saved_type(V.getPointer(), AggregateLiteral,
70 V.getAlignment().getQuantity());
75 return saved_type(addr.getPointer(), AggregateAddress,
76 V.getAlignment().getQuantity());
84 auto alignment = cast<llvm::AllocaInst>(value)->getAlignment();
92 case AggregateLiteral:
94 case AggregateAddress: {
98 case ComplexAddress: {
110 llvm_unreachable(
"bad saved r-value kind");
114 char *EHScopeStack::allocate(
size_t Size) {
116 if (!StartOfBuffer) {
117 unsigned Capacity = 1024;
118 while (Capacity < Size) Capacity *= 2;
119 StartOfBuffer =
new char[Capacity];
120 StartOfData = EndOfBuffer = StartOfBuffer + Capacity;
121 }
else if (static_cast<size_t>(StartOfData - StartOfBuffer) < Size) {
122 unsigned CurrentCapacity = EndOfBuffer - StartOfBuffer;
123 unsigned UsedCapacity = CurrentCapacity - (StartOfData - StartOfBuffer);
125 unsigned NewCapacity = CurrentCapacity;
128 }
while (NewCapacity < UsedCapacity + Size);
130 char *NewStartOfBuffer =
new char[NewCapacity];
131 char *NewEndOfBuffer = NewStartOfBuffer + NewCapacity;
132 char *NewStartOfData = NewEndOfBuffer - UsedCapacity;
133 memcpy(NewStartOfData, StartOfData, UsedCapacity);
134 delete [] StartOfBuffer;
135 StartOfBuffer = NewStartOfBuffer;
136 EndOfBuffer = NewEndOfBuffer;
137 StartOfData = NewStartOfData;
140 assert(StartOfBuffer + Size <= StartOfData);
145 void EHScopeStack::deallocate(
size_t Size) {
153 if (!cleanup || !cleanup->isLifetimeMarker())
165 if (cleanup.isActive())
return si;
166 si = cleanup.getEnclosingNormalCleanup();
183 InnermostNormalCleanup,
190 return Scope->getCleanupBuffer();
194 assert(!
empty() &&
"popping exception stack when not empty");
196 assert(isa<EHCleanupScope>(*
begin()));
198 InnermostNormalCleanup = Cleanup.getEnclosingNormalCleanup();
199 InnermostEHScope = Cleanup.getEnclosingEHScope();
200 deallocate(Cleanup.getAllocatedSize());
206 if (!BranchFixups.empty()) {
210 BranchFixups.clear();
227 assert(!
empty() &&
"popping exception stack when not empty");
238 new (buffer)
EHCatchScope(numHandlers, InnermostEHScope);
260 unsigned MinSize = cast<EHCleanupScope>(*it).getFixupDepth();
261 assert(BranchFixups.size() >= MinSize &&
"fixup stack out of order");
263 while (BranchFixups.size() > MinSize &&
264 BranchFixups.back().Destination ==
nullptr)
265 BranchFixups.pop_back();
282 assert(!cleanup.hasActiveFlag() &&
"cleanup already has active flag?");
283 cleanup.setActiveFlag(active);
285 if (cleanup.isNormalCleanup()) cleanup.setTestFlagInNormalCleanup();
286 if (cleanup.isEHCleanup()) cleanup.setTestFlagInEHCleanup();
289 void EHScopeStack::Cleanup::anchor() {}
292 llvm::Instruction *beforeInst) {
293 auto store =
new llvm::StoreInst(value, addr.
getPointer(), beforeInst);
298 llvm::Instruction *beforeInst) {
299 auto load =
new llvm::LoadInst(addr.
getPointer(), name, beforeInst);
308 llvm::SwitchInst *Switch,
309 llvm::BasicBlock *CleanupEntry) {
310 llvm::SmallPtrSet<llvm::BasicBlock*, 4> CasesAdded;
346 llvm::BasicBlock *Block) {
349 llvm::TerminatorInst *Term = Block->getTerminator();
350 assert(Term &&
"can't transition block without terminator");
352 if (llvm::BranchInst *Br = dyn_cast<llvm::BranchInst>(Term)) {
353 assert(Br->isUnconditional());
355 "cleanup.dest", Term);
356 llvm::SwitchInst *Switch =
358 Br->eraseFromParent();
361 return cast<llvm::SwitchInst>(Term);
366 assert(Block &&
"resolving a null target block");
367 if (!EHStack.getNumBranchFixups())
return;
369 assert(EHStack.hasNormalCleanups() &&
370 "branch fixups exist with no normal cleanups on stack");
372 llvm::SmallPtrSet<llvm::BasicBlock*, 4> ModifiedOptimisticBlocks;
373 bool ResolvedAny =
false;
375 for (
unsigned I = 0,
E = EHStack.getNumBranchFixups();
I !=
E; ++
I) {
390 if (!ModifiedOptimisticBlocks.insert(BranchBB).second)
400 EHStack.popNullFixups();
407 while (EHStack.stable_begin() != Old) {
413 bool FallThroughIsBranchThrough =
416 PopCleanupBlock(FallThroughIsBranchThrough);
424 size_t OldLifetimeExtendedSize) {
425 PopCleanupBlocks(Old);
428 for (
size_t I = OldLifetimeExtendedSize,
429 E = LifetimeExtendedCleanupStack.size();
I !=
E; ) {
431 assert((
I % llvm::alignOf<LifetimeExtendedCleanupHeader>() == 0) &&
432 "misaligned cleanup stack entry");
436 LifetimeExtendedCleanupStack[
I]);
439 EHStack.pushCopyOfCleanup(Header.
getKind(),
440 &LifetimeExtendedCleanupStack[
I],
444 LifetimeExtendedCleanupStack.resize(OldLifetimeExtendedSize);
449 assert(Scope.isNormalCleanup());
450 llvm::BasicBlock *Entry = Scope.getNormalBlock();
453 Scope.setNormalBlock(Entry);
464 llvm::BasicBlock *Entry) {
465 llvm::BasicBlock *Pred = Entry->getSinglePredecessor();
466 if (!Pred)
return Entry;
468 llvm::BranchInst *Br = dyn_cast<llvm::BranchInst>(Pred->getTerminator());
469 if (!Br || Br->isConditional())
return Entry;
470 assert(Br->getSuccessor(0) == Entry);
475 bool WasInsertBlock = CGF.
Builder.GetInsertBlock() == Entry;
476 assert(!WasInsertBlock || CGF.
Builder.GetInsertPoint() == Entry->end());
479 Br->eraseFromParent();
483 Entry->replaceAllUsesWith(Pred);
486 Pred->getInstList().splice(Pred->end(), Entry->getInstList());
489 Entry->eraseFromParent();
492 CGF.
Builder.SetInsertPoint(Pred);
503 llvm::BasicBlock *ContBB =
nullptr;
509 CGF.
Builder.CreateCondBr(IsActive, CleanupBB, ContBB);
514 Fn->
Emit(CGF, flags);
515 assert(CGF.
HaveInsertPoint() &&
"cleanup ended with no insertion point?");
523 llvm::BasicBlock *From,
524 llvm::BasicBlock *To) {
527 llvm::TerminatorInst *Term = Exit->getTerminator();
529 if (llvm::BranchInst *Br = dyn_cast<llvm::BranchInst>(Term)) {
530 assert(Br->isUnconditional() && Br->getSuccessor(0) == From);
531 Br->setSuccessor(0, To);
533 llvm::SwitchInst *Switch = cast<llvm::SwitchInst>(Term);
534 for (
unsigned I = 0,
E = Switch->getNumSuccessors();
I !=
E; ++
I)
535 if (Switch->getSuccessor(
I) == From)
536 Switch->setSuccessor(
I, To);
548 llvm::BasicBlock *entry = scope.getNormalBlock();
553 for (llvm::BasicBlock::use_iterator
554 i = entry->use_begin(), e = entry->use_end(); i != e; ) {
558 use.set(unreachableBB);
561 llvm::SwitchInst *si = cast<llvm::SwitchInst>(use.getUser());
562 if (si->getNumCases() == 1 && si->getDefaultDest() == unreachableBB) {
567 llvm::LoadInst *condition = cast<llvm::LoadInst>(si->getCondition());
570 si->eraseFromParent();
574 assert(condition->use_empty());
575 condition->eraseFromParent();
579 assert(entry->use_empty());
587 assert(!EHStack.empty() &&
"cleanup stack is empty!");
588 assert(isa<EHCleanupScope>(*EHStack.begin()) &&
"top not a cleanup!");
590 assert(Scope.getFixupDepth() <= EHStack.getNumBranchFixups());
593 bool IsActive = Scope.isActive();
595 Scope.shouldTestFlagInNormalCleanup() ? Scope.getActiveFlag()
598 Scope.shouldTestFlagInEHCleanup() ? Scope.getActiveFlag()
603 llvm::BasicBlock *EHEntry = Scope.getCachedEHDispatchBlock();
604 assert(Scope.hasEHBranches() == (EHEntry !=
nullptr));
605 bool RequiresEHCleanup = (EHEntry !=
nullptr);
611 unsigned FixupDepth = Scope.getFixupDepth();
612 bool HasFixups = EHStack.getNumBranchFixups() != FixupDepth;
615 bool HasExistingBranches = Scope.hasBranches();
618 llvm::BasicBlock *FallthroughSource =
Builder.GetInsertBlock();
619 bool HasFallthrough = (FallthroughSource !=
nullptr && IsActive);
625 bool HasPrebranchedFallthrough =
626 (FallthroughSource && FallthroughSource->getTerminator());
631 assert(!Scope.isNormalCleanup() || !HasPrebranchedFallthrough ||
632 (Scope.getNormalBlock() &&
633 FallthroughSource->getTerminator()->getSuccessor(0)
634 == Scope.getNormalBlock()));
636 bool RequiresNormalCleanup =
false;
637 if (Scope.isNormalCleanup() &&
638 (HasFixups || HasExistingBranches || HasFallthrough)) {
639 RequiresNormalCleanup =
true;
644 if (Scope.isNormalCleanup() && HasPrebranchedFallthrough && !IsActive) {
645 llvm::BasicBlock *prebranchDest;
650 if (FallthroughIsBranchThrough) {
651 EHScope &enclosing = *EHStack.find(Scope.getEnclosingNormalCleanup());
659 prebranchDest = createBasicBlock(
"forwarded-prebranch");
660 EmitBlock(prebranchDest);
663 llvm::BasicBlock *normalEntry = Scope.getNormalBlock();
664 assert(normalEntry && !normalEntry->use_empty());
667 normalEntry, prebranchDest);
671 if (!RequiresNormalCleanup && !RequiresEHCleanup) {
673 EHStack.popCleanup();
674 assert(EHStack.getNumBranchFixups() == 0 ||
675 EHStack.hasNormalCleanups());
684 auto *CleanupSource =
reinterpret_cast<char *
>(Scope.getCleanupBuffer());
685 llvm::AlignedCharArray<EHScopeStack::ScopeStackAlignment, 8 * sizeof(void *)> CleanupBufferStack;
686 std::unique_ptr<char[]> CleanupBufferHeap;
687 size_t CleanupSize = Scope.getCleanupSize();
690 if (CleanupSize <=
sizeof(CleanupBufferStack)) {
691 memcpy(CleanupBufferStack.buffer, CleanupSource, CleanupSize);
694 CleanupBufferHeap.reset(
new char[CleanupSize]);
695 memcpy(CleanupBufferHeap.get(), CleanupSource, CleanupSize);
700 if (Scope.isNormalCleanup())
702 if (Scope.isEHCleanup())
705 if (!RequiresNormalCleanup) {
707 EHStack.popCleanup();
711 if (HasFallthrough && !HasPrebranchedFallthrough &&
712 !HasFixups && !HasExistingBranches) {
715 EHStack.popCleanup();
717 EmitCleanup(*
this, Fn, cleanupFlags, NormalActiveFlag);
727 CGBuilderTy::InsertPoint savedInactiveFallthroughIP;
731 if (HasFallthrough) {
732 if (!HasPrebranchedFallthrough)
733 Builder.CreateStore(
Builder.getInt32(0), getNormalCleanupDestSlot());
737 }
else if (FallthroughSource) {
738 assert(!IsActive &&
"source without fallthrough for active cleanup");
739 savedInactiveFallthroughIP =
Builder.saveAndClearIP();
745 EmitBlock(NormalEntry);
750 bool HasEnclosingCleanups =
751 (Scope.getEnclosingNormalCleanup() != EHStack.stable_end());
758 llvm::BasicBlock *BranchThroughDest =
nullptr;
759 if (Scope.hasBranchThroughs() ||
760 (FallthroughSource && FallthroughIsBranchThrough) ||
761 (HasFixups && HasEnclosingCleanups)) {
762 assert(HasEnclosingCleanups);
763 EHScope &
S = *EHStack.find(Scope.getEnclosingNormalCleanup());
767 llvm::BasicBlock *FallthroughDest =
nullptr;
772 if (!Scope.hasBranchThroughs() && !HasFixups && !HasFallthrough &&
773 Scope.getNumBranchAfters() == 1) {
774 assert(!BranchThroughDest || !IsActive);
777 llvm::Instruction *NormalCleanupDestSlot =
778 cast<llvm::Instruction>(getNormalCleanupDestSlot().getPointer());
779 if (NormalCleanupDestSlot->hasOneUse()) {
780 NormalCleanupDestSlot->user_back()->eraseFromParent();
781 NormalCleanupDestSlot->eraseFromParent();
782 NormalCleanupDest =
nullptr;
785 llvm::BasicBlock *BranchAfter = Scope.getBranchAfterBlock(0);
793 }
else if (Scope.getNumBranchAfters() ||
794 (HasFallthrough && !FallthroughIsBranchThrough) ||
795 (HasFixups && !HasEnclosingCleanups)) {
797 llvm::BasicBlock *Default =
798 (BranchThroughDest ? BranchThroughDest : getUnreachableBlock());
801 const unsigned SwitchCapacity = 10;
803 llvm::LoadInst *Load =
806 llvm::SwitchInst *Switch =
809 InstsToAppend.push_back(Load);
810 InstsToAppend.push_back(Switch);
813 if (FallthroughSource && !FallthroughIsBranchThrough) {
814 FallthroughDest = createBasicBlock(
"cleanup.cont");
816 Switch->addCase(
Builder.getInt32(0), FallthroughDest);
819 for (
unsigned I = 0,
E = Scope.getNumBranchAfters();
I !=
E; ++
I) {
820 Switch->addCase(Scope.getBranchAfterIndex(
I),
821 Scope.getBranchAfterBlock(
I));
826 if (HasFixups && !HasEnclosingCleanups)
830 assert(BranchThroughDest);
835 EHStack.popCleanup();
836 assert(EHStack.hasNormalCleanups() == HasEnclosingCleanups);
838 EmitCleanup(*
this, Fn, cleanupFlags, NormalActiveFlag);
841 llvm::BasicBlock *NormalExit =
Builder.GetInsertBlock();
842 for (
unsigned I = 0,
E = InstsToAppend.size();
I !=
E; ++
I)
843 NormalExit->getInstList().push_back(InstsToAppend[
I]);
846 for (
unsigned I = FixupDepth,
E = EHStack.getNumBranchFixups();
852 getNormalCleanupDestSlot(),
863 if (!HasFallthrough && FallthroughSource) {
868 Builder.restoreIP(savedInactiveFallthroughIP);
873 }
else if (HasFallthrough && FallthroughDest) {
874 assert(!FallthroughIsBranchThrough);
875 EmitBlock(FallthroughDest);
879 }
else if (HasFallthrough) {
891 llvm::BasicBlock *NewNormalEntry =
896 if (NewNormalEntry != NormalEntry && NormalEntry == NormalExit)
897 for (
unsigned I = FixupDepth, E = EHStack.getNumBranchFixups();
899 EHStack.getBranchFixup(I).OptimisticBranchBlock = NewNormalEntry;
903 assert(EHStack.hasNormalCleanups() || EHStack.getNumBranchFixups() == 0);
906 if (RequiresEHCleanup) {
907 CGBuilderTy::InsertPoint SavedIP =
Builder.saveAndClearIP();
911 llvm::BasicBlock *NextAction = getEHDispatchBlock(EHParent);
916 bool PushedTerminate =
false;
919 llvm::CleanupPadInst *CPI =
nullptr;
921 EHStack.pushTerminate();
922 PushedTerminate =
true;
926 ParentPad = llvm::ConstantTokenNone::get(CGM.getLLVMContext());
927 CurrentFuncletPad = CPI =
Builder.CreateCleanupPad(ParentPad);
932 if (EHActiveFlag.
isValid() || IsActive) {
934 EmitCleanup(*
this, Fn, cleanupFlags, EHActiveFlag);
938 Builder.CreateCleanupRet(CPI, NextAction);
944 EHStack.popTerminate();
957 &&
"stale jump destination");
961 EHStack.getInnermostActiveNormalCleanup();
966 if (TopCleanup == EHStack.stable_end() ||
982 &&
"stale jump destination");
984 if (!HaveInsertPoint())
992 TopCleanup = EHStack.getInnermostActiveNormalCleanup();
997 if (TopCleanup == EHStack.stable_end() ||
1012 Builder.ClearInsertionPoint();
1025 cast<EHCleanupScope>(*EHStack.find(TopCleanup));
1035 assert(Scope.isNormalCleanup());
1036 I = Scope.getEnclosingNormalCleanup();
1041 Scope.addBranchAfter(Index, Dest.
getBlock());
1048 if (!Scope.addBranchThrough(Dest.
getBlock()))
1053 Builder.ClearInsertionPoint();
1068 if (S.getNormalBlock())
return true;
1069 I = S.getEnclosingNormalCleanup();
1087 if (scope.hasEHBranches())
1090 i = scope.getEnclosingEHScope();
1109 llvm::Instruction *dominatingIP) {
1115 bool isActivatedInConditional =
1118 bool needFlag =
false;
1123 if (Scope.isNormalCleanup() &&
1125 Scope.setTestFlagInNormalCleanup();
1130 if (Scope.isEHCleanup() &&
1132 Scope.setTestFlagInEHCleanup();
1137 if (!needFlag)
return;
1139 Address var = Scope.getActiveFlag();
1142 "cleanup.isactive");
1143 Scope.setActiveFlag(var);
1145 assert(dominatingIP &&
"no existing variable and no dominating IP!");
1165 llvm::Instruction *dominatingIP) {
1166 assert(C != EHStack.stable_end() &&
"activating bottom of stack?");
1168 assert(!Scope.isActive() &&
"double activation");
1172 Scope.setActive(
true);
1177 llvm::Instruction *dominatingIP) {
1178 assert(C != EHStack.stable_end() &&
"deactivating bottom of stack?");
1180 assert(Scope.isActive() &&
"double deactivation");
1183 if (C == EHStack.stable_begin()) {
1186 CGBuilderTy::InsertPoint SavedIP =
Builder.saveAndClearIP();
1195 Scope.setActive(
false);
1199 if (!NormalCleanupDest)
1201 CreateTempAlloca(
Builder.getInt32Ty(),
"cleanup.dest.slot");
void pushTerminate()
Push a terminate handler on the stack.
static llvm::BasicBlock * CreateNormalEntry(CodeGenFunction &CGF, EHCleanupScope &Scope)
void ActivateCleanupBlock(EHScopeStack::stable_iterator Cleanup, llvm::Instruction *DominatingIP)
ActivateCleanupBlock - Activates an initially-inactive cleanup.
A (possibly-)qualified type.
void setIsEHCleanupKind()
static llvm::LoadInst * createLoadInstBefore(Address addr, const Twine &name, llvm::Instruction *beforeInst)
static void destroyOptimisticNormalEntry(CodeGenFunction &CGF, EHCleanupScope &scope)
We don't need a normal entry block for the given cleanup.
bool isInConditionalBranch() const
isInConditionalBranch - Return true if we're currently emitting one branch or the other of a conditio...
std::pair< llvm::Value *, llvm::Value * > getComplexVal() const
getComplexVal - Return the real/imag components of this complex value.
static stable_iterator stable_end()
Create a stable reference to the bottom of the EH stack.
llvm::AllocaInst * CreateTempAlloca(llvm::Type *Ty, const Twine &Name="tmp")
CreateTempAlloca - This creates a alloca and inserts it into the entry block.
QuantityType getQuantity() const
getQuantity - Get the raw integer representation of this quantity.
static llvm::SwitchInst * TransitionToCleanupSwitch(CodeGenFunction &CGF, llvm::BasicBlock *Block)
Transitions the terminator of the given exit-block of a cleanup to be a cleanup switch.
const llvm::DataLayout & getDataLayout() const
std::unique_ptr< llvm::MemoryBuffer > Buffer
static bool needsSaving(llvm::Value *value)
Answer whether the given value needs extra work to be saved.
static void EmitCleanup(CodeGenFunction &CGF, EHScopeStack::Cleanup *Fn, EHScopeStack::Cleanup::Flags flags, Address ActiveFlag)
A protected scope for zero-cost EH handling.
A scope which attempts to handle some, possibly all, types of exceptions.
A jump destination is an abstract label, branching to which may require a jump out through normal cle...
An exceptions scope which calls std::terminate if any exception reaches it.
stable_iterator stabilize(iterator it) const
Translates an iterator into a stable_iterator.
CodeGenFunction - This class organizes the per-function state that is used while generating LLVM code...
Denotes a cleanup that should run when a scope is exited using exceptional control flow (a throw stat...
bool hasEHBranches() const
static const EHPersonality & get(CodeGenModule &CGM, const FunctionDecl *FD)
A metaprogramming class for ensuring that a value will dominate an arbitrary position in a function...
class EHCatchScope * pushCatch(unsigned NumHandlers)
Push a set of catch handlers on the stack.
iterator begin() const
Returns an iterator pointing to the innermost EH scope.
BranchFixup & getBranchFixup(unsigned I)
CharUnits - This is an opaque type for sizes expressed in character units.
bool isObviouslyBranchWithoutCleanups(JumpDest Dest) const
isObviouslyBranchWithoutCleanups - Return true if a branch to the specified destination obviously has...
Scope - A scope is a transient data structure that is used while parsing the program.
void initFullExprCleanup()
Set up the last cleaup that was pushed as a conditional full-expression cleanup.
A stack of scopes which respond to exceptions, including cleanups and catch blocks.
llvm::BasicBlock * createBasicBlock(const Twine &name="", llvm::Function *parent=nullptr, llvm::BasicBlock *before=nullptr)
createBasicBlock - Create an LLVM basic block.
Denotes a cleanup that should run when a scope is exited using normal control flow (falling off the e...
void popFilter()
Pops an exceptions filter off the stack.
detail::InMemoryDirectory::const_iterator I
static bool IsUsedAsEHCleanup(EHScopeStack &EHStack, EHScopeStack::stable_iterator cleanup)
static size_t getSizeForNumHandlers(unsigned N)
iterator find(stable_iterator save) const
Turn a stable reference to a scope depth into a unstable pointer to the EH stack. ...
static CharUnits One()
One - Construct a CharUnits quantity of one.
std::pair< llvm::Value *, llvm::Value * > ComplexPairTy
unsigned getNumBranchFixups() const
static void createStoreInstBefore(llvm::Value *value, Address addr, llvm::Instruction *beforeInst)
RValue - This trivial value class is used to represent the result of an expression that is evaluated...
static void ResolveAllBranchFixups(CodeGenFunction &CGF, llvm::SwitchInst *Switch, llvm::BasicBlock *CleanupEntry)
All the branch fixups on the EH stack have propagated out past the outermost normal cleanup; resolve ...
llvm::BranchInst * InitialBranch
The initial branch of the fixup.
Address CreateDefaultAlignTempAlloca(llvm::Type *Ty, const Twine &Name="tmp")
CreateDefaultAlignedTempAlloca - This creates an alloca with the default ABI alignment of the given L...
llvm::Value * getPointer() const
bool empty() const
Determines whether the exception-scopes stack is empty.
static size_t getSizeForCleanupSize(size_t Size)
Gets the size required for a lazy cleanup scope with the given cleanup-data requirements.
void clearFixups()
Clears the branch-fixups list.
llvm::AllocaInst * NormalCleanupDest
i32s containing the indexes of the cleanup destinations.
llvm::BasicBlock * getBlock() const
EHScopeStack::stable_iterator getScopeDepth() const
static CharUnits fromQuantity(QuantityType Quantity)
fromQuantity - Construct a CharUnits quantity from a raw integer type.
EHScopeStack::stable_iterator getEnclosingEHScope() const
stable_iterator stable_begin() const
Create a stable reference to the top of the EH stack.
llvm::AllocaInst * ActiveFlag
An optional i1 variable indicating whether this cleanup has been activated yet.
bool containsOnlyLifetimeMarkers(stable_iterator Old) const
void ResolveBranchFixups(llvm::BasicBlock *Target)
static OMPLinearClause * Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, OpenMPLinearClauseKind Modifier, SourceLocation ModifierLoc, SourceLocation ColonLoc, SourceLocation EndLoc, ArrayRef< Expr * > VL, ArrayRef< Expr * > PL, ArrayRef< Expr * > IL, Expr *Step, Expr *CalcStep)
Creates clause with a list of variables VL and a linear step Step.
unsigned getDestIndex() const
bool usesFuncletPads() const
Does this personality use landingpads or the family of pad instructions designed to form funclets...
EHCleanupScope(bool isNormal, bool isEH, bool isActive, unsigned cleanupSize, unsigned fixupDepth, EHScopeStack::stable_iterator enclosingNormal, EHScopeStack::stable_iterator enclosingEH)
llvm::BasicBlock * OptimisticBranchBlock
The block containing the terminator which needs to be modified into a switch if this fixup is resolve...
void popCleanup()
Pops a cleanup scope off the stack. This is private to CGCleanup.cpp.
The l-value was considered opaque, so the alignment was determined from a type.
bool HaveInsertPoint() const
HaveInsertPoint - True if an insertion point is defined.
llvm::BasicBlock * Destination
The ultimate destination of the branch.
CharUnits getPointerAlign() const
A saved depth on the scope stack.
Represents a C++ temporary.
llvm::BasicBlock * getUnreachableBlock()
void setBeforeOutermostConditional(llvm::Value *value, Address addr)
void DeactivateCleanupBlock(EHScopeStack::stable_iterator Cleanup, llvm::Instruction *DominatingIP)
DeactivateCleanupBlock - Deactivates the given cleanup block.
void EmitCXXTemporary(const CXXTemporary *Temporary, QualType TempType, Address Ptr)
Emits all the code to cause the given temporary to be cleaned up.
unsigned DestinationIndex
The destination index value.
void setIsNormalCleanupKind()
virtual void Emit(CodeGenFunction &CGF, Flags flags)=0
Emit the cleanup.
static size_t getSizeForNumFilters(unsigned numFilters)
static bool IsUsedAsNormalCleanup(EHScopeStack &EHStack, EHScopeStack::stable_iterator C)
static void ForwardPrebranchedFallthrough(llvm::BasicBlock *Exit, llvm::BasicBlock *From, llvm::BasicBlock *To)
CharUnits getAlignment() const
Return the alignment of this pointer.
class EHFilterScope * pushFilter(unsigned NumFilters)
Push an exceptions filter on the stack.
llvm::Value * getAggregatePointer() const
bool encloses(stable_iterator I) const
Returns true if this scope encloses I.
static RValue getComplex(llvm::Value *V1, llvm::Value *V2)
void popNullFixups()
Pops lazily-removed fixups from the end of the list.
llvm::Value * getScalarVal() const
getScalarVal() - Return the Value* of this scalar value.
Address CreateStructGEP(Address Addr, unsigned Index, CharUnits Offset, const llvm::Twine &Name="")
static llvm::BasicBlock * SimplifyCleanupEntry(CodeGenFunction &CGF, llvm::BasicBlock *Entry)
Attempts to reduce a cleanup's entry block to a fallthrough.
llvm::LoadInst * CreateLoad(Address Addr, const llvm::Twine &Name="")
detail::InMemoryDirectory::const_iterator E
llvm::StoreInst * CreateStore(llvm::Value *Val, Address Addr, bool IsVolatile=false)
Address getNormalCleanupDestSlot()
static void SetupCleanupBlockActivation(CodeGenFunction &CGF, EHScopeStack::stable_iterator C, ForActivation_t kind, llvm::Instruction *dominatingIP)
The given cleanup block is changing activation state.
void EmitBlock(llvm::BasicBlock *BB, bool IsFinished=false)
EmitBlock - Emit the given block.
llvm::BasicBlock * getNormalBlock() const
BoundNodesTreeBuilder *const Builder
stable_iterator getInnermostActiveNormalCleanup() const
void PopCleanupBlocks(EHScopeStack::stable_iterator OldCleanupStackSize)
Takes the old cleanup stack size and emits the cleanup blocks that have been added.
unsigned kind
All of the diagnostics that can be emitted by the frontend.
Address getAggregateAddress() const
getAggregateAddr() - Return the Value* of the address of the aggregate.
bool hasNormalCleanups() const
Determines whether there are any normal cleanups on the stack.
unsigned getNumFilters() const
stable_iterator getInnermostEHScope() const
bool strictlyEncloses(stable_iterator I) const
Returns true if this scope strictly encloses I: that is, if it encloses I and is not I...
stable_iterator getInnermostNormalCleanup() const
Returns the innermost normal cleanup on the stack, or stable_end() if there are no normal cleanups...
An exceptions scope which filters exceptions thrown through it.
static RValue get(llvm::Value *V)
void EmitBranchThroughCleanup(JumpDest Dest)
EmitBranchThroughCleanup - Emit a branch from the current insert block through the normal cleanup han...
static RValue getAggregate(Address addr, bool isVolatile=false)
Information for lazily generating a cleanup.
A non-stable pointer into the scope stack.
void PopCleanupBlock(bool FallThroughIsBranchThrough=false)
PopCleanupBlock - Will pop the cleanup entry on the stack and process all branch fixups.