1*da58b97aSjoerg //===- LiveRangeCalc.cpp - Calculate live ranges -------------------------===//
206f32e7eSjoerg //
306f32e7eSjoerg // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
406f32e7eSjoerg // See https://llvm.org/LICENSE.txt for license information.
506f32e7eSjoerg // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
606f32e7eSjoerg //
706f32e7eSjoerg //===----------------------------------------------------------------------===//
806f32e7eSjoerg //
906f32e7eSjoerg // Implementation of the LiveRangeCalc class.
1006f32e7eSjoerg //
1106f32e7eSjoerg //===----------------------------------------------------------------------===//
1206f32e7eSjoerg 
1306f32e7eSjoerg #include "llvm/CodeGen/LiveRangeCalc.h"
1406f32e7eSjoerg #include "llvm/ADT/BitVector.h"
1506f32e7eSjoerg #include "llvm/ADT/STLExtras.h"
1606f32e7eSjoerg #include "llvm/ADT/SetVector.h"
1706f32e7eSjoerg #include "llvm/ADT/SmallVector.h"
1806f32e7eSjoerg #include "llvm/CodeGen/LiveInterval.h"
1906f32e7eSjoerg #include "llvm/CodeGen/MachineBasicBlock.h"
2006f32e7eSjoerg #include "llvm/CodeGen/MachineDominators.h"
2106f32e7eSjoerg #include "llvm/CodeGen/MachineFunction.h"
2206f32e7eSjoerg #include "llvm/CodeGen/MachineInstr.h"
2306f32e7eSjoerg #include "llvm/CodeGen/MachineOperand.h"
2406f32e7eSjoerg #include "llvm/CodeGen/MachineRegisterInfo.h"
2506f32e7eSjoerg #include "llvm/CodeGen/SlotIndexes.h"
2606f32e7eSjoerg #include "llvm/CodeGen/TargetRegisterInfo.h"
2706f32e7eSjoerg #include "llvm/MC/LaneBitmask.h"
2806f32e7eSjoerg #include "llvm/Support/ErrorHandling.h"
2906f32e7eSjoerg #include "llvm/Support/raw_ostream.h"
3006f32e7eSjoerg #include <algorithm>
3106f32e7eSjoerg #include <cassert>
3206f32e7eSjoerg #include <iterator>
3306f32e7eSjoerg #include <tuple>
3406f32e7eSjoerg #include <utility>
3506f32e7eSjoerg 
3606f32e7eSjoerg using namespace llvm;
3706f32e7eSjoerg 
3806f32e7eSjoerg #define DEBUG_TYPE "regalloc"
3906f32e7eSjoerg 
4006f32e7eSjoerg // Reserve an address that indicates a value that is known to be "undef".
4106f32e7eSjoerg static VNInfo UndefVNI(0xbad, SlotIndex());
4206f32e7eSjoerg 
resetLiveOutMap()4306f32e7eSjoerg void LiveRangeCalc::resetLiveOutMap() {
4406f32e7eSjoerg   unsigned NumBlocks = MF->getNumBlockIDs();
4506f32e7eSjoerg   Seen.clear();
4606f32e7eSjoerg   Seen.resize(NumBlocks);
4706f32e7eSjoerg   EntryInfos.clear();
4806f32e7eSjoerg   Map.resize(NumBlocks);
4906f32e7eSjoerg }
5006f32e7eSjoerg 
reset(const MachineFunction * mf,SlotIndexes * SI,MachineDominatorTree * MDT,VNInfo::Allocator * VNIA)5106f32e7eSjoerg void LiveRangeCalc::reset(const MachineFunction *mf,
5206f32e7eSjoerg                           SlotIndexes *SI,
5306f32e7eSjoerg                           MachineDominatorTree *MDT,
5406f32e7eSjoerg                           VNInfo::Allocator *VNIA) {
5506f32e7eSjoerg   MF = mf;
5606f32e7eSjoerg   MRI = &MF->getRegInfo();
5706f32e7eSjoerg   Indexes = SI;
5806f32e7eSjoerg   DomTree = MDT;
5906f32e7eSjoerg   Alloc = VNIA;
6006f32e7eSjoerg   resetLiveOutMap();
6106f32e7eSjoerg   LiveIn.clear();
6206f32e7eSjoerg }
6306f32e7eSjoerg 
updateFromLiveIns()6406f32e7eSjoerg void LiveRangeCalc::updateFromLiveIns() {
6506f32e7eSjoerg   LiveRangeUpdater Updater;
6606f32e7eSjoerg   for (const LiveInBlock &I : LiveIn) {
6706f32e7eSjoerg     if (!I.DomNode)
6806f32e7eSjoerg       continue;
6906f32e7eSjoerg     MachineBasicBlock *MBB = I.DomNode->getBlock();
7006f32e7eSjoerg     assert(I.Value && "No live-in value found");
7106f32e7eSjoerg     SlotIndex Start, End;
7206f32e7eSjoerg     std::tie(Start, End) = Indexes->getMBBRange(MBB);
7306f32e7eSjoerg 
7406f32e7eSjoerg     if (I.Kill.isValid())
7506f32e7eSjoerg       // Value is killed inside this block.
7606f32e7eSjoerg       End = I.Kill;
7706f32e7eSjoerg     else {
7806f32e7eSjoerg       // The value is live-through, update LiveOut as well.
7906f32e7eSjoerg       // Defer the Domtree lookup until it is needed.
8006f32e7eSjoerg       assert(Seen.test(MBB->getNumber()));
8106f32e7eSjoerg       Map[MBB] = LiveOutPair(I.Value, nullptr);
8206f32e7eSjoerg     }
8306f32e7eSjoerg     Updater.setDest(&I.LR);
8406f32e7eSjoerg     Updater.add(Start, End, I.Value);
8506f32e7eSjoerg   }
8606f32e7eSjoerg   LiveIn.clear();
8706f32e7eSjoerg }
8806f32e7eSjoerg 
extend(LiveRange & LR,SlotIndex Use,unsigned PhysReg,ArrayRef<SlotIndex> Undefs)8906f32e7eSjoerg void LiveRangeCalc::extend(LiveRange &LR, SlotIndex Use, unsigned PhysReg,
9006f32e7eSjoerg                            ArrayRef<SlotIndex> Undefs) {
9106f32e7eSjoerg   assert(Use.isValid() && "Invalid SlotIndex");
9206f32e7eSjoerg   assert(Indexes && "Missing SlotIndexes");
9306f32e7eSjoerg   assert(DomTree && "Missing dominator tree");
9406f32e7eSjoerg 
9506f32e7eSjoerg   MachineBasicBlock *UseMBB = Indexes->getMBBFromIndex(Use.getPrevSlot());
9606f32e7eSjoerg   assert(UseMBB && "No MBB at Use");
9706f32e7eSjoerg 
9806f32e7eSjoerg   // Is there a def in the same MBB we can extend?
9906f32e7eSjoerg   auto EP = LR.extendInBlock(Undefs, Indexes->getMBBStartIdx(UseMBB), Use);
10006f32e7eSjoerg   if (EP.first != nullptr || EP.second)
10106f32e7eSjoerg     return;
10206f32e7eSjoerg 
10306f32e7eSjoerg   // Find the single reaching def, or determine if Use is jointly dominated by
10406f32e7eSjoerg   // multiple values, and we may need to create even more phi-defs to preserve
10506f32e7eSjoerg   // VNInfo SSA form.  Perform a search for all predecessor blocks where we
10606f32e7eSjoerg   // know the dominating VNInfo.
10706f32e7eSjoerg   if (findReachingDefs(LR, *UseMBB, Use, PhysReg, Undefs))
10806f32e7eSjoerg     return;
10906f32e7eSjoerg 
11006f32e7eSjoerg   // When there were multiple different values, we may need new PHIs.
11106f32e7eSjoerg   calculateValues();
11206f32e7eSjoerg }
11306f32e7eSjoerg 
11406f32e7eSjoerg // This function is called by a client after using the low-level API to add
11506f32e7eSjoerg // live-out and live-in blocks.  The unique value optimization is not
11606f32e7eSjoerg // available, SplitEditor::transferValues handles that case directly anyway.
calculateValues()11706f32e7eSjoerg void LiveRangeCalc::calculateValues() {
11806f32e7eSjoerg   assert(Indexes && "Missing SlotIndexes");
11906f32e7eSjoerg   assert(DomTree && "Missing dominator tree");
12006f32e7eSjoerg   updateSSA();
12106f32e7eSjoerg   updateFromLiveIns();
12206f32e7eSjoerg }
12306f32e7eSjoerg 
isDefOnEntry(LiveRange & LR,ArrayRef<SlotIndex> Undefs,MachineBasicBlock & MBB,BitVector & DefOnEntry,BitVector & UndefOnEntry)12406f32e7eSjoerg bool LiveRangeCalc::isDefOnEntry(LiveRange &LR, ArrayRef<SlotIndex> Undefs,
12506f32e7eSjoerg                                  MachineBasicBlock &MBB, BitVector &DefOnEntry,
12606f32e7eSjoerg                                  BitVector &UndefOnEntry) {
12706f32e7eSjoerg   unsigned BN = MBB.getNumber();
12806f32e7eSjoerg   if (DefOnEntry[BN])
12906f32e7eSjoerg     return true;
13006f32e7eSjoerg   if (UndefOnEntry[BN])
13106f32e7eSjoerg     return false;
13206f32e7eSjoerg 
13306f32e7eSjoerg   auto MarkDefined = [BN, &DefOnEntry](MachineBasicBlock &B) -> bool {
13406f32e7eSjoerg     for (MachineBasicBlock *S : B.successors())
13506f32e7eSjoerg       DefOnEntry[S->getNumber()] = true;
13606f32e7eSjoerg     DefOnEntry[BN] = true;
13706f32e7eSjoerg     return true;
13806f32e7eSjoerg   };
13906f32e7eSjoerg 
14006f32e7eSjoerg   SetVector<unsigned> WorkList;
14106f32e7eSjoerg   // Checking if the entry of MBB is reached by some def: add all predecessors
14206f32e7eSjoerg   // that are potentially defined-on-exit to the work list.
14306f32e7eSjoerg   for (MachineBasicBlock *P : MBB.predecessors())
14406f32e7eSjoerg     WorkList.insert(P->getNumber());
14506f32e7eSjoerg 
14606f32e7eSjoerg   for (unsigned i = 0; i != WorkList.size(); ++i) {
14706f32e7eSjoerg     // Determine if the exit from the block is reached by some def.
14806f32e7eSjoerg     unsigned N = WorkList[i];
14906f32e7eSjoerg     MachineBasicBlock &B = *MF->getBlockNumbered(N);
15006f32e7eSjoerg     if (Seen[N]) {
15106f32e7eSjoerg       const LiveOutPair &LOB = Map[&B];
15206f32e7eSjoerg       if (LOB.first != nullptr && LOB.first != &UndefVNI)
15306f32e7eSjoerg         return MarkDefined(B);
15406f32e7eSjoerg     }
15506f32e7eSjoerg     SlotIndex Begin, End;
15606f32e7eSjoerg     std::tie(Begin, End) = Indexes->getMBBRange(&B);
15706f32e7eSjoerg     // Treat End as not belonging to B.
15806f32e7eSjoerg     // If LR has a segment S that starts at the next block, i.e. [End, ...),
15906f32e7eSjoerg     // std::upper_bound will return the segment following S. Instead,
16006f32e7eSjoerg     // S should be treated as the first segment that does not overlap B.
161*da58b97aSjoerg     LiveRange::iterator UB = upper_bound(LR, End.getPrevSlot());
16206f32e7eSjoerg     if (UB != LR.begin()) {
16306f32e7eSjoerg       LiveRange::Segment &Seg = *std::prev(UB);
16406f32e7eSjoerg       if (Seg.end > Begin) {
16506f32e7eSjoerg         // There is a segment that overlaps B. If the range is not explicitly
16606f32e7eSjoerg         // undefined between the end of the segment and the end of the block,
16706f32e7eSjoerg         // treat the block as defined on exit. If it is, go to the next block
16806f32e7eSjoerg         // on the work list.
16906f32e7eSjoerg         if (LR.isUndefIn(Undefs, Seg.end, End))
17006f32e7eSjoerg           continue;
17106f32e7eSjoerg         return MarkDefined(B);
17206f32e7eSjoerg       }
17306f32e7eSjoerg     }
17406f32e7eSjoerg 
17506f32e7eSjoerg     // No segment overlaps with this block. If this block is not defined on
17606f32e7eSjoerg     // entry, or it undefines the range, do not process its predecessors.
17706f32e7eSjoerg     if (UndefOnEntry[N] || LR.isUndefIn(Undefs, Begin, End)) {
17806f32e7eSjoerg       UndefOnEntry[N] = true;
17906f32e7eSjoerg       continue;
18006f32e7eSjoerg     }
18106f32e7eSjoerg     if (DefOnEntry[N])
18206f32e7eSjoerg       return MarkDefined(B);
18306f32e7eSjoerg 
18406f32e7eSjoerg     // Still don't know: add all predecessors to the work list.
18506f32e7eSjoerg     for (MachineBasicBlock *P : B.predecessors())
18606f32e7eSjoerg       WorkList.insert(P->getNumber());
18706f32e7eSjoerg   }
18806f32e7eSjoerg 
18906f32e7eSjoerg   UndefOnEntry[BN] = true;
19006f32e7eSjoerg   return false;
19106f32e7eSjoerg }
19206f32e7eSjoerg 
findReachingDefs(LiveRange & LR,MachineBasicBlock & UseMBB,SlotIndex Use,unsigned PhysReg,ArrayRef<SlotIndex> Undefs)19306f32e7eSjoerg bool LiveRangeCalc::findReachingDefs(LiveRange &LR, MachineBasicBlock &UseMBB,
19406f32e7eSjoerg                                      SlotIndex Use, unsigned PhysReg,
19506f32e7eSjoerg                                      ArrayRef<SlotIndex> Undefs) {
19606f32e7eSjoerg   unsigned UseMBBNum = UseMBB.getNumber();
19706f32e7eSjoerg 
19806f32e7eSjoerg   // Block numbers where LR should be live-in.
19906f32e7eSjoerg   SmallVector<unsigned, 16> WorkList(1, UseMBBNum);
20006f32e7eSjoerg 
20106f32e7eSjoerg   // Remember if we have seen more than one value.
20206f32e7eSjoerg   bool UniqueVNI = true;
20306f32e7eSjoerg   VNInfo *TheVNI = nullptr;
20406f32e7eSjoerg 
20506f32e7eSjoerg   bool FoundUndef = false;
20606f32e7eSjoerg 
20706f32e7eSjoerg   // Using Seen as a visited set, perform a BFS for all reaching defs.
20806f32e7eSjoerg   for (unsigned i = 0; i != WorkList.size(); ++i) {
20906f32e7eSjoerg     MachineBasicBlock *MBB = MF->getBlockNumbered(WorkList[i]);
21006f32e7eSjoerg 
21106f32e7eSjoerg #ifndef NDEBUG
21206f32e7eSjoerg     if (MBB->pred_empty()) {
21306f32e7eSjoerg       MBB->getParent()->verify();
21406f32e7eSjoerg       errs() << "Use of " << printReg(PhysReg, MRI->getTargetRegisterInfo())
21506f32e7eSjoerg              << " does not have a corresponding definition on every path:\n";
21606f32e7eSjoerg       const MachineInstr *MI = Indexes->getInstructionFromIndex(Use);
21706f32e7eSjoerg       if (MI != nullptr)
21806f32e7eSjoerg         errs() << Use << " " << *MI;
21906f32e7eSjoerg       report_fatal_error("Use not jointly dominated by defs.");
22006f32e7eSjoerg     }
22106f32e7eSjoerg 
22206f32e7eSjoerg     if (Register::isPhysicalRegister(PhysReg) && !MBB->isLiveIn(PhysReg)) {
22306f32e7eSjoerg       MBB->getParent()->verify();
22406f32e7eSjoerg       const TargetRegisterInfo *TRI = MRI->getTargetRegisterInfo();
22506f32e7eSjoerg       errs() << "The register " << printReg(PhysReg, TRI)
22606f32e7eSjoerg              << " needs to be live in to " << printMBBReference(*MBB)
22706f32e7eSjoerg              << ", but is missing from the live-in list.\n";
22806f32e7eSjoerg       report_fatal_error("Invalid global physical register");
22906f32e7eSjoerg     }
23006f32e7eSjoerg #endif
23106f32e7eSjoerg     FoundUndef |= MBB->pred_empty();
23206f32e7eSjoerg 
23306f32e7eSjoerg     for (MachineBasicBlock *Pred : MBB->predecessors()) {
23406f32e7eSjoerg        // Is this a known live-out block?
23506f32e7eSjoerg        if (Seen.test(Pred->getNumber())) {
23606f32e7eSjoerg          if (VNInfo *VNI = Map[Pred].first) {
23706f32e7eSjoerg            if (TheVNI && TheVNI != VNI)
23806f32e7eSjoerg              UniqueVNI = false;
23906f32e7eSjoerg            TheVNI = VNI;
24006f32e7eSjoerg          }
24106f32e7eSjoerg          continue;
24206f32e7eSjoerg        }
24306f32e7eSjoerg 
24406f32e7eSjoerg        SlotIndex Start, End;
24506f32e7eSjoerg        std::tie(Start, End) = Indexes->getMBBRange(Pred);
24606f32e7eSjoerg 
24706f32e7eSjoerg        // First time we see Pred.  Try to determine the live-out value, but set
24806f32e7eSjoerg        // it as null if Pred is live-through with an unknown value.
24906f32e7eSjoerg        auto EP = LR.extendInBlock(Undefs, Start, End);
25006f32e7eSjoerg        VNInfo *VNI = EP.first;
25106f32e7eSjoerg        FoundUndef |= EP.second;
25206f32e7eSjoerg        setLiveOutValue(Pred, EP.second ? &UndefVNI : VNI);
25306f32e7eSjoerg        if (VNI) {
25406f32e7eSjoerg          if (TheVNI && TheVNI != VNI)
25506f32e7eSjoerg            UniqueVNI = false;
25606f32e7eSjoerg          TheVNI = VNI;
25706f32e7eSjoerg        }
25806f32e7eSjoerg        if (VNI || EP.second)
25906f32e7eSjoerg          continue;
26006f32e7eSjoerg 
26106f32e7eSjoerg        // No, we need a live-in value for Pred as well
26206f32e7eSjoerg        if (Pred != &UseMBB)
26306f32e7eSjoerg          WorkList.push_back(Pred->getNumber());
26406f32e7eSjoerg        else
26506f32e7eSjoerg           // Loopback to UseMBB, so value is really live through.
26606f32e7eSjoerg          Use = SlotIndex();
26706f32e7eSjoerg     }
26806f32e7eSjoerg   }
26906f32e7eSjoerg 
27006f32e7eSjoerg   LiveIn.clear();
27106f32e7eSjoerg   FoundUndef |= (TheVNI == nullptr || TheVNI == &UndefVNI);
27206f32e7eSjoerg   if (!Undefs.empty() && FoundUndef)
27306f32e7eSjoerg     UniqueVNI = false;
27406f32e7eSjoerg 
27506f32e7eSjoerg   // Both updateSSA() and LiveRangeUpdater benefit from ordered blocks, but
27606f32e7eSjoerg   // neither require it. Skip the sorting overhead for small updates.
27706f32e7eSjoerg   if (WorkList.size() > 4)
27806f32e7eSjoerg     array_pod_sort(WorkList.begin(), WorkList.end());
27906f32e7eSjoerg 
28006f32e7eSjoerg   // If a unique reaching def was found, blit in the live ranges immediately.
28106f32e7eSjoerg   if (UniqueVNI) {
28206f32e7eSjoerg     assert(TheVNI != nullptr && TheVNI != &UndefVNI);
28306f32e7eSjoerg     LiveRangeUpdater Updater(&LR);
28406f32e7eSjoerg     for (unsigned BN : WorkList) {
28506f32e7eSjoerg       SlotIndex Start, End;
28606f32e7eSjoerg       std::tie(Start, End) = Indexes->getMBBRange(BN);
28706f32e7eSjoerg       // Trim the live range in UseMBB.
28806f32e7eSjoerg       if (BN == UseMBBNum && Use.isValid())
28906f32e7eSjoerg         End = Use;
29006f32e7eSjoerg       else
29106f32e7eSjoerg         Map[MF->getBlockNumbered(BN)] = LiveOutPair(TheVNI, nullptr);
29206f32e7eSjoerg       Updater.add(Start, End, TheVNI);
29306f32e7eSjoerg     }
29406f32e7eSjoerg     return true;
29506f32e7eSjoerg   }
29606f32e7eSjoerg 
29706f32e7eSjoerg   // Prepare the defined/undefined bit vectors.
29806f32e7eSjoerg   EntryInfoMap::iterator Entry;
29906f32e7eSjoerg   bool DidInsert;
30006f32e7eSjoerg   std::tie(Entry, DidInsert) = EntryInfos.insert(
30106f32e7eSjoerg       std::make_pair(&LR, std::make_pair(BitVector(), BitVector())));
30206f32e7eSjoerg   if (DidInsert) {
30306f32e7eSjoerg     // Initialize newly inserted entries.
30406f32e7eSjoerg     unsigned N = MF->getNumBlockIDs();
30506f32e7eSjoerg     Entry->second.first.resize(N);
30606f32e7eSjoerg     Entry->second.second.resize(N);
30706f32e7eSjoerg   }
30806f32e7eSjoerg   BitVector &DefOnEntry = Entry->second.first;
30906f32e7eSjoerg   BitVector &UndefOnEntry = Entry->second.second;
31006f32e7eSjoerg 
31106f32e7eSjoerg   // Multiple values were found, so transfer the work list to the LiveIn array
31206f32e7eSjoerg   // where UpdateSSA will use it as a work list.
31306f32e7eSjoerg   LiveIn.reserve(WorkList.size());
31406f32e7eSjoerg   for (unsigned BN : WorkList) {
31506f32e7eSjoerg     MachineBasicBlock *MBB = MF->getBlockNumbered(BN);
31606f32e7eSjoerg     if (!Undefs.empty() &&
31706f32e7eSjoerg         !isDefOnEntry(LR, Undefs, *MBB, DefOnEntry, UndefOnEntry))
31806f32e7eSjoerg       continue;
31906f32e7eSjoerg     addLiveInBlock(LR, DomTree->getNode(MBB));
32006f32e7eSjoerg     if (MBB == &UseMBB)
32106f32e7eSjoerg       LiveIn.back().Kill = Use;
32206f32e7eSjoerg   }
32306f32e7eSjoerg 
32406f32e7eSjoerg   return false;
32506f32e7eSjoerg }
32606f32e7eSjoerg 
32706f32e7eSjoerg // This is essentially the same iterative algorithm that SSAUpdater uses,
32806f32e7eSjoerg // except we already have a dominator tree, so we don't have to recompute it.
updateSSA()32906f32e7eSjoerg void LiveRangeCalc::updateSSA() {
33006f32e7eSjoerg   assert(Indexes && "Missing SlotIndexes");
33106f32e7eSjoerg   assert(DomTree && "Missing dominator tree");
33206f32e7eSjoerg 
33306f32e7eSjoerg   // Interate until convergence.
33406f32e7eSjoerg   bool Changed;
33506f32e7eSjoerg   do {
33606f32e7eSjoerg     Changed = false;
33706f32e7eSjoerg     // Propagate live-out values down the dominator tree, inserting phi-defs
33806f32e7eSjoerg     // when necessary.
33906f32e7eSjoerg     for (LiveInBlock &I : LiveIn) {
34006f32e7eSjoerg       MachineDomTreeNode *Node = I.DomNode;
34106f32e7eSjoerg       // Skip block if the live-in value has already been determined.
34206f32e7eSjoerg       if (!Node)
34306f32e7eSjoerg         continue;
34406f32e7eSjoerg       MachineBasicBlock *MBB = Node->getBlock();
34506f32e7eSjoerg       MachineDomTreeNode *IDom = Node->getIDom();
34606f32e7eSjoerg       LiveOutPair IDomValue;
34706f32e7eSjoerg 
34806f32e7eSjoerg       // We need a live-in value to a block with no immediate dominator?
34906f32e7eSjoerg       // This is probably an unreachable block that has survived somehow.
35006f32e7eSjoerg       bool needPHI = !IDom || !Seen.test(IDom->getBlock()->getNumber());
35106f32e7eSjoerg 
35206f32e7eSjoerg       // IDom dominates all of our predecessors, but it may not be their
35306f32e7eSjoerg       // immediate dominator. Check if any of them have live-out values that are
35406f32e7eSjoerg       // properly dominated by IDom. If so, we need a phi-def here.
35506f32e7eSjoerg       if (!needPHI) {
35606f32e7eSjoerg         IDomValue = Map[IDom->getBlock()];
35706f32e7eSjoerg 
35806f32e7eSjoerg         // Cache the DomTree node that defined the value.
35906f32e7eSjoerg         if (IDomValue.first && IDomValue.first != &UndefVNI &&
36006f32e7eSjoerg             !IDomValue.second) {
36106f32e7eSjoerg           Map[IDom->getBlock()].second = IDomValue.second =
36206f32e7eSjoerg             DomTree->getNode(Indexes->getMBBFromIndex(IDomValue.first->def));
36306f32e7eSjoerg         }
36406f32e7eSjoerg 
36506f32e7eSjoerg         for (MachineBasicBlock *Pred : MBB->predecessors()) {
36606f32e7eSjoerg           LiveOutPair &Value = Map[Pred];
36706f32e7eSjoerg           if (!Value.first || Value.first == IDomValue.first)
36806f32e7eSjoerg             continue;
36906f32e7eSjoerg           if (Value.first == &UndefVNI) {
37006f32e7eSjoerg             needPHI = true;
37106f32e7eSjoerg             break;
37206f32e7eSjoerg           }
37306f32e7eSjoerg 
37406f32e7eSjoerg           // Cache the DomTree node that defined the value.
37506f32e7eSjoerg           if (!Value.second)
37606f32e7eSjoerg             Value.second =
37706f32e7eSjoerg               DomTree->getNode(Indexes->getMBBFromIndex(Value.first->def));
37806f32e7eSjoerg 
37906f32e7eSjoerg           // This predecessor is carrying something other than IDomValue.
38006f32e7eSjoerg           // It could be because IDomValue hasn't propagated yet, or it could be
38106f32e7eSjoerg           // because MBB is in the dominance frontier of that value.
38206f32e7eSjoerg           if (DomTree->dominates(IDom, Value.second)) {
38306f32e7eSjoerg             needPHI = true;
38406f32e7eSjoerg             break;
38506f32e7eSjoerg           }
38606f32e7eSjoerg         }
38706f32e7eSjoerg       }
38806f32e7eSjoerg 
38906f32e7eSjoerg       // The value may be live-through even if Kill is set, as can happen when
39006f32e7eSjoerg       // we are called from extendRange. In that case LiveOutSeen is true, and
39106f32e7eSjoerg       // LiveOut indicates a foreign or missing value.
39206f32e7eSjoerg       LiveOutPair &LOP = Map[MBB];
39306f32e7eSjoerg 
39406f32e7eSjoerg       // Create a phi-def if required.
39506f32e7eSjoerg       if (needPHI) {
39606f32e7eSjoerg         Changed = true;
39706f32e7eSjoerg         assert(Alloc && "Need VNInfo allocator to create PHI-defs");
39806f32e7eSjoerg         SlotIndex Start, End;
39906f32e7eSjoerg         std::tie(Start, End) = Indexes->getMBBRange(MBB);
40006f32e7eSjoerg         LiveRange &LR = I.LR;
40106f32e7eSjoerg         VNInfo *VNI = LR.getNextValue(Start, *Alloc);
40206f32e7eSjoerg         I.Value = VNI;
40306f32e7eSjoerg         // This block is done, we know the final value.
40406f32e7eSjoerg         I.DomNode = nullptr;
40506f32e7eSjoerg 
40606f32e7eSjoerg         // Add liveness since updateFromLiveIns now skips this node.
40706f32e7eSjoerg         if (I.Kill.isValid()) {
40806f32e7eSjoerg           if (VNI)
40906f32e7eSjoerg             LR.addSegment(LiveInterval::Segment(Start, I.Kill, VNI));
41006f32e7eSjoerg         } else {
41106f32e7eSjoerg           if (VNI)
41206f32e7eSjoerg             LR.addSegment(LiveInterval::Segment(Start, End, VNI));
41306f32e7eSjoerg           LOP = LiveOutPair(VNI, Node);
41406f32e7eSjoerg         }
41506f32e7eSjoerg       } else if (IDomValue.first && IDomValue.first != &UndefVNI) {
41606f32e7eSjoerg         // No phi-def here. Remember incoming value.
41706f32e7eSjoerg         I.Value = IDomValue.first;
41806f32e7eSjoerg 
41906f32e7eSjoerg         // If the IDomValue is killed in the block, don't propagate through.
42006f32e7eSjoerg         if (I.Kill.isValid())
42106f32e7eSjoerg           continue;
42206f32e7eSjoerg 
42306f32e7eSjoerg         // Propagate IDomValue if it isn't killed:
42406f32e7eSjoerg         // MBB is live-out and doesn't define its own value.
42506f32e7eSjoerg         if (LOP.first == IDomValue.first)
42606f32e7eSjoerg           continue;
42706f32e7eSjoerg         Changed = true;
42806f32e7eSjoerg         LOP = IDomValue;
42906f32e7eSjoerg       }
43006f32e7eSjoerg     }
43106f32e7eSjoerg   } while (Changed);
43206f32e7eSjoerg }
43306f32e7eSjoerg 
isJointlyDominated(const MachineBasicBlock * MBB,ArrayRef<SlotIndex> Defs,const SlotIndexes & Indexes)43406f32e7eSjoerg bool LiveRangeCalc::isJointlyDominated(const MachineBasicBlock *MBB,
43506f32e7eSjoerg                                        ArrayRef<SlotIndex> Defs,
43606f32e7eSjoerg                                        const SlotIndexes &Indexes) {
43706f32e7eSjoerg   const MachineFunction &MF = *MBB->getParent();
43806f32e7eSjoerg   BitVector DefBlocks(MF.getNumBlockIDs());
43906f32e7eSjoerg   for (SlotIndex I : Defs)
44006f32e7eSjoerg     DefBlocks.set(Indexes.getMBBFromIndex(I)->getNumber());
44106f32e7eSjoerg 
44206f32e7eSjoerg   SetVector<unsigned> PredQueue;
44306f32e7eSjoerg   PredQueue.insert(MBB->getNumber());
44406f32e7eSjoerg   for (unsigned i = 0; i != PredQueue.size(); ++i) {
44506f32e7eSjoerg     unsigned BN = PredQueue[i];
44606f32e7eSjoerg     if (DefBlocks[BN])
44706f32e7eSjoerg       return true;
44806f32e7eSjoerg     const MachineBasicBlock *B = MF.getBlockNumbered(BN);
44906f32e7eSjoerg     for (const MachineBasicBlock *P : B->predecessors())
45006f32e7eSjoerg       PredQueue.insert(P->getNumber());
45106f32e7eSjoerg   }
45206f32e7eSjoerg   return false;
45306f32e7eSjoerg }
454