1 //===--- Passes/DataflowAnalysis.cpp --------------------------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 //===----------------------------------------------------------------------===// 10 11 #include "bolt/Passes/DataflowAnalysis.h" 12 13 #define DEBUG_TYPE "dataflow" 14 15 namespace llvm { 16 17 raw_ostream &operator<<(raw_ostream &OS, const BitVector &State) { 18 LLVM_DEBUG({ 19 OS << "BitVector("; 20 const char *Sep = ""; 21 if (State.count() > (State.size() >> 1)) { 22 OS << "all, except: "; 23 BitVector BV = State; 24 BV.flip(); 25 for (int I = BV.find_first(); I != -1; I = BV.find_next(I)) { 26 OS << Sep << I; 27 Sep = " "; 28 } 29 OS << ")"; 30 return OS; 31 } 32 for (int I = State.find_first(); I != -1; I = State.find_next(I)) { 33 OS << Sep << I; 34 Sep = " "; 35 } 36 OS << ")"; 37 return OS; 38 }); 39 OS << "BitVector"; 40 return OS; 41 } 42 43 namespace bolt { 44 45 void doForAllPreds(const BinaryBasicBlock &BB, 46 std::function<void(ProgramPoint)> Task) { 47 MCPlusBuilder *MIB = BB.getFunction()->getBinaryContext().MIB.get(); 48 for (BinaryBasicBlock *Pred : BB.predecessors()) { 49 if (Pred->isValid()) 50 Task(ProgramPoint::getLastPointAt(*Pred)); 51 } 52 if (!BB.isLandingPad()) 53 return; 54 for (BinaryBasicBlock *Thrower : BB.throwers()) { 55 for (MCInst &Inst : *Thrower) { 56 if (!MIB->isInvoke(Inst)) 57 continue; 58 const Optional<MCPlus::MCLandingPad> EHInfo = MIB->getEHInfo(Inst); 59 if (!EHInfo || EHInfo->first != BB.getLabel()) 60 continue; 61 Task(ProgramPoint(&Inst)); 62 } 63 } 64 } 65 66 /// Operates on all successors of a basic block. 67 void doForAllSuccs(const BinaryBasicBlock &BB, 68 std::function<void(ProgramPoint)> Task) { 69 for (BinaryBasicBlock *Succ : BB.successors()) { 70 if (Succ->isValid()) 71 Task(ProgramPoint::getFirstPointAt(*Succ)); 72 } 73 } 74 75 void RegStatePrinter::print(raw_ostream &OS, const BitVector &State) const { 76 if (State.all()) { 77 OS << "(all)"; 78 return; 79 } 80 if (State.count() > (State.size() >> 1)) { 81 OS << "all, except: "; 82 BitVector BV = State; 83 BV.flip(); 84 for (int I = BV.find_first(); I != -1; I = BV.find_next(I)) { 85 OS << BC.MRI->getName(I) << " "; 86 } 87 return; 88 } 89 for (int I = State.find_first(); I != -1; I = State.find_next(I)) { 90 OS << BC.MRI->getName(I) << " "; 91 } 92 } 93 94 } // namespace bolt 95 } // namespace llvm 96