From 87299dec03db4cad748244fcfbd4b72c3847cff6 Mon Sep 17 00:00:00 2001
From: Jason Hiser <jdhiser@gmail.com>
Date: Thu, 31 Jan 2019 10:31:23 -0500
Subject: [PATCH] added irdb-cfg

---
 include/inc-cfg/BasicBlock.hpp   | 30 ++++++------
 include/inc-cfg/CFG.hpp          | 80 +++++++++++---------------------
 include/inc-cfg/callgraph.hpp    | 56 +++++++++++-----------
 include/inc-cfg/criticaledge.hpp | 49 ++++++++-----------
 include/inc-cfg/domgraph.hpp     | 75 +++++++++++-------------------
 include/irdb-cfg                 |  2 +-
 6 files changed, 116 insertions(+), 176 deletions(-)

diff --git a/include/inc-cfg/BasicBlock.hpp b/include/inc-cfg/BasicBlock.hpp
index c04e483..8d24374 100644
--- a/include/inc-cfg/BasicBlock.hpp
+++ b/include/inc-cfg/BasicBlock.hpp
@@ -20,14 +20,14 @@
 
 #include <ostream>
 #include <set>
+#include <vector>
 
 namespace IRDB_SDK
 {
 	using namespace std;
-
 	class BasicBlock_t;
-
 	using BasicBlockSet_t = set<BasicBlock_t*>;
+	using InstructionVector_t = vector<Instruction_t*>;
 
 	class BasicBlock_t
 	{
@@ -35,24 +35,20 @@ namespace IRDB_SDK
 			BasicBlock_t() {}
 			BasicBlock_t(const BasicBlock_t& copy) = delete;
 		public:
+			virtual ~BasicBlock_t() {}
 
-			bool                       getIsExitBlock()     const = 0;
-			const InstructionVector_t& getInstructions()    const = 0;
-			const BasicBlockSet_t&     getPredecessors()    const = 0;
-			const BasicBlockSet_t&     getSuccessors()      const = 0;
-			const BasicBlockSet_t&     getIndirectTargets() const = 0;
-			const BasicBlock_t*        getFallthrough()     const = 0;
-			const BasicBlock_t*        getTarget()          const = 0;
-
+			virtual bool                       getIsExitBlock()          const = 0;
+			virtual const InstructionVector_t& getInstructions()         const = 0;
+			virtual const BasicBlockSet_t&     getPredecessors()         const = 0;
+			virtual const BasicBlockSet_t&     getSuccessors()           const = 0;
+			virtual const BasicBlockSet_t&     getIndirectTargets()      const = 0;
+			virtual bool                       endsInBranch()            const = 0;
+			virtual bool                       endsInIndirectBranch()    const = 0;
+			virtual bool                       endsInConditionalBranch() const = 0;
+			virtual Instruction_t*             getBranchInstruction()    const = 0;
 
-			bool           endsInBranch()            = 0;
-			bool           endsInIndirectBranch()    = 0;
-			bool           endsInConditionalBranch() = 0;
-			Instruction_t* getBranchInstruction()    = 0;
-
-			void           dump(ostream &os=std::cout) = 0 ;
+			virtual void           dump(ostream &os=cout) const = 0 ;
 
 	};
 	ostream& operator<<(ostream& os, const BasicBlock_t& block);
-
 }
diff --git a/include/inc-cfg/CFG.hpp b/include/inc-cfg/CFG.hpp
index 8bf1d0b..ad8fcce 100644
--- a/include/inc-cfg/CFG.hpp
+++ b/include/inc-cfg/CFG.hpp
@@ -1,56 +1,28 @@
-/*
- * Copyright (c) 2014 - Zephyr Software LLC
- *
- * This file may be used and modified for non-commercial purposes as long as
- * all copyright, permission, and nonwarranty notices are preserved.
- * Redistribution is prohibited without prior written consent from Zephyr
- * Software.
- *
- * Please contact the authors for restrictions applying to commercial use.
- *
- * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
- * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
- * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
- *
- * Author: Zephyr Software
- * e-mail: jwd@zephyr-software.com
- * URL   : http://www.zephyr-software.com/
- *
- */
 
-enum CFG_EdgeTypeEnum { CFG_FallthroughEdge, CFG_TargetEdge, CFG_IndirectEdge };
-typedef std::set<CFG_EdgeTypeEnum> CFG_EdgeType;
-
-class ControlFlowGraph_t
+namespace IRDB_SDK
 {
-	public:
-		ControlFlowGraph_t(Function_t* func);
-		BasicBlock_t* GetEntry() const { return entry; }
-		Function_t* GetFunction() const { return function; }
-		BasicBlockSet_t& GetBlocks()   { return blocks; }
-		const BasicBlockSet_t& GetBlocks()   const { return blocks; }
-		void dump(std::ostream &os=std::cout) const { os<<*this; }
-		bool HasEdge(BasicBlock_t *p_src, BasicBlock_t *p_tgt) const;
-		CFG_EdgeType GetEdgeType(const BasicBlock_t *p_src, const BasicBlock_t *p_tgt) const;
-
-	private:
-	// methods 
-		void Build(Function_t *func);
-		void alloc_blocks(const InstructionSet_t &starts, map<Instruction_t*,BasicBlock_t*>& insn2block_map);
-		void build_blocks(const map<Instruction_t*,BasicBlock_t*>& insn2block_map);
-		void find_unblocked_instructions(InstructionSet_t &starts, Function_t* func);
-
-	// data
-		BasicBlockSet_t blocks;
-		BasicBlock_t* entry;
-		Function_t* function;
-
-	/* friends */
-	public:
-		friend std::ostream& operator<<(std::ostream& os, const ControlFlowGraph_t& cfg);
-};
-
-
-std::ostream& operator<<(std::ostream& os, const ControlFlowGraph_t& cfg);
-
-
+	using namespace std;
+	enum CFGEdgeTypeEnum { cetFallthroughEdge, cetTargetEdge, cetIndirectEdge };
+	using CFGEdgeType_t = set<CFGEdgeTypeEnum>;
+
+	class ControlFlowGraph_t
+	{
+		protected:
+			ControlFlowGraph_t() { }
+			ControlFlowGraph_t(const ControlFlowGraph_t& copy)  = delete;
+		public:
+
+			virtual BasicBlock_t*          getEntry()                                                        const = 0 ;
+			virtual Function_t*            getFunction()                                                     const = 0 ;
+			virtual const BasicBlockSet_t& getBlocks()                                                       const = 0 ;
+			virtual bool                   hasEdge(BasicBlock_t *p_src, BasicBlock_t *p_tgt)                 const = 0 ;
+			virtual CFGEdgeType_t          getEdgeType(const BasicBlock_t *p_src, const BasicBlock_t *p_tgt) const = 0 ;
+			virtual void                   dump(ostream &os=cout)                                            const = 0 ;
+
+		// factories
+			static unique_ptr<ControlFlowGraph_t> factory(Function_t* func);
+
+	};
+	ostream& operator<<(ostream& os, const ControlFlowGraph_t& cfg);
+
+}
diff --git a/include/inc-cfg/callgraph.hpp b/include/inc-cfg/callgraph.hpp
index f1c0077..a47a9c0 100644
--- a/include/inc-cfg/callgraph.hpp
+++ b/include/inc-cfg/callgraph.hpp
@@ -4,6 +4,14 @@ namespace IRDB_SDK
 {
 	using namespace std;
 
+	class CallGraph_t;
+	class CallGraphNode_t;
+
+	using CallGraphEdge_t    = pair<CallGraphNode_t*,CallGraphNode_t*>;
+	using CallGraphNodeSet_t = set<CallGraphNode_t*>;
+	using CallSite_t         = Instruction_t*;
+	using CallSiteSet_t      = set<CallSite_t>;
+
 
 	class CallGraphNode_t
 	{
@@ -13,36 +21,29 @@ namespace IRDB_SDK
 		public:
 			virtual ~CallGraphNode_t() { }
 
-			bool isHellnode() const  =0;
-			Function_t* getFunction() const  =0;
+			virtual bool        isHellnode()           const  = 0;
+			virtual Function_t* getFunction()          const  = 0;
+			virtual void        dump(ostream& os=cout) const  = 0;
 	};
 
-
-
-	using CallGraphEdge_t    = pair<CallGraphNode_t*,CallGraphNode_t*>;
-	using CallGraphNodeSet_t = set<CallGraphNode_t*>;
-	using CallSite_t         = Instruction_t*;
-	using CallSiteSet_t      = set<CallSite_t>;
-
-	class Callgraph_t
+	class CallGraph_t
 	{
 		protected:
-			Callgraph_t() {}
-			Callgraph_t(const Callgraph_t& copy) = delete;
+			CallGraph_t() {}
+			CallGraph_t(const CallGraph_t& copy) = delete;
 		public:
-			virtual ~Callgraph_t() { }
+			virtual ~CallGraph_t() { }
 			
-			virtual void addFile() = 0;
-
-			virtual bool  edgeExists(const CallGraphEdge_t& edge) const = 0;
+		// accessors
 
+			virtual void  addFile(FileIR_t* const firp) = 0;
+			virtual bool  edgeExists(const CallGraphEdge_t& edge)        const = 0;
 			virtual const CallGraphNodeSet_t& 
 			              getCallersOfNode(CallGraphNode_t* const node)  const = 0;
-
 			virtual const CallGraphNodeSet_t& 
 			              getCalleesOfNode(CallGraphNode_t* const node)  const = 0;
-			
-			virtual const CallGraphNodeSet_t& ancestors, 
+			/*
+			virtual const CallGraphNodeSet_t& 
 				       getAncestors
 			               (
 				        const Function_t* const fn, 
@@ -50,22 +51,25 @@ namespace IRDB_SDK
 				       )                                            const = 0;
 			virtual const  CallSiteSet_t& 
 			               getCallSites(CallGraphNode_t* const n1)      const = 0;
-
-			virtual void   dump(std::ostream& fout)                     const = 0;
-			virtual string getNodeName(const CallGraphNode_t* const n1) const = 0;
-			virtual string getCallsiteDisassembly(const CallSite_t &c)  const = 0;
+ 			virtual string getNodeName(const CallGraphNode_t* const n1) const = 0;
+			*/
 			virtual bool   isReachable
 			               (
 			                CallGraphNode_t* const from, 
 			                CallGraphNode_t* const to, 
 			                bool skipHellNode = false
-			               ) const = 0;
-
+			               )                                            const = 0;
 			virtual const  CallGraphNode_t& 
 			               getDefaultHellNode()                         const = 0; 
-
 			virtual CallGraphNode_t* 
 			               findNode(Function_t* const fn)               const = 0;
+		// printer
+			virtual void   dump(ostream& fout)                     const = 0;
+
+		// factories
+			static unique_ptr<CallGraph_t>  factory(FileIR_t* const firp=nullptr);
 	};
+	ostream& operator<<(ostream& os, const CallGraph_t& cg);
+	ostream& operator<<(ostream& os, const CallGraphNode_t& cgn);
 
 }
diff --git a/include/inc-cfg/criticaledge.hpp b/include/inc-cfg/criticaledge.hpp
index 6126703..9b372be 100644
--- a/include/inc-cfg/criticaledge.hpp
+++ b/include/inc-cfg/criticaledge.hpp
@@ -1,33 +1,22 @@
-/*
- * Copyright (c) 2019 - Zephyr Software LLC
- *
- * This file may be used and modified for non-commercial purposes as long as
- * all copyright, permission, and nonwarranty notices are preserved.
- * Redistribution is prohibited without prior written consent from Zephyr
- * Software.
- *
- * Please contact the authors for restrictions applying to commercial use.
- *
- * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
- * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
- * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
- *
- * Author: Zephyr Software
- * e-mail: jwd@zephyr-software.com
- * URL   : http://www.zephyr-software.com/
- *
- */
 
-typedef std::tuple<BasicBlock_t*, BasicBlock_t*> BasicBlockEdge_t;
-typedef std::set<BasicBlockEdge_t> BasicBlockEdgeSet_t;
-
-class CriticalEdgeAnalyzer_t
+namespace IRDB_SDK
 {
-	public:
-		CriticalEdgeAnalyzer_t(const ControlFlowGraph_t &p_cfg, const bool p_conservative=true);
-		BasicBlockEdgeSet_t GetAllCriticalEdges() const;
+	using namespace std;
+	using BasicBlockEdge_t    =  tuple<BasicBlock_t*, BasicBlock_t*>;
+	using BasicBlockEdgeSet_t =  set<BasicBlockEdge_t> ;
+
+	class CriticalEdges_t
+	{
+		protected:
+			CriticalEdges_t(){}	
+			CriticalEdges_t(const CriticalEdges_t& copy) = delete;
+		public:
+			static unique_ptr<CriticalEdges_t> factory(
+			                                           const ControlFlowGraph_t &p_cfg, 
+			                                           const bool p_conservative=true
+			                                          );
+
+			virtual const BasicBlockEdgeSet_t& getAllCriticalEdges() const = 0;
+	};
 
-	private:
-		const ControlFlowGraph_t m_cfg;
-		const bool m_conservative;
-};
+}
diff --git a/include/inc-cfg/domgraph.hpp b/include/inc-cfg/domgraph.hpp
index 087fc4d..65ccef5 100644
--- a/include/inc-cfg/domgraph.hpp
+++ b/include/inc-cfg/domgraph.hpp
@@ -1,54 +1,33 @@
 
-
-
-typedef std::map<const BasicBlock_t*, BasicBlockSet_t> DominatorMap_t;
-typedef std::map<const BasicBlock_t*, BasicBlock_t*> BlockToBlockMap_t;
-
-class DominatorGraph_t
+namespace IRDB_SDK
 {
-	public:
-		DominatorGraph_t(const ControlFlowGraph_t* p_cfg, bool needs_postdoms=false, bool needs_idoms=false);
-
-
-		// get the (post) dominators for a node 
-		BasicBlockSet_t& GetDominators(const BasicBlock_t* node) { return dom_graph[node]; }
-		BasicBlockSet_t& GetPostDominators(const BasicBlock_t* node) { return post_dom_graph[node]; }
-
-		const BasicBlockSet_t& GetDominators(const BasicBlock_t* node) const { return dom_graph.at(node); }
-		const BasicBlockSet_t& GetPostDominators(const BasicBlock_t* node) const { return post_dom_graph.at(node); }
-
-		bool HasWarnings() const { return warn; }
-
-
-		// get the immeidate (post) dominators for a node 
-		const BasicBlock_t* GetImmediateDominator(const BasicBlock_t* node)  const
-		{ BlockToBlockMap_t::const_iterator it=idom_graph.find(node); return (it!=idom_graph.end()) ? it->second : NULL; }
-		const BasicBlock_t* GetImmediatePostDominators(const BasicBlock_t* node)  const
-		{ BlockToBlockMap_t::const_iterator it=post_idom_graph.find(node); return (it!=post_idom_graph.end()) ? it->second : NULL; }
-
 
-	private:
-
-        	typedef const BasicBlockSet_t& (*pred_func_ptr_t) (const BasicBlock_t* node);
-
-		DominatorMap_t Dom_Comp(const BasicBlockSet_t& N, pred_func_ptr_t pred_func, BasicBlock_t* r);
-		BlockToBlockMap_t Idom_Comp(const BasicBlockSet_t& N, const DominatorMap_t &Domin, BasicBlock_t* r);
-
-
-		DominatorMap_t dom_graph;
-		BlockToBlockMap_t idom_graph;
-
-		DominatorMap_t post_dom_graph;
-		BlockToBlockMap_t post_idom_graph;
-
-		const ControlFlowGraph_t& cfg;	// a reference to our cfg.
-
-		bool warn;
-
-                friend std::ostream& operator<<(std::ostream& os, const DominatorGraph_t& cfg);
+	using namespace std;
+
+	using  DominatorMap_t    = map<const BasicBlock_t*, BasicBlockSet_t>; 
+	using  BlockToBlockMap_t = map<const BasicBlock_t*, BasicBlock_t*>;
+
+	class DominatorGraph_t
+	{
+		protected:
+			DominatorGraph_t(){}
+			DominatorGraph_t(const DominatorGraph_t& copy)=delete;
+		public:
+			unique_ptr<DominatorGraph_t*> factory(
+			                                      const ControlFlowGraph_t* p_cfg, 
+			                                      bool needs_postdoms=false, 
+			                                      bool needs_idoms=false
+			                                      );
+
+			virtual const BasicBlockSet_t& getDominators(const BasicBlock_t* node)               const = 0 ;
+			virtual const BasicBlockSet_t& getPostDominators(const BasicBlock_t* node)           const = 0 ;
+			virtual bool                   hasWarnings()                                         const = 0 ;
+			virtual const BasicBlock_t*    getImmediateDominator(const BasicBlock_t* node)       const = 0 ;
+			virtual const BasicBlock_t*    getImmediatePostDominators(const BasicBlock_t* node)  const = 0 ;
+			virtual void                   dump(ostream &os=cout)                                const = 0 ;
 	
-};
-
-std::ostream& operator<<(std::ostream& os, const DominatorGraph_t& cfg);
+	};
+	ostream& operator<<(ostream& os, const DominatorGraph_t& cfg);
 
+}
 
diff --git a/include/irdb-cfg b/include/irdb-cfg
index 6251c73..21f4c5d 100644
--- a/include/irdb-cfg
+++ b/include/irdb-cfg
@@ -23,7 +23,7 @@
 
 
 /* Building a CFG depends on core functionality */
-#include <IRDB_SDK-core.hpp>
+#include <irdb-core>
 
 #include <vector>
 #include <set>
-- 
GitLab