int CurrentBaseState;
int NextState;
- SmallVector<ActionHandler *, 4> HandlerStack;
+ SmallVector<std::unique_ptr<ActionHandler>, 4> HandlerStack;
SmallPtrSet<const Function *, 4> VisitedHandlers;
int currentEHNumber() const {
void createUnwindMapEntry(int ToState, ActionHandler *AH);
void createTryBlockMapEntry(int TryLow, int TryHigh,
ArrayRef<CatchHandler *> Handlers);
- void processCallSite(ArrayRef<ActionHandler *> Actions, ImmutableCallSite CS);
+ void processCallSite(MutableArrayRef<std::unique_ptr<ActionHandler>> Actions,
+ ImmutableCallSite CS);
void calculateStateNumbers(const Function &F);
};
}
// Parse the llvm.eh.actions call we found.
MachineBasicBlock *LPadMBB = MBBMap[LP->getParent()];
- SmallVector<ActionHandler *, 4> Actions;
+ SmallVector<std::unique_ptr<ActionHandler>, 4> Actions;
parseEHActions(ActionsCall, Actions);
// Iterate EH actions from most to least precedence, which means
// iterating in reverse.
for (auto I = Actions.rbegin(), E = Actions.rend(); I != E; ++I) {
- ActionHandler *Action = *I;
+ ActionHandler *Action = I->get();
if (auto *CH = dyn_cast<CatchHandler>(Action)) {
const auto *Filter =
dyn_cast<Function>(CH->getSelector()->stripPointerCasts());
MMI.addSEHCleanupHandler(LPadMBB, Fini);
}
}
- DeleteContainerPointers(Actions);
}
}
#endif
}
-void WinEHNumbering::processCallSite(ArrayRef<ActionHandler *> Actions,
- ImmutableCallSite CS) {
+void WinEHNumbering::processCallSite(
+ MutableArrayRef<std::unique_ptr<ActionHandler>> Actions,
+ ImmutableCallSite CS) {
DEBUG(dbgs() << "processCallSite (EH state = " << currentEHNumber()
<< ") for: ");
print_name(CS ? CS.getCalledValue() : nullptr);
if (HandlerStack[FirstMismatch]->getHandlerBlockOrFunc() !=
Actions[FirstMismatch]->getHandlerBlockOrFunc())
break;
- // Delete any actions that are already represented on the handler stack.
- delete Actions[FirstMismatch];
}
// Don't recurse while we are looping over the handler stack. Instead, defer
// the numbering of the catch handlers until we are done popping.
SmallVector<CatchHandler *, 4> PoppedCatches;
for (int I = HandlerStack.size() - 1; I >= FirstMismatch; --I) {
- if (auto *CH = dyn_cast<CatchHandler>(HandlerStack.back())) {
- PoppedCatches.push_back(CH);
- } else {
- // Delete cleanup handlers
- delete HandlerStack.back();
- }
- HandlerStack.pop_back();
+ std::unique_ptr<ActionHandler> Handler = HandlerStack.pop_back_val();
+ if (isa<CatchHandler>(Handler.get()))
+ PoppedCatches.push_back(cast<CatchHandler>(Handler.release()));
}
int TryHigh = NextState - 1;
if (HandlerStack[FirstMismatch]->getHandlerBlockOrFunc() !=
Actions[FirstMismatch]->getHandlerBlockOrFunc())
break;
- delete Actions[FirstMismatch];
}
}
bool LastActionWasCatch = false;
for (size_t I = FirstMismatch; I != Actions.size(); ++I) {
// We can reuse eh states when pushing two catches for the same invoke.
- bool CurrActionIsCatch = isa<CatchHandler>(Actions[I]);
+ bool CurrActionIsCatch = isa<CatchHandler>(Actions[I].get());
// FIXME: Reenable this optimization!
if (CurrActionIsCatch && LastActionWasCatch && false) {
DEBUG(dbgs() << "setEHState for handler to " << currentEHNumber()
DEBUG(dbgs() << "createUnwindMapEntry(" << currentEHNumber() << ", ");
print_name(Actions[I]->getHandlerBlockOrFunc());
DEBUG(dbgs() << ")\n");
- createUnwindMapEntry(currentEHNumber(), Actions[I]);
+ createUnwindMapEntry(currentEHNumber(), Actions[I].get());
DEBUG(dbgs() << "setEHState for handler to " << NextState << "\n");
Actions[I]->setEHState(NextState);
NextState++;
}
- HandlerStack.push_back(Actions[I]);
+ HandlerStack.push_back(std::move(Actions[I]));
LastActionWasCatch = CurrActionIsCatch;
}
}
DEBUG(dbgs() << "Calculating state numbers for: " << F.getName() << '\n');
- SmallVector<ActionHandler *, 4> ActionList;
+ SmallVector<std::unique_ptr<ActionHandler>, 4> ActionList;
for (const BasicBlock &BB : F) {
for (const Instruction &I : BB) {
const auto *CI = dyn_cast<CallInst>(&I);
// Populate the indirectbr instructions' target lists if we deferred
// doing so above.
SetVector<BasicBlock*> CheckedTargets;
+ SmallVector<std::unique_ptr<ActionHandler>, 4> ActionList;
for (auto &LPadImplPair : LPadImpls) {
IntrinsicInst *Recover = cast<IntrinsicInst>(LPadImplPair.first);
IndirectBrInst *Branch = LPadImplPair.second;
// Get a list of handlers called by
- SmallVector<ActionHandler *, 4> ActionList;
parseEHActions(Recover, ActionList);
// Add an indirect branch listing possible successors of the catch handlers.
SetVector<BasicBlock *> ReturnTargets;
- for (ActionHandler *Action : ActionList) {
- if (auto *CA = dyn_cast<CatchHandler>(Action)) {
+ for (const auto &Action : ActionList) {
+ if (auto *CA = dyn_cast<CatchHandler>(Action.get())) {
Function *Handler = cast<Function>(CA->getHandlerBlockOrFunc());
getPossibleReturnTargets(&F, Handler, ReturnTargets);
}
- delete Action;
}
ActionList.clear();
for (BasicBlock *Target : ReturnTargets) {
// parent function.
if (auto *LPI = BB.getLandingPadInst()) {
IntrinsicInst *Recover = cast<IntrinsicInst>(LPI->getNextNode());
- SmallVector<ActionHandler *, 4> ActionList;
+ SmallVector<std::unique_ptr<ActionHandler>, 4> ActionList;
parseEHActions(Recover, ActionList);
- for (auto *Action : ActionList) {
- if (auto *CH = dyn_cast<CatchHandler>(Action)) {
+ for (const auto &Action : ActionList) {
+ if (auto *CH = dyn_cast<CatchHandler>(Action.get())) {
Function *NestedF = cast<Function>(CH->getHandlerBlockOrFunc());
getPossibleReturnTargets(ParentF, NestedF, Targets);
}
// Remap the exception variables into the outlined function.
SmallVector<BlockAddress *, 4> ActionTargets;
- SmallVector<ActionHandler *, 4> ActionList;
+ SmallVector<std::unique_ptr<ActionHandler>, 4> ActionList;
parseEHActions(EHActions, ActionList);
- for (auto *Action : ActionList) {
- auto *Catch = dyn_cast<CatchHandler>(Action);
+ for (const auto &Action : ActionList) {
+ auto *Catch = dyn_cast<CatchHandler>(Action.get());
if (!Catch)
continue;
// The dyn_cast to function here selects C++ catch handlers and skips
ActionTargets.push_back(NewBA);
}
}
- DeleteContainerPointers(ActionList);
ActionList.clear();
OutlinedBB->getInstList().push_back(EHActions);
// This is a public function, declared in WinEHFuncInfo.h and is also
// referenced by WinEHNumbering in FunctionLoweringInfo.cpp.
-void llvm::parseEHActions(const IntrinsicInst *II,
- SmallVectorImpl<ActionHandler *> &Actions) {
+void llvm::parseEHActions(
+ const IntrinsicInst *II,
+ SmallVectorImpl<std::unique_ptr<ActionHandler>> &Actions) {
for (unsigned I = 0, E = II->getNumArgOperands(); I != E;) {
uint64_t ActionKind =
cast<ConstantInt>(II->getArgOperand(I))->getZExtValue();
int64_t EHObjIndexVal = EHObjIndex->getSExtValue();
Constant *Handler = cast<Constant>(II->getArgOperand(I + 3));
I += 4;
- auto *CH = new CatchHandler(/*BB=*/nullptr, Selector, /*NextBB=*/nullptr);
+ auto CH = make_unique<CatchHandler>(/*BB=*/nullptr, Selector,
+ /*NextBB=*/nullptr);
CH->setHandlerBlockOrFunc(Handler);
CH->setExceptionVarIndex(EHObjIndexVal);
- Actions.push_back(CH);
+ Actions.push_back(std::move(CH));
} else if (ActionKind == 0) {
Constant *Handler = cast<Constant>(II->getArgOperand(I + 1));
I += 2;
- auto *CH = new CleanupHandler(/*BB=*/nullptr);
+ auto CH = make_unique<CleanupHandler>(/*BB=*/nullptr);
CH->setHandlerBlockOrFunc(Handler);
- Actions.push_back(CH);
+ Actions.push_back(std::move(CH));
} else {
llvm_unreachable("Expected either a catch or cleanup handler!");
}