Path: blob/main/contrib/llvm-project/llvm/lib/Analysis/DomTreeUpdater.cpp
35233 views
//===- DomTreeUpdater.cpp - DomTree/Post DomTree Updater --------*- C++ -*-===//1//2// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.3// See https://llvm.org/LICENSE.txt for license information.4// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception5//6//===----------------------------------------------------------------------===//7//8// This file implements the DomTreeUpdater class, which provides a uniform way9// to update dominator tree related data structures.10//11//===----------------------------------------------------------------------===//1213#include "llvm/Analysis/DomTreeUpdater.h"14#include "llvm/ADT/SmallSet.h"15#include "llvm/Analysis/GenericDomTreeUpdaterImpl.h"16#include "llvm/Analysis/PostDominators.h"17#include "llvm/IR/Constants.h"18#include "llvm/IR/Instructions.h"19#include "llvm/Support/GenericDomTree.h"20#include <algorithm>21#include <functional>22#include <utility>2324namespace llvm {2526template class GenericDomTreeUpdater<DomTreeUpdater, DominatorTree,27PostDominatorTree>;2829template void30GenericDomTreeUpdater<DomTreeUpdater, DominatorTree,31PostDominatorTree>::recalculate(Function &F);3233bool DomTreeUpdater::forceFlushDeletedBB() {34if (DeletedBBs.empty())35return false;3637for (auto *BB : DeletedBBs) {38// After calling deleteBB or callbackDeleteBB under Lazy UpdateStrategy,39// validateDeleteBB() removes all instructions of DelBB and adds an40// UnreachableInst as its terminator. So we check whether the BasicBlock to41// delete only has an UnreachableInst inside.42assert(BB->size() == 1 && isa<UnreachableInst>(BB->getTerminator()) &&43"DelBB has been modified while awaiting deletion.");44BB->removeFromParent();45eraseDelBBNode(BB);46delete BB;47}48DeletedBBs.clear();49Callbacks.clear();50return true;51}5253// The DT and PDT require the nodes related to updates54// are not deleted when update functions are called.55// So BasicBlock deletions must be pended when the56// UpdateStrategy is Lazy. When the UpdateStrategy is57// Eager, the BasicBlock will be deleted immediately.58void DomTreeUpdater::deleteBB(BasicBlock *DelBB) {59validateDeleteBB(DelBB);60if (Strategy == UpdateStrategy::Lazy) {61DeletedBBs.insert(DelBB);62return;63}6465DelBB->removeFromParent();66eraseDelBBNode(DelBB);67delete DelBB;68}6970void DomTreeUpdater::callbackDeleteBB(71BasicBlock *DelBB, std::function<void(BasicBlock *)> Callback) {72validateDeleteBB(DelBB);73if (Strategy == UpdateStrategy::Lazy) {74Callbacks.push_back(CallBackOnDeletion(DelBB, Callback));75DeletedBBs.insert(DelBB);76return;77}7879DelBB->removeFromParent();80eraseDelBBNode(DelBB);81Callback(DelBB);82delete DelBB;83}8485void DomTreeUpdater::validateDeleteBB(BasicBlock *DelBB) {86assert(DelBB && "Invalid push_back of nullptr DelBB.");87assert(pred_empty(DelBB) && "DelBB has one or more predecessors.");88// DelBB is unreachable and all its instructions are dead.89while (!DelBB->empty()) {90Instruction &I = DelBB->back();91// Replace used instructions with an arbitrary value (poison).92if (!I.use_empty())93I.replaceAllUsesWith(PoisonValue::get(I.getType()));94DelBB->back().eraseFromParent();95}96// Make sure DelBB has a valid terminator instruction. As long as DelBB is a97// Child of Function F it must contain valid IR.98new UnreachableInst(DelBB->getContext(), DelBB);99}100101LLVM_DUMP_METHOD102void DomTreeUpdater::dump() const {103Base::dump();104#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)105raw_ostream &OS = dbgs();106OS << "Pending Callbacks:\n";107int Index = 0;108for (const auto &BB : Callbacks) {109OS << " " << Index << " : ";110++Index;111if (BB->hasName())112OS << BB->getName() << "(";113else114OS << "(no_name)(";115OS << BB << ")\n";116}117#endif118}119120} // namespace llvm121122123