#include <ostream> namespace libIRDB { using namespace std; using DominatorMap_t = map<IRDB_SDK::BasicBlock_t*, IRDB_SDK::BasicBlockSet_t>; using BlockToBlockMap_t = map<IRDB_SDK::BasicBlock_t*, IRDB_SDK::BasicBlock_t*>; class DominatorGraph_t : public IRDB_SDK::DominatorGraph_t { public: DominatorGraph_t(const ControlFlowGraph_t* p_cfg, bool needs_postdoms=false, bool needs_idoms=false); virtual ~DominatorGraph_t() { } // get the (post) dominators for a node IRDB_SDK::BasicBlockSet_t& GetDominators(IRDB_SDK::BasicBlock_t* node) { return dom_graph[node]; } IRDB_SDK::BasicBlockSet_t& GetPostDominators(IRDB_SDK::BasicBlock_t* node) { return post_dom_graph[node]; } const IRDB_SDK::BasicBlockSet_t& getDominators(const IRDB_SDK::BasicBlock_t* node) const { return dom_graph.at(const_cast<IRDB_SDK::BasicBlock_t*>(node)); } const IRDB_SDK::BasicBlockSet_t& getDominated (const IRDB_SDK::BasicBlock_t* node) const { return dominated_graph.at(const_cast<IRDB_SDK::BasicBlock_t*>(node)); } // const IRDB_SDK::BasicBlockSet_t& getPostDominators(const IRDB_SDK::BasicBlock_t* node) const { assert(0); } // const IRDB_SDK::BasicBlockSet_t& getPostDominated (const IRDB_SDK::BasicBlock_t* node) const { assert(0); } bool hasWarnings() const { return warn; } // get the immeidate (post) dominators for a node const IRDB_SDK::BasicBlock_t* getImmediateDominator (const IRDB_SDK::BasicBlock_t* node) const { auto it=idom_graph.find(const_cast<IRDB_SDK::BasicBlock_t*>(node)); return (it!=idom_graph.end()) ? it->second : nullptr; } const IRDB_SDK::BasicBlockSet_t& getImmediateDominated (const IRDB_SDK::BasicBlock_t* node) const { const static IRDB_SDK::BasicBlockSet_t empty; auto it=idominated_graph.find(const_cast<IRDB_SDK::BasicBlock_t*>(node)); return (it!=idominated_graph.end()) ? it->second : empty; } // const IRDB_SDK::BasicBlock_t* getImmediatePostDominator(const IRDB_SDK::BasicBlock_t* node) const { assert(0); } // const IRDB_SDK::BasicBlockSet_t& getImmediatePostDominated(const IRDB_SDK::BasicBlock_t* node) const { assert(0); } void dump(ostream& os=cout) const; private: void Dominated_Compute(); using pred_func_ptr_t = const IRDB_SDK::BasicBlockSet_t& (*) (const IRDB_SDK::BasicBlock_t* node); DominatorMap_t Dom_Comp(const IRDB_SDK::BasicBlockVector_t& N, pred_func_ptr_t pred_func, IRDB_SDK::BasicBlock_t* r); BlockToBlockMap_t Idom_Comp(const IRDB_SDK::BasicBlockVector_t& N, const DominatorMap_t &Domin, IRDB_SDK::BasicBlock_t* r); DominatorMap_t dom_graph; BlockToBlockMap_t idom_graph; DominatorMap_t dominated_graph; DominatorMap_t idominated_graph; DominatorMap_t post_dom_graph; BlockToBlockMap_t post_idom_graph; const ControlFlowGraph_t& cfg; // a reference to our cfg. bool warn; }; }