Remove incorrect export declaration
[dyninst.git] / patchAPI / h / PatchCFG.h
1 /*
2  * See the dyninst/COPYRIGHT file for copyright information.
3  * 
4  * We provide the Paradyn Tools (below described as "Paradyn")
5  * on an AS IS basis, and do not warrant its validity or performance.
6  * We reserve the right to update, modify, or discontinue this
7  * software at any time.  We shall have no obligation to supply such
8  * updates or modifications or any other form of support to you.
9  * 
10  * By your use of Paradyn, you understand and agree that we (or any
11  * other person or entity with proprietary rights in Paradyn) are
12  * under no obligation to provide either maintenance services,
13  * update services, notices of latent defects, or correction of
14  * defects for Paradyn.
15  * 
16  * This library is free software; you can redistribute it and/or
17  * modify it under the terms of the GNU Lesser General Public
18  * License as published by the Free Software Foundation; either
19  * version 2.1 of the License, or (at your option) any later version.
20  * 
21  * This library is distributed in the hope that it will be useful,
22  * but WITHOUT ANY WARRANTY; without even the implied warranty of
23  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
24  * Lesser General Public License for more details.
25  * 
26  * You should have received a copy of the GNU Lesser General Public
27  * License along with this library; if not, write to the Free Software
28  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
29  */
30 /* Public Interface */
31
32 #ifndef _PATCHAPI_DYNINST_CFG_H_
33 #define _PATCHAPI_DYNINST_CFG_H_
34
35 #include "CFG.h"
36 #include "PatchCommon.h"
37 #include "PatchObject.h"
38 #include "Point.h"
39
40 namespace Dyninst {
41 namespace PatchAPI {
42
43 class PatchParseCallback;
44
45 class PatchEdge;
46 class PatchBlock;
47 class PatchFunction;
48 class PatchCallback;
49
50 class PATCHAPI_EXPORT PatchEdge {
51    friend class PatchBlock;
52    friend class PatchFunction;
53    friend class PatchObject;
54    friend class Callback;
55    friend class PatchParseCallback;
56
57   public:
58    static PatchEdge *create(ParseAPI::Edge *,
59                                             PatchBlock *src,
60                                             PatchBlock *trg);
61    PatchEdge(ParseAPI::Edge *internalEdge,
62              PatchBlock *source,
63              PatchBlock *target);
64    PatchEdge(const PatchEdge *parent,
65              PatchBlock *child_src,
66              PatchBlock *child_trg);
67    virtual ~PatchEdge();
68
69    // Getters
70    ParseAPI::Edge *edge() const;
71    PatchBlock *src();
72    PatchBlock *trg();
73    ParseAPI::EdgeTypeEnum type() const;
74    bool sinkEdge() const;
75    bool interproc() const;
76    bool intraproc() const { return !interproc(); }
77
78    void remove(Point *);
79    PatchCallback *cb() const;
80
81    bool consistency() const;
82
83    std::string format() const;
84
85  protected:
86     ParseAPI::Edge *edge_;
87     PatchBlock *src_;
88     PatchBlock *trg_;
89
90     EdgePoints points_;
91 };
92
93 class PATCHAPI_EXPORT PatchBlock {
94   friend class PatchEdge;
95   friend class PatchFunction;
96   friend class PatchObject;
97    friend class PatchParseCallback;
98
99   public:
100    typedef std::map<Address, InstructionAPI::Instruction::Ptr> Insns;
101     typedef std::vector<PatchEdge*> edgelist;
102
103     static PatchBlock *create(ParseAPI::Block *, PatchFunction *);
104     PatchBlock(const PatchBlock *parblk, PatchObject *child);
105     PatchBlock(ParseAPI::Block *block, PatchObject *obj);
106     virtual ~PatchBlock();
107
108     // Getters
109     Address start() const;
110     Address end() const;
111     Address last() const;
112     Address size() const;
113
114     PatchFunction* getFunction(ParseAPI::Function*);
115     bool isShared();
116     int containingFuncs() const;
117     void getInsns(Insns &insns) const;
118     InstructionAPI::Instruction::Ptr getInsn(Address a) const;
119     std::string disassemble() const;
120     bool containsCall() const { return 0 < numCallEdges(); };
121     bool containsDynamicCall();
122     std::string format() const;
123     std::string long_format() const;
124     PatchFunction* getCallee();
125
126     ParseAPI::Block *block() const;
127     PatchObject* object() const;
128     PatchObject *obj() const { return object(); }
129     const edgelist &sources();
130     const edgelist &targets();
131     
132     PatchEdge *findSource(ParseAPI::EdgeTypeEnum type);
133     PatchEdge *findTarget(ParseAPI::EdgeTypeEnum type);
134
135     template <class OutputIterator> 
136     void getFuncs(OutputIterator result);
137
138     Point *findPoint(Location loc, Point::Type type, bool create = true);
139
140    void remove(Point *);
141    PatchCallback *cb() const;
142
143    bool consistency() const;
144
145    bool wasUserAdded() const;
146
147    virtual void markModified()  {};
148
149   protected:
150     typedef enum {
151       backwards,
152       forwards } Direction;
153
154     void removeSourceEdge(PatchEdge *e);
155     void removeTargetEdge(PatchEdge *e);
156     void destroyPoints();
157
158     void addSourceEdge(PatchEdge *e, bool addIfEmpty = true);
159     void addTargetEdge(PatchEdge *e, bool addIfEmpty = true);
160
161     void splitBlock(PatchBlock *succ);
162     int numRetEdges() const;
163     int numCallEdges() const;
164
165     ParseAPI::Block *block_;
166     edgelist srclist_;
167     edgelist trglist_;
168     PatchObject* obj_;
169
170     BlockPoints points_;
171 };
172
173
174
175 class PATCHAPI_EXPORT PatchFunction {
176    friend class PatchEdge;
177    friend class PatchBlock;
178    friend class PatchObject;
179    friend class PatchParseCallback;
180    friend class PatchModifier;
181
182    public:
183      struct compare {
184        bool operator()(PatchBlock * const &b1,
185                        PatchBlock * const &b2) const {
186          if(b1->start() < b2->start())
187            return true;
188          else
189            return false;
190        }
191      };
192      typedef std::set<PatchBlock *, compare> Blockset;
193
194      static PatchFunction *create(ParseAPI::Function *, PatchObject*);
195      PatchFunction(ParseAPI::Function *f, PatchObject* o);
196      PatchFunction(const PatchFunction* parFunc, PatchObject* child);
197      virtual ~PatchFunction();
198
199      const string &name() const { return func_->name(); }
200      Address addr() const { return addr_;  }
201      ParseAPI::Function *function() const { return func_; }
202      PatchObject *obj() const { return obj_; }
203
204      PatchBlock *entry();
205      const Blockset &blocks();
206      const Blockset &callBlocks();
207      //const Blockset &returnBlocks();
208      const Blockset &exitBlocks();
209
210      Point *findPoint(Location loc, Point::Type type, bool create = true);
211
212      // Moved to source code because we treat non-returning calls as exits
213      bool verifyExit(PatchBlock *block) { return exitBlocks().find(block) != exitBlocks().end(); }
214      bool verifyCall(PatchBlock *block) { return callBlocks().find(block) != callBlocks().end(); }
215
216      // Const : no building the exit/call sets (returns true if set is empty)
217      bool verifyExitConst(const PatchBlock *block) const { 
218         return exit_blocks_.empty() || 
219             exit_blocks_.find(const_cast<PatchBlock *>(block)) != exit_blocks_.end(); 
220      }
221      bool verifyCallConst(const PatchBlock *block) const { 
222         return call_blocks_.empty() || 
223             call_blocks_.find(const_cast<PatchBlock *>(block)) != call_blocks_.end(); 
224      }
225
226      // Fast access to a range of instruction points
227      bool findInsnPoints(Point::Type type, PatchBlock *block,
228                                          InsnPoints::const_iterator &start,
229                                          InsnPoints::const_iterator &end);
230
231    void remove(Point *);
232    PatchCallback *cb() const;
233
234    bool consistency() const;
235
236    virtual void markModified() {};
237
238    protected:
239      // For callbacks from ParseAPI to PatchAPI
240      void removeBlock(PatchBlock *);
241      void addBlock(PatchBlock *);
242      void splitBlock(PatchBlock *first, PatchBlock *second);
243      void destroyPoints();
244      void destroyBlockPoints(PatchBlock *block);
245      void invalidateBlocks();
246
247      ParseAPI::Function *func_;
248      PatchObject* obj_;
249      Address addr_;
250
251      Blockset all_blocks_;
252      Blockset call_blocks_;
253      Blockset return_blocks_;
254      Blockset exit_blocks_;
255
256      FuncPoints points_;
257      // For context-specific
258      std::map<PatchBlock *, BlockPoints> blockPoints_;
259      std::map<PatchEdge *, EdgePoints> edgePoints_;
260 };
261
262 template <class OutputIterator>
263 void PatchBlock::getFuncs(OutputIterator result) {
264   std::vector<ParseAPI::Function *> pFuncs;
265   block()->getFuncs(pFuncs);
266   for (unsigned i = 0; i < pFuncs.size(); ++i) {
267     PatchFunction *func = getFunction(pFuncs[i]);
268     *result = func;
269     ++result;
270   }
271 }
272
273 #define ASSERT_CONSISTENCY_FAILURE 1
274 #define CONSIST_FAIL {if (ASSERT_CONSISTENCY_FAILURE) assert(0); return false;}
275
276 };
277 };
278
279
280 #endif /* _PATCHAPI_DYNINST_CFG_H_ */