Update copyright to LGPL on all files
[dyninst.git] / dyninstAPI / src / inst.h
1 /*
2  * Copyright (c) 1996-2009 Barton P. Miller
3  * 
4  * We provide the Paradyn Parallel Performance Tools (below
5  * described as "Paradyn") on an AS IS basis, and do not warrant its
6  * validity or performance.  We reserve the right to update, modify,
7  * or discontinue this software at any time.  We shall have no
8  * obligation to supply such updates or modifications or any other
9  * form of support to you.
10  * 
11  * By your use of Paradyn, you understand and agree that we (or any
12  * other person or entity with proprietary rights in Paradyn) are
13  * under no obligation to provide either maintenance services,
14  * update services, notices of latent defects, or correction of
15  * defects for Paradyn.
16  * 
17  * This library is free software; you can redistribute it and/or
18  * modify it under the terms of the GNU Lesser General Public
19  * License as published by the Free Software Foundation; either
20  * version 2.1 of the License, or (at your option) any later version.
21  * 
22  * This library is distributed in the hope that it will be useful,
23  * but WITHOUT ANY WARRANTY; without even the implied warranty of
24  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
25  * Lesser General Public License for more details.
26  * 
27  * You should have received a copy of the GNU Lesser General Public
28  * License along with this library; if not, write to the Free Software
29  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
30  */
31
32 // $Id: inst.h,v 1.104 2008/09/15 18:37:49 jaw Exp $
33
34 #ifndef INST_HDR
35 #define INST_HDR
36
37 #include <string>
38 #include "common/h/Vector.h"
39 #include "common/h/Dictionary.h"
40 #include "opcode.h" // enum opCode now defined here.
41 #include "common/h/Types.h"
42 #include "arch.h" // codeBufIndex_t 
43 #include "dyninstAPI/src/ast.h" // astNodePtr
44
45 /****************************************************************************/
46 /****************************************************************************/
47 /****************************************************************************/
48
49 class instPoint;
50 class miniTramp;
51 class baseTramp;
52 class process;
53 class int_function;
54 class metricFocusNode;
55 class codeGen;
56 class registerSpace;
57 class AddressSpace;
58 class image_variable;
59
60 typedef enum { callNoArgs, callRecordType, callFullArgs } callOptions;
61 typedef enum { callPreInsn, callPostInsn, callBranchTargetInsn, callUnset } callWhen;
62 typedef enum { orderFirstAtPoint, orderLastAtPoint } callOrder;
63
64 extern pdvector<Address> getTrampAddressesAtPoint(process *proc, 
65                                                   const instPoint *loc,
66                                                   callWhen when);
67
68 class AstNode;
69
70 /* Utility functions */
71
72 int getPointCost(process *proc, const instPoint *point);
73
74
75 /* return the function asociated with a point. */
76 int_function *getFunction(instPoint *point);
77
78 /*
79  * struct to define a list of inst requests 
80  *
81  */
82 #define FUNC_ENTRY      0x1             /* entry to the function */
83 #define FUNC_EXIT       0x2             /* exit from function */
84 #define FUNC_CALL       0x4             /* subroutines called from func */
85 #define FUNC_ARG        0x8             /* use arg as argument */
86
87 // Container class for "instrument this point with this function". 
88 // What I want to know is who is allergic to multi-letter arguments? Yeesh.
89 class instMapping {
90
91    public:
92
93       instMapping(const std::string f, const std::string i, const int w, 
94             callWhen wn, callOrder o, AstNodePtr a = AstNodePtr(), std::string l = "")
95          : func(f), inst(i), lib(l),
96          where(w), when(wn), order(o), useTrampGuard(true),
97          mt_only(false), allow_trap(false) {
98             if (a != AstNodePtr()) args.push_back(a);
99          }
100
101       instMapping(const std::string f, const std::string i, const int w, 
102             AstNodePtr a = AstNodePtr(), std::string l = "")
103          : func(f), inst(i), lib(l),
104          where(w), when(callPreInsn), order(orderLastAtPoint),
105          useTrampGuard(true), mt_only(false), allow_trap(false) {
106             if (a != AstNodePtr()) args.push_back(a);
107          }
108
109       instMapping(const std::string f, const std::string i, const int w, 
110             pdvector<AstNodePtr> &aList, std::string l = "") :
111          func(f), inst(i), lib(l),
112          where(w), when(callPreInsn), order(orderLastAtPoint),
113          useTrampGuard(true), mt_only(false), allow_trap(false) {
114             for(unsigned u=0; u < aList.size(); u++) {
115                if (aList[u] != AstNodePtr()) args.push_back(aList[u]);
116             }
117          };
118
119       // Fork
120       instMapping(const instMapping *parMapping, process *child);
121
122   ~instMapping() {
123   }
124
125 public:
126   void dontUseTrampGuard() { useTrampGuard = false; }
127   void markAs_MTonly() { mt_only = true; }
128   void canUseTrap(bool t) { allow_trap = t; }
129   bool is_MTonly() { return mt_only; }
130
131   std::string func;                 /* function to instrument */
132   std::string inst;                 /* inst. function to place at func */
133   std::string lib;                  /* library name */
134   int where;                   /* FUNC_ENTRY, FUNC_EXIT, FUNC_CALL */
135   callWhen when;               /* callPreInsn, callPostInsn */
136   callOrder order;             /* orderFirstAtPoint, orderLastAtPoint */
137   pdvector<AstNodePtr> args;      /* what to pass as arg0 ... n */
138   bool useTrampGuard;
139   bool mt_only;
140   bool allow_trap;
141   pdvector<miniTramp *> miniTramps;
142 };
143
144
145 /*
146  * get information about the cost of primitives.
147  *
148  */
149 void initPrimitiveCost();
150 void initDefaultPointFrequencyTable();
151
152 //
153 // Return the expected runtime of the passed function in instruction times.
154 //
155 unsigned getPrimitiveCost(const std::string &name);
156
157 /*
158  * Generate an instruction.
159  * Previously this was handled by the polymorphic "emit" function, which
160  * took a variety of argument types and variously returned either an
161  * Address or a Register or nothing of value.  The following family of
162  * functions replace "emit" with more strongly typed versions.
163  */
164
165 typedef enum gnenum {
166    rc_before_jump,
167    rc_after_jump,
168    rc_no_control
169 } RegControl;
170
171 // The return value is a magic "hand this in when we update" black box;
172 // emitA handles emission of things like ifs that need to be updated later.
173 codeBufIndex_t emitA(opCode op, Register src1, Register src2, Register dst, 
174                      codeGen &gen, RegControl rc, bool noCost);
175
176 // for operations requiring a Register to be returned
177 // (e.g., getRetValOp, getParamOp, getSysRetValOp, getSysParamOp)
178 Register emitR(opCode op, Register src1, Register src2, Register dst, 
179                codeGen &gen, bool noCost, 
180                const instPoint *location, bool for_multithreaded);
181
182 // for general arithmetic and logic operations which return nothing
183 void     emitV(opCode op, Register src1, Register src2, Register dst, 
184                codeGen &gen, bool noCost, 
185                registerSpace *rs = NULL, int size = 4,
186                const instPoint * location = NULL, AddressSpace * proc = NULL);
187
188 // for loadOp and loadConstOp (reading from an Address)
189 void     emitVload(opCode op, Address src1, Register src2, Register dst, 
190                    codeGen &gen, bool noCost, 
191                    registerSpace *rs = NULL, int size = 4, 
192                    const instPoint * location = NULL, AddressSpace * proc = NULL);
193
194 // for storeOp (writing to an Address)
195 void     emitVstore(opCode op, Register src1, Register src2, Address dst, 
196                     codeGen &gen, bool noCost, 
197                     registerSpace *rs = NULL, int size = 4, 
198                     const instPoint * location = NULL, AddressSpace * proc = NULL);
199
200 // for loadOp and loadConstOp (reading from an Address)
201 void     emitVload(opCode op, const image_variable* src1, Register src2, Register dst, 
202                    codeGen &gen, bool noCost, 
203                    registerSpace *rs = NULL, int size = 4, 
204                    const instPoint * location = NULL, AddressSpace * proc = NULL);
205
206 // for storeOp (writing to an Address)
207 void     emitVstore(opCode op, Register src1, Register src2, const image_variable* dst, 
208                     codeGen &gen, bool noCost, 
209                     registerSpace *rs = NULL, int size = 4, 
210                     const instPoint * location = NULL, AddressSpace * proc = NULL);
211
212 // and the retyped original emitImm companion
213 void     emitImm(opCode op, Register src, RegValue src2imm, Register dst, 
214                  codeGen &gen, bool noCost,
215                  registerSpace *rs = NULL);
216
217
218 //#include "dyninstAPI/h/BPatch_memoryAccess_NP.h"
219 class BPatch_addrSpec_NP;
220 typedef BPatch_addrSpec_NP BPatch_countSpec_NP;
221
222 // Don't need the above: countSpec is typedefed to addrSpec
223
224 void emitJmpMC(int condition, int offset, codeGen &gen);
225
226 void emitASload(const BPatch_addrSpec_NP *as, Register dest, codeGen &gen, bool noCost);
227
228 void emitCSload(const BPatch_countSpec_NP *as, Register dest, codeGen &gen, bool noCost);
229
230 // VG(11/06/01): moved here and added location
231 Register emitFuncCall(opCode op, codeGen &gen,
232                       pdvector<AstNodePtr> &operands,
233                                           bool noCost, 
234                       int_function *func);
235
236 // Obsolete version that uses an address. DON'T USE THIS or expect it to survive.
237 Register emitFuncCall(opCode op, codeGen &gen,
238                       pdvector<AstNodePtr> &operands, 
239                                   bool noCost, 
240                       Address callee_addr_);
241
242 int getInsnCost(opCode t);
243
244 /*
245  * get the requested parameter into a register.
246  *
247  */
248 Register getParameter(Register dest, int param);
249
250 extern std::string getProcessStatus(const AddressSpace *p);
251
252 // TODO - what about mangled names ?
253 // expects the symbol name advanced past the underscore
254 extern unsigned findTags(const std::string funcName);
255
256 extern Address getMaxBranch();
257
258 // find these internal functions before finding any other functions
259 // extern dictionary_hash<std::string, unsigned> tagDict;
260 extern dictionary_hash <std::string, unsigned> primitiveCosts;
261
262 bool writeFunctionPtr(AddressSpace *p, Address addr, int_function *f);
263
264 /**
265  * A set of optimized emiters for common idioms.  Return 
266  * false if the platform can't perform any optimizations.
267  **/
268 //Store constant in memory at address
269 bool emitStoreConst(Address addr, int imm, codeGen &gen, bool noCost);
270 //Add constant to memory at address
271 bool emitAddSignedImm(Address addr, long int imm, codeGen &gen, bool noCost);
272 //Subtract constant from memory at address
273 bool emitSubSignedImm(Address addr, long int imm, codeGen &gen, bool noCost);
274
275 #endif