libvex_ir.h revision 496a58d130a28ac3a5ba33c9012dabbe61dc852c
1
2/*---------------------------------------------------------------*/
3/*---                                                         ---*/
4/*--- This file (libvex_ir.h) is                              ---*/
5/*--- Copyright (c) OpenWorks LLP.  All rights reserved.      ---*/
6/*---                                                         ---*/
7/*---------------------------------------------------------------*/
8
9/*
10   This file is part of LibVEX, a library for dynamic binary
11   instrumentation and translation.
12
13   Copyright (C) 2004-2005 OpenWorks LLP.
14
15   This program is free software; you can redistribute it and/or modify
16   it under the terms of the GNU General Public License as published by
17   the Free Software Foundation; Version 2 dated June 1991 of the
18   license.
19
20   This program is distributed in the hope that it will be useful,
21   but WITHOUT ANY WARRANTY; without even the implied warranty of
22   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE, or liability
23   for damages.  See the GNU General Public License for more details.
24
25   Neither the names of the U.S. Department of Energy nor the
26   University of California nor the names of its contributors may be
27   used to endorse or promote products derived from this software
28   without prior written permission.
29
30   You should have received a copy of the GNU General Public License
31   along with this program; if not, write to the Free Software
32   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
33   USA.
34*/
35
36#ifndef __LIBVEX_IR_H
37#define __LIBVEX_IR_H
38
39#include "libvex_basictypes.h"
40
41
42
43/*---------------------------------------------------------------*/
44/*--- Type definitions for the IR                             ---*/
45/*---------------------------------------------------------------*/
46
47/* General comments about naming schemes:
48
49   All publically visible functions contain the name of the primary
50   type on which they operate (IRFoo, IRBar, etc).  Hence you should
51   be able to identify these functions by grepping for "IR[A-Z]".
52
53   For some type 'IRFoo':
54
55   - ppIRFoo is the printing method for IRFoo, printing it to the
56     output channel specified in the LibVEX_Initialise call.
57
58   - eqIRFoo is a structural equality predicate for IRFoos.
59
60   - dopyIRFoo is a deep copy constructor for IRFoos.
61     It recursively traverses the entire argument tree and
62     produces a complete new tree.
63
64   - sopyIRFoo is the shallow copy constructor for IRFoos.
65     It creates a new top-level copy of the supplied object,
66     but does not copy any sub-objects.
67*/
68
69/* ------------------ Types ------------------ */
70
71typedef
72   enum {
73      Ity_INVALID=0x10FFF,
74      Ity_I1=0x11000,
75      Ity_I8,
76      Ity_I16,
77      Ity_I32,
78      Ity_I64,
79      Ity_I128,  /* 128-bit scalar */
80      Ity_F32,   /* IEEE 754 float */
81      Ity_F64,   /* IEEE 754 double */
82      Ity_V128   /* 128-bit SIMD */
83   }
84   IRType;
85
86extern void ppIRType ( IRType );
87extern Int  sizeofIRType ( IRType );
88
89
90/* ------------------ Constants ------------------ */
91
92typedef
93   enum {
94      Ico_U1=0x12000,
95      Ico_U8,
96      Ico_U16,
97      Ico_U32,
98      Ico_U64,
99      Ico_F64,   /* 64-bit IEEE754 floating */
100      Ico_F64i,  /* 64-bit unsigned int to be interpreted literally
101                    as a IEEE754 double value. */
102      Ico_V128   /* 128-bit restricted vector constant, with 1 bit for
103                    each of 16 byte lanes */
104   }
105   IRConstTag;
106
107typedef
108   struct _IRConst {
109      IRConstTag tag;
110      union {
111         Bool   U1;
112         UChar  U8;
113         UShort U16;
114         UInt   U32;
115         ULong  U64;
116         Double F64;
117         ULong  F64i;
118         UShort V128;
119      } Ico;
120   }
121   IRConst;
122
123extern IRConst* IRConst_U1   ( Bool );
124extern IRConst* IRConst_U8   ( UChar );
125extern IRConst* IRConst_U16  ( UShort );
126extern IRConst* IRConst_U32  ( UInt );
127extern IRConst* IRConst_U64  ( ULong );
128extern IRConst* IRConst_F64  ( Double );
129extern IRConst* IRConst_F64i ( ULong );
130extern IRConst* IRConst_V128 ( UShort );
131
132extern IRConst* dopyIRConst ( IRConst* );
133
134extern void ppIRConst ( IRConst* );
135extern Bool eqIRConst ( IRConst*, IRConst* );
136
137
138/* ------------------ Call targets ------------------ */
139
140/* Describes a helper function to call.  The name part is purely for
141   pretty printing and not actually used.  regparms=n tells the back
142   end that the callee has been declared
143   "__attribute__((regparm(n)))".  On some targets (x86) the back end
144   will need to construct a non-standard sequence to call a function
145   declared like this.
146
147   mcx_mask is a sop to Memcheck.  It indicates which args should be
148   considered 'always defined' when lazily computing definedness of
149   the result.  Bit 0 of mcx_mask corresponds to args[0], bit 1 to
150   args[1], etc.  If a bit is set, the corresponding arg is excluded
151   (hence "x" in "mcx") from definedness checking.
152*/
153
154typedef
155   struct {
156      Int    regparms;
157      HChar* name;
158      void*  addr;
159      UInt   mcx_mask;
160   }
161   IRCallee;
162
163extern IRCallee* mkIRCallee ( Int regparms, HChar* name, void* addr );
164
165extern IRCallee* dopyIRCallee ( IRCallee* );
166
167extern void ppIRCallee ( IRCallee* );
168
169
170/* ------------------ Guest state arrays ------------------ */
171
172typedef
173   struct {
174      Int    base;
175      IRType elemTy;
176      Int    nElems;
177   }
178   IRArray;
179
180extern IRArray* mkIRArray ( Int, IRType, Int );
181
182extern IRArray* dopyIRArray ( IRArray* );
183
184extern void ppIRArray ( IRArray* );
185extern Bool eqIRArray ( IRArray*, IRArray* );
186
187
188/* ------------------ Temporaries ------------------ */
189
190/* The IR optimiser relies on the fact that IRTemps are 32-bit
191   ints.  Do not change them to be ints of any other size. */
192typedef UInt IRTemp;
193
194extern void ppIRTemp ( IRTemp );
195
196#define IRTemp_INVALID ((IRTemp)0xFFFFFFFF)
197
198
199/* ------------------ Binary and unary ops ------------------ */
200
201typedef
202   enum {
203      /* Do not change this ordering.  The IR generators
204         rely on (eg) Iop_Add64 == IopAdd8 + 3. */
205      Iop_INVALID=0x13000,
206      Iop_Add8,  Iop_Add16,  Iop_Add32,  Iop_Add64,
207      Iop_Sub8,  Iop_Sub16,  Iop_Sub32,  Iop_Sub64,
208      /* Signless mul.  MullS/MullU is elsewhere. */
209      Iop_Mul8,  Iop_Mul16,  Iop_Mul32,  Iop_Mul64,
210      Iop_Or8,   Iop_Or16,   Iop_Or32,   Iop_Or64,
211      Iop_And8,  Iop_And16,  Iop_And32,  Iop_And64,
212      Iop_Xor8,  Iop_Xor16,  Iop_Xor32,  Iop_Xor64,
213      Iop_Shl8,  Iop_Shl16,  Iop_Shl32,  Iop_Shl64,
214      Iop_Shr8,  Iop_Shr16,  Iop_Shr32,  Iop_Shr64,
215      Iop_Sar8,  Iop_Sar16,  Iop_Sar32,  Iop_Sar64,
216      /* Integer comparisons. */
217      Iop_CmpEQ8,  Iop_CmpEQ16,  Iop_CmpEQ32,  Iop_CmpEQ64,
218      Iop_CmpNE8,  Iop_CmpNE16,  Iop_CmpNE32,  Iop_CmpNE64,
219      /* Tags for unary ops */
220      Iop_Not8,  Iop_Not16,  Iop_Not32,  Iop_Not64,
221      /* Widening multiplies */
222      Iop_MullS8, Iop_MullS16, Iop_MullS32, Iop_MullS64,
223      Iop_MullU8, Iop_MullU16, Iop_MullU32, Iop_MullU64,
224
225      /* Wierdo integer stuff */
226      Iop_Clz32,   /* count leading zeroes */
227      Iop_Ctz32,   /* count trailing zeros */
228      /* Ctz32/Clz32 are UNDEFINED when given arguments of zero.
229         You must ensure they are never given a zero argument.
230      */
231
232      /* Ordering not important after here. */
233      Iop_CmpLT32S,
234      Iop_CmpLE32S,
235      Iop_CmpLT32U,
236      Iop_CmpLE32U,
237
238      /* Division */
239      /* TODO: clarify semantics wrt rounding, negative values, whatever */
240      Iop_DivU32,   // :: I32,I32 -> I32 (simple div, no mod)
241      Iop_DivS32,   // ditto, signed
242
243      Iop_DivModU64to32, // :: I64,I32 -> I64
244                         // of which lo half is div and hi half is mod
245      Iop_DivModS64to32, // ditto, signed
246
247      Iop_DivModU128to64, // :: V128,I64 -> V128
248                          // of which lo half is div and hi half is mod
249      Iop_DivModS128to64, // ditto, signed
250
251      /* Widening conversions */
252      Iop_8Uto16, Iop_8Uto32, Iop_16Uto32, Iop_32Uto64,
253      Iop_8Sto16, Iop_8Sto32, Iop_16Sto32, Iop_32Sto64,
254      /* Narrowing conversions */
255      Iop_32to8,
256      /* 8 <-> 16 bit conversions */
257      Iop_16to8,      // :: I16 -> I8, low half
258      Iop_16HIto8,    // :: I16 -> I8, high half
259      Iop_8HLto16,    // :: (I8,I8) -> I16
260      /* 16 <-> 32 bit conversions */
261      Iop_32to16,     // :: I32 -> I16, low half
262      Iop_32HIto16,   // :: I32 -> I16, high half
263      Iop_16HLto32,   // :: (I16,I16) -> I32
264      /* 32 <-> 64 bit conversions */
265      Iop_64to32,     // :: I64 -> I32, low half
266      Iop_64HIto32,   // :: I64 -> I32, high half
267      Iop_32HLto64,   // :: (I32,I32) -> I64
268      /* 64 <-> 128 bit conversions */
269      Iop_128to64,    // :: I128 -> I64, low half
270      Iop_128HIto64,  // :: I128 -> I64, high half
271      Iop_64HLto128,  // :: (I64,I64) -> I128
272      /* 1-bit stuff */
273      Iop_Not1,   /* :: Ity_Bit -> Ity_Bit */
274      Iop_32to1,  /* :: Ity_I32 -> Ity_Bit, just select bit[0] */
275      Iop_1Uto8,  /* :: Ity_Bit -> Ity_I8, unsigned widen */
276      Iop_1Uto32, /* :: Ity_Bit -> Ity_I32, unsigned widen */
277      Iop_1Sto8,  /* :: Ity_Bit -> Ity_I8,  signed widen */
278      Iop_1Sto16, /* :: Ity_Bit -> Ity_I16, signed widen */
279      Iop_1Sto32, /* :: Ity_Bit -> Ity_I32, signed widen */
280      Iop_1Sto64, /* :: Ity_Bit -> Ity_I64, signed widen */
281
282      /* ------ Floating point.  We try and be IEEE754 compliant. ------ */
283
284      /* Binary operations mandated by IEEE754. */
285      Iop_AddF64, Iop_SubF64, Iop_MulF64, Iop_DivF64, /* Iop_RemF64, */
286
287      /* Binary ops supported by IA32 but not mandated by 754. */
288      Iop_AtanF64,       /* FPATAN,  arctan(arg1/arg2)       */
289      Iop_Yl2xF64,       /* FYL2X,   arg1 * log2(arg2)       */
290      Iop_Yl2xp1F64,     /* FYL2XP1, arg1 * log2(arg2+1.0)   */
291      Iop_PRemF64,       /* FPREM,   non-IEEE remainder(arg1/arg2)    */
292      Iop_PRemC3210F64,  /* C3210 flags resulting from FPREM, :: I32 */
293      Iop_PRem1F64,      /* FPREM1,  IEEE remainder(arg1/arg2)    */
294      Iop_PRem1C3210F64, /* C3210 flags resulting from FPREM1, :: I32 */
295      Iop_ScaleF64,      /* FSCALE,  arg1 * (2^RoundTowardsZero(arg2)) */
296      /* Note that on x86 guest, PRem1{C3210} has the same behaviour
297         as the IEEE mandated RemF64, except it is limited in the
298         range of its operand.  Hence the partialness. */
299
300      /* Unary operations mandated by IEEE754. */
301      Iop_NegF64, Iop_SqrtF64,
302
303      /* Unary ops supported by IA32 but not mandated by 754. */
304      Iop_AbsF64,    /* FABS */
305      Iop_SinF64,    /* FSIN */
306      Iop_CosF64,    /* FCOS */
307      Iop_TanF64,    /* FTAN */
308      Iop_2xm1F64,   /* (2^arg - 1.0) */
309
310      /* Comparison, yielding GT/LT/EQ/UN(ordered), as per the following:
311            0x45 Unordered
312            0x01 LT
313            0x00 GT
314            0x40 EQ
315         This just happens to be the Intel encoding.  The values
316         are recorded in the type IRCmpF64Result.
317      */
318      Iop_CmpF64,
319
320      /* --- Int to/from FP conversions. --- */
321      /* For the most part, these take a first argument :: Ity_I32
322         (as IRRoundingMode) which is an indication of the rounding
323         mode to use, as per the following encoding:
324            00b  to nearest (the default)
325            01b  to -infinity
326            10b  to +infinity
327            11b  to zero
328         This just happens to be the Intel encoding.  For reference only,
329         the PPC encoding is:
330            00b  to nearest (the default)
331            01b  to zero
332            10b  to +infinity
333            11b  to -infinity
334         Any PPC -> IR front end will have to translate these PPC
335         encodings to the standard encodings.
336
337         If one of these conversions gets an out-of-range condition,
338         or a NaN, as an argument, the result is host-defined.  On x86
339         the "integer indefinite" value 0x80..00 is produced.
340         On PPC it is either 0x80..00 or 0x7F..FF depending on the sign
341         of the argument.
342
343         Rounding is required whenever the destination type cannot
344         represent exactly all values of the source type.
345      */
346      Iop_F64toI16,  /* IRRoundingMode(I32) x F64 -> I16 */
347      Iop_F64toI32,  /* IRRoundingMode(I32) x F64 -> I32 */
348      Iop_F64toI64,  /* IRRoundingMode(I32) x F64 -> I64 */
349
350      Iop_I16toF64,  /*                       I16 -> F64 */
351      Iop_I32toF64,  /*                       I32 -> F64 */
352      Iop_I64toF64,  /* IRRoundingMode(I32) x I64 -> F64 */
353
354      Iop_F32toF64,  /*                       F32 -> F64 */
355      Iop_F64toF32,  /* IRRoundingMode(I32) x F64 -> F32 */
356
357      /* F64 -> F64, also takes an I32 first argument encoding the
358         rounding mode. */
359      Iop_RoundF64,
360
361      /* Reinterpretation.  Take an F64 and produce an I64 with
362         the same bit pattern, or vice versa. */
363      Iop_ReinterpF64asI64, Iop_ReinterpI64asF64,
364      Iop_ReinterpF32asI32, Iop_ReinterpI32asF32,
365
366      /* ------------------ 64-bit SIMD Integer. ------------------ */
367
368      /* MISC (vector integer cmp != 0) */
369      Iop_CmpNEZ8x8, Iop_CmpNEZ16x4, Iop_CmpNEZ32x2,
370
371      /* ADDITION (normal / unsigned sat / signed sat) */
372      Iop_Add8x8,   Iop_Add16x4,   Iop_Add32x2,
373      Iop_QAdd8Ux8, Iop_QAdd16Ux4,
374      Iop_QAdd8Sx8, Iop_QAdd16Sx4,
375
376      /* SUBTRACTION (normal / unsigned sat / signed sat) */
377      Iop_Sub8x8,   Iop_Sub16x4,   Iop_Sub32x2,
378      Iop_QSub8Ux8, Iop_QSub16Ux4,
379      Iop_QSub8Sx8, Iop_QSub16Sx4,
380
381      /* MULTIPLICATION (normal / high half of signed/unsigned) */
382      Iop_Mul16x4,
383      Iop_MulHi16Ux4,
384      Iop_MulHi16Sx4,
385
386      /* AVERAGING: note: (arg1 + arg2 + 1) >> 1 */
387      Iop_Avg8Ux8,
388      Iop_Avg16Ux4,
389
390      /* MIN/MAX */
391      Iop_Max16Sx4,
392      Iop_Max8Ux8,
393      Iop_Min16Sx4,
394      Iop_Min8Ux8,
395
396      /* COMPARISON */
397      Iop_CmpEQ8x8,  Iop_CmpEQ16x4,  Iop_CmpEQ32x2,
398      Iop_CmpGT8Sx8, Iop_CmpGT16Sx4, Iop_CmpGT32Sx2,
399
400      /* VECTOR x SCALAR SHIFT (shift amt :: Ity_I8) */
401      Iop_ShlN16x4, Iop_ShlN32x2,
402      Iop_ShrN16x4, Iop_ShrN32x2,
403      Iop_SarN16x4, Iop_SarN32x2,
404
405      /* NARROWING -- narrow 2xI64 into 1xI64, hi half from left arg */
406      Iop_QNarrow16Ux4,
407      Iop_QNarrow16Sx4,
408      Iop_QNarrow32Sx2,
409
410      /* INTERLEAVING -- interleave lanes from low or high halves of
411         operands.  Most-significant result lane is from the left
412         arg. */
413      Iop_InterleaveHI8x8, Iop_InterleaveHI16x4, Iop_InterleaveHI32x2,
414      Iop_InterleaveLO8x8, Iop_InterleaveLO16x4, Iop_InterleaveLO32x2,
415
416      /* ------------------ 128-bit SIMD FP. ------------------ */
417
418      /* --- 32x4 vector FP --- */
419
420      /* binary */
421      Iop_Add32Fx4, Iop_Sub32Fx4, Iop_Mul32Fx4, Iop_Div32Fx4,
422      Iop_Max32Fx4, Iop_Min32Fx4,
423      Iop_CmpEQ32Fx4, Iop_CmpLT32Fx4, Iop_CmpLE32Fx4, Iop_CmpUN32Fx4,
424
425      /* unary */
426      Iop_Recip32Fx4, Iop_Sqrt32Fx4, Iop_RSqrt32Fx4,
427
428      /* --- 32x4 lowest-lane-only scalar FP --- */
429
430      /* In binary cases, upper 3/4 is copied from first operand.  In
431         unary cases, upper 3/4 is copied from the operand. */
432
433      /* binary */
434      Iop_Add32F0x4, Iop_Sub32F0x4, Iop_Mul32F0x4, Iop_Div32F0x4,
435      Iop_Max32F0x4, Iop_Min32F0x4,
436      Iop_CmpEQ32F0x4, Iop_CmpLT32F0x4, Iop_CmpLE32F0x4, Iop_CmpUN32F0x4,
437
438      /* unary */
439      Iop_Recip32F0x4, Iop_Sqrt32F0x4, Iop_RSqrt32F0x4,
440
441      /* --- 64x2 vector FP --- */
442
443      /* binary */
444      Iop_Add64Fx2, Iop_Sub64Fx2, Iop_Mul64Fx2, Iop_Div64Fx2,
445      Iop_Max64Fx2, Iop_Min64Fx2,
446      Iop_CmpEQ64Fx2, Iop_CmpLT64Fx2, Iop_CmpLE64Fx2, Iop_CmpUN64Fx2,
447
448      /* unary */
449      Iop_Recip64Fx2, Iop_Sqrt64Fx2, Iop_RSqrt64Fx2,
450
451      /* --- 64x2 lowest-lane-only scalar FP --- */
452
453      /* In binary cases, upper half is copied from first operand.  In
454         unary cases, upper half is copied from the operand. */
455
456      /* binary */
457      Iop_Add64F0x2, Iop_Sub64F0x2, Iop_Mul64F0x2, Iop_Div64F0x2,
458      Iop_Max64F0x2, Iop_Min64F0x2,
459      Iop_CmpEQ64F0x2, Iop_CmpLT64F0x2, Iop_CmpLE64F0x2, Iop_CmpUN64F0x2,
460
461      /* unary */
462      Iop_Recip64F0x2, Iop_Sqrt64F0x2, Iop_RSqrt64F0x2,
463
464      /* --- pack / unpack --- */
465
466      /* 64 <-> 128 bit vector */
467      Iop_V128to64,     // :: V128 -> I64, low half
468      Iop_V128HIto64,   // :: V128 -> I64, high half
469      Iop_64HLtoV128,   // :: (I64,I64) -> V128
470
471      Iop_64UtoV128,
472      Iop_SetV128lo64,
473
474      /* 32 <-> 128 bit vector */
475      Iop_32UtoV128,
476      Iop_V128to32,     // :: V128 -> I32, lowest lane
477      Iop_SetV128lo32,  // :: (V128,I32) -> V128
478
479      /* ------------------ 128-bit SIMD Integer. ------------------ */
480
481      /* BITWISE OPS */
482      Iop_NotV128,
483      Iop_AndV128, Iop_OrV128, Iop_XorV128,
484
485      /* MISC (vector integer cmp != 0) */
486      Iop_CmpNEZ8x16, Iop_CmpNEZ16x8, Iop_CmpNEZ32x4, Iop_CmpNEZ64x2,
487
488      /* ADDITION (normal / unsigned sat / signed sat) */
489      Iop_Add8x16,   Iop_Add16x8,   Iop_Add32x4,  Iop_Add64x2,
490      Iop_QAdd8Ux16, Iop_QAdd16Ux8,
491      Iop_QAdd8Sx16, Iop_QAdd16Sx8,
492
493      /* SUBTRACTION (normal / unsigned sat / signed sat) */
494      Iop_Sub8x16,   Iop_Sub16x8,   Iop_Sub32x4,  Iop_Sub64x2,
495      Iop_QSub8Ux16, Iop_QSub16Ux8,
496      Iop_QSub8Sx16, Iop_QSub16Sx8,
497
498      /* MULTIPLICATION (normal / high half of signed/unsigned) */
499      Iop_Mul16x8,
500      Iop_MulHi16Ux8,
501      Iop_MulHi16Sx8,
502
503      /* AVERAGING: note: (arg1 + arg2 + 1) >> 1 */
504      Iop_Avg8Ux16,
505      Iop_Avg16Ux8,
506
507      /* MIN/MAX */
508      Iop_Max16Sx8,
509      Iop_Max8Ux16,
510      Iop_Min16Sx8,
511      Iop_Min8Ux16,
512
513      /* COMPARISON */
514      Iop_CmpEQ8x16,  Iop_CmpEQ16x8,  Iop_CmpEQ32x4,
515      Iop_CmpGT8Sx16, Iop_CmpGT16Sx8, Iop_CmpGT32Sx4,
516
517      /* VECTOR x SCALAR SHIFT (shift amt :: Ity_I8) */
518      Iop_ShlN16x8, Iop_ShlN32x4, Iop_ShlN64x2,
519      Iop_ShrN16x8, Iop_ShrN32x4, Iop_ShrN64x2,
520      Iop_SarN16x8, Iop_SarN32x4,
521
522      /* NARROWING -- narrow 2xV128 into 1xV128, hi half from left arg */
523      Iop_QNarrow16Ux8,
524      Iop_QNarrow16Sx8,
525      Iop_QNarrow32Sx4,
526
527      /* INTERLEAVING -- interleave lanes from low or high halves of
528         operands.  Most-significant result lane is from the left
529         arg. */
530      Iop_InterleaveHI8x16, Iop_InterleaveHI16x8,
531      Iop_InterleaveHI32x4, Iop_InterleaveHI64x2,
532      Iop_InterleaveLO8x16, Iop_InterleaveLO16x8,
533      Iop_InterleaveLO32x4, Iop_InterleaveLO64x2
534   }
535   IROp;
536
537extern void ppIROp ( IROp );
538
539
540/* Encoding of IEEE754-specified rounding modes in Float -> Int
541   conversions.  This is the same as the encoding used by Intel IA32
542   to indicate x87 rounding mode. */
543typedef
544   enum { Irrm_NEAREST=0, Irrm_NegINF=1, Irrm_PosINF=2, Irrm_ZERO=3 }
545   IRRoundingMode;
546
547/* Floating point comparison result values, as created by Iop_CmpF64.
548   This is also derived from what IA32 does. */
549typedef
550   enum {
551      Ircr_UN = 0x45,
552      Ircr_LT = 0x01,
553      Ircr_GT = 0x00,
554      Ircr_EQ = 0x40
555   }
556   IRCmpF64Result;
557
558
559/* ------------------ Expressions ------------------ */
560/*
561   Some details of expression semantics:
562
563   IRExpr_GetI (also IRStmt_PutI)
564   ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
565   This carries two ints, which give the lowest and highest possible
566   byte offsets that the GetI can possibly reference.  For example, if
567   the type is Ity_I32, and the Expr may have a value of M, M+4 or
568   M+8, where M is a translation-time known constant, then the low and
569   high limits are M and M+11 respectively.
570
571   PutI's limit values are interpreted identically.
572
573   The limit values are used by IR optimisers to establish
574   aliasing/non-aliasing between seperate GetI and PutI events, which
575   could be used to do reordering of them, or suchlike things.
576   Clearly it's critical to give the correct limit values -- this is
577   something that can't be automatically checked (in general), and so
578   the front-end writers must be very careful to tell the truth, since
579   not doing so could lead to obscure IR optimisation bugs.
580
581   IRExpr_CCall
582   ~~~~~~~~~~~~
583   The name is the C helper function; the backends will call back to
584   the front ends to get the address of a host-code helper function to
585   be called.
586
587   The args are a NULL-terminated array of arguments.  The stated
588   return IRType, and the implied argument types, must match that of
589   the function being called well enough so that the back end can
590   actually generate correct code for the call.
591
592   The called function **must** satisfy the following:
593
594   * no side effects -- must be a pure function, the result of which
595     depends only on the passed parameters.
596
597   * it may not look at, nor modify, any of the guest state since that
598     would hide guest state transitions from instrumenters
599
600   * it may not access guest memory, since that would hide guest
601     memory transactions from the instrumenters
602
603   This is restrictive, but makes the semantics clean, and does
604   not interfere with IR optimisation.
605
606   If you want to call a helper which can mess with guest state and/or
607   memory, instead use IRStmt_Dirty.  This is a lot more flexible, but
608   you pay for that flexibility in that you have to give a bunch of
609   details about what the helper does (and you better be telling the
610   truth, otherwise any derived instrumentation will be wrong).  Also
611   IRStmt_Dirty inhibits various IR optimisations and so can cause
612   quite poor code to be generated.  Try to avoid it.
613*/
614
615/* The possible kinds of expressions are as follows: */
616typedef
617   enum {
618      Iex_Binder,  /* Used only in pattern matching.
619                      Not an expression. */
620      Iex_Get,     /* read guest state, fixed offset */
621      Iex_GetI,    /* read guest state, run-time offset */
622      Iex_Tmp,     /* value of temporary */
623      Iex_Binop,   /* binary operation */
624      Iex_Unop,    /* unary operation */
625      Iex_LDle,    /* little-endian read from memory */
626      Iex_Const,   /* constant-valued expression */
627      Iex_Mux0X,   /* ternary if-then-else operator (STRICT) */
628      Iex_CCall    /* call to pure (side-effect-free) helper fn */
629   }
630   IRExprTag;
631
632typedef
633   struct _IRExpr {
634      IRExprTag tag;
635      union {
636         struct {
637            Int binder;
638         } Binder;
639         struct {
640            Int    offset;
641            IRType ty;
642         } Get;
643         struct {
644            IRArray* descr;
645            struct _IRExpr* ix;
646            Int bias;
647         } GetI;
648         struct {
649            IRTemp tmp;
650         } Tmp;
651         struct {
652            IROp op;
653            struct _IRExpr* arg1;
654            struct _IRExpr* arg2;
655         } Binop;
656         struct {
657            IROp op;
658            struct _IRExpr* arg;
659         } Unop;
660         struct {
661            IRType ty;
662            struct _IRExpr* addr;
663         } LDle;
664         struct {
665            IRConst* con;
666         } Const;
667         struct {
668            IRCallee* cee;
669            IRType    retty;
670            struct _IRExpr** args;
671         }  CCall;
672         struct {
673            struct _IRExpr* cond;
674            struct _IRExpr* expr0;
675            struct _IRExpr* exprX;
676         } Mux0X;
677      } Iex;
678   }
679   IRExpr;
680
681extern IRExpr* IRExpr_Binder ( Int binder );
682extern IRExpr* IRExpr_Get    ( Int off, IRType ty );
683extern IRExpr* IRExpr_GetI   ( IRArray* descr, IRExpr* ix, Int bias );
684extern IRExpr* IRExpr_Tmp    ( IRTemp tmp );
685extern IRExpr* IRExpr_Binop  ( IROp op, IRExpr* arg1, IRExpr* arg2 );
686extern IRExpr* IRExpr_Unop   ( IROp op, IRExpr* arg );
687extern IRExpr* IRExpr_LDle   ( IRType ty, IRExpr* addr );
688extern IRExpr* IRExpr_Const  ( IRConst* con );
689extern IRExpr* IRExpr_CCall  ( IRCallee* cee, IRType retty, IRExpr** args );
690extern IRExpr* IRExpr_Mux0X  ( IRExpr* cond, IRExpr* expr0, IRExpr* exprX );
691
692extern IRExpr* dopyIRExpr ( IRExpr* );
693
694extern void ppIRExpr ( IRExpr* );
695
696/* NULL-terminated IRExpr expression vectors, suitable for use as arg
697   lists in clean/dirty helper calls. */
698
699extern IRExpr** mkIRExprVec_0 ( void );
700extern IRExpr** mkIRExprVec_1 ( IRExpr* );
701extern IRExpr** mkIRExprVec_2 ( IRExpr*, IRExpr* );
702extern IRExpr** mkIRExprVec_3 ( IRExpr*, IRExpr*, IRExpr* );
703extern IRExpr** mkIRExprVec_4 ( IRExpr*, IRExpr*, IRExpr*, IRExpr* );
704extern IRExpr** mkIRExprVec_5 ( IRExpr*, IRExpr*,
705                                IRExpr*, IRExpr*, IRExpr* );
706
707extern IRExpr** sopyIRExprVec ( IRExpr** );
708extern IRExpr** dopyIRExprVec ( IRExpr** );
709
710/* Make a constant expression from the given host word taking into
711   account of course the host word size. */
712extern IRExpr* mkIRExpr_HWord ( HWord );
713
714/* Convenience function for constructing clean helper calls. */
715extern
716IRExpr* mkIRExprCCall ( IRType retty,
717                        Int regparms, HChar* name, void* addr,
718                        IRExpr** args );
719
720
721/* Convenience functions for atoms, that is, IRExprs which
722   are either Iex_Tmp or Iex_Const. */
723static inline Bool isIRAtom ( IRExpr* e ) {
724   return toBool(e->tag == Iex_Tmp || e->tag == Iex_Const);
725}
726
727/* Are these two IR atoms identical?  Causes an assertion
728   failure if they are passed non-atoms. */
729extern Bool eqIRAtom ( IRExpr*, IRExpr* );
730
731
732/* ------------------ Jump kinds ------------------ */
733
734/* This describes hints which can be passed to the dispatcher at guest
735   control-flow transfer points.
736
737   Re Ijk_Invalidate: typically the guest state will have two
738   pseudo-registers, guest_TISTART and guest_TILEN, which
739   specify the start and length of the region to be invalidated.
740   It is the responsibility of the relevant toIR.c to ensure that
741   these are filled in with suitable values before issuing a jump
742   of kind Ijk_TInval.
743*/
744typedef
745   enum {
746      Ijk_Boring=0x14000, /* not interesting; just goto next */
747      Ijk_Call,           /* guest is doing a call */
748      Ijk_Ret,            /* guest is doing a return */
749      Ijk_ClientReq,      /* do guest client req before continuing */
750      Ijk_Syscall,        /* do guest syscall before continuing */
751      Ijk_Yield,          /* client is yielding to thread scheduler */
752      Ijk_EmWarn,         /* report emulation warning before continuing */
753      Ijk_NoDecode,       /* next instruction cannot be decoded */
754      Ijk_MapFail,        /* Vex-provided address translation failed */
755      Ijk_TInval          /* Invalidate translations before continuing. */
756   }
757   IRJumpKind;
758
759extern void ppIRJumpKind ( IRJumpKind );
760
761
762/* ------------------ Dirty helper calls ------------------ */
763
764/* A dirty call is a flexible mechanism for calling a helper function
765   or procedure.  The helper function may read, write or modify client
766   memory, and may read, write or modify client state.  It can take
767   arguments and optionally return a value.  It may return different
768   results and/or do different things when called repeated with the
769   same arguments, by means of storing private state.
770
771   If a value is returned, it is assigned to the nominated return
772   temporary.
773
774   Dirty calls are statements rather than expressions for obvious
775   reasons.  If a dirty call is stated as writing guest state, any
776   values derived from the written parts of the guest state are
777   invalid.  Similarly, if the dirty call is stated as writing
778   memory, any loaded values are invalidated by it.
779
780   In order that instrumentation is possible, the call must state, and
781   state correctly
782
783   * whether it reads, writes or modifies memory, and if so where
784     (only one chunk can be stated)
785
786   * whether it reads, writes or modifies guest state, and if so which
787     pieces (several pieces may be stated, and currently their extents
788     must be known at translation-time).
789
790   Normally, code is generated to pass just the args to the helper.
791   However, if .needsBBP is set, then an extra first argument is
792   passed, which is the baseblock pointer, so that the callee can
793   access the guest state.  It is invalid for .nFxState to be zero
794   but .needsBBP to be True, since .nFxState==0 is a claim that the
795   call does not access guest state.
796
797   IMPORTANT NOTE re GUARDS: Dirty calls are strict, very strict.  The
798   arguments are evaluated REGARDLESS of the guard value.  It is
799   unspecified the relative order of arg evaluation and guard
800   evaluation.
801*/
802
803#define VEX_N_FXSTATE  7   /* enough for FXSAVE/FXRSTOR on x86 */
804
805typedef
806   enum {
807      Ifx_None = 0x15000,   /* no effect */
808      Ifx_Read,             /* reads the resource */
809      Ifx_Write,            /* writes the resource */
810      Ifx_Modify,           /* modifies the resource */
811   }
812   IREffect;
813
814extern void ppIREffect ( IREffect );
815
816
817typedef
818   struct {
819      /* What to call, and details of args/results */
820      IRCallee* cee;    /* where to call */
821      IRExpr*   guard;  /* :: Ity_Bit.  Controls whether call happens */
822      IRExpr**  args;   /* arg list, ends in NULL */
823      IRTemp    tmp;    /* to assign result to, or IRTemp_INVALID if none */
824
825      /* Mem effects; we allow only one R/W/M region to be stated */
826      IREffect  mFx;    /* indicates memory effects, if any */
827      IRExpr*   mAddr;  /* of access, or NULL if mFx==Ifx_None */
828      Int       mSize;  /* of access, or zero if mFx==Ifx_None */
829
830      /* Guest state effects; up to N allowed */
831      Bool needsBBP; /* True => also pass guest state ptr to callee */
832      Int  nFxState; /* must be 0 .. VEX_N_FXSTATE */
833      struct {
834         IREffect fx;   /* read, write or modify?  Ifx_None is invalid. */
835         Int      offset;
836         Int      size;
837      } fxState[VEX_N_FXSTATE];
838   }
839   IRDirty;
840
841extern void     ppIRDirty ( IRDirty* );
842extern IRDirty* emptyIRDirty ( void );
843
844extern IRDirty* dopyIRDirty ( IRDirty* );
845
846/* A handy function which takes some of the tedium out of constructing
847   dirty helper calls.  The called function impliedly does not return
848   any value and has a constant-True guard.  The call is marked as
849   accessing neither guest state nor memory (hence the "unsafe"
850   designation) -- you can mess with this later if need be.  A
851   suitable IRCallee is constructed from the supplied bits. */
852extern
853IRDirty* unsafeIRDirty_0_N ( Int regparms, HChar* name, void* addr,
854                             IRExpr** args );
855
856/* Similarly, make a zero-annotation dirty call which returns a value,
857   and assign that to the given temp. */
858extern
859IRDirty* unsafeIRDirty_1_N ( IRTemp dst,
860                             Int regparms, HChar* name, void* addr,
861                             IRExpr** args );
862
863
864/* ------------------ Statements ------------------ */
865
866/* The possible kinds of statements are as follows: */
867typedef
868   enum {
869      Ist_IMark,  /* instruction mark: describe addr/len of guest insn
870                     whose IR follows */
871      Ist_Put,    /* write guest state, fixed offset */
872      Ist_PutI,   /* write guest state, run-time offset */
873      Ist_Tmp,    /* assign value to temporary */
874      Ist_STle,   /* little-endian write to memory */
875      Ist_Dirty,  /* call complex ("dirty") helper function */
876      Ist_MFence, /* memory fence */
877      Ist_Exit    /* conditional exit from BB */
878   }
879   IRStmtTag;
880
881typedef
882   struct _IRStmt {
883      IRStmtTag tag;
884      union {
885         struct {
886            Addr64 addr;
887            Int    len;
888         } IMark;
889         struct {
890            Int     offset;
891            IRExpr* data;
892         } Put;
893         struct {
894            IRArray* descr;
895            IRExpr*  ix;
896            Int      bias;
897            IRExpr*  data;
898         } PutI;
899         struct {
900            IRTemp  tmp;
901            IRExpr* data;
902         } Tmp;
903         struct {
904            IRExpr* addr;
905            IRExpr* data;
906         } STle;
907         struct {
908            IRDirty* details;
909         } Dirty;
910         struct {
911         } MFence;
912         struct {
913            IRExpr*    guard;
914            IRJumpKind jk;
915            IRConst*   dst;
916         } Exit;
917      } Ist;
918   }
919   IRStmt;
920
921extern IRStmt* IRStmt_IMark  ( Addr64 addr, Int len );
922extern IRStmt* IRStmt_Put    ( Int off, IRExpr* data );
923extern IRStmt* IRStmt_PutI   ( IRArray* descr, IRExpr* ix, Int bias,
924                               IRExpr* data );
925extern IRStmt* IRStmt_Tmp    ( IRTemp tmp, IRExpr* data );
926extern IRStmt* IRStmt_STle   ( IRExpr* addr, IRExpr* data );
927extern IRStmt* IRStmt_Dirty  ( IRDirty* details );
928extern IRStmt* IRStmt_MFence ( void );
929extern IRStmt* IRStmt_Exit   ( IRExpr* guard, IRJumpKind jk, IRConst* dst );
930
931extern IRStmt* dopyIRStmt ( IRStmt* );
932
933extern void ppIRStmt ( IRStmt* );
934
935
936/* ------------------ Basic Blocks ------------------ */
937
938/* A bunch of statements, expressions, etc, are incomplete without an
939   environment indicating the type of each IRTemp.  So this provides
940   one.  IR temporaries are really just unsigned ints and so this
941   provides an array, 0 .. n_types_used-1 of them.
942*/
943typedef
944   struct {
945      IRType* types;
946      Int     types_size;
947      Int     types_used;
948   }
949   IRTypeEnv;
950
951extern IRTemp     newIRTemp     ( IRTypeEnv*, IRType );
952extern IRTypeEnv* dopyIRTypeEnv ( IRTypeEnv* );
953
954extern void ppIRTypeEnv ( IRTypeEnv* );
955
956
957/* Basic blocks contain:
958   - A table giving a type for each temp
959   - An expandable array of statements
960   - An expression of type 32 or 64 bits, depending on the
961     guest's word size, indicating the next destination.
962   - An indication of any special actions (JumpKind) needed
963     for this final jump.
964*/
965typedef
966   struct _IRBB {
967      IRTypeEnv* tyenv;
968      IRStmt**   stmts;
969      Int        stmts_size;
970      Int        stmts_used;
971      IRExpr*    next;
972      IRJumpKind jumpkind;
973   }
974   IRBB;
975
976extern IRBB* emptyIRBB ( void );
977
978extern IRBB* dopyIRBB ( IRBB* );
979
980extern void ppIRBB ( IRBB* );
981
982extern void addStmtToIRBB ( IRBB*, IRStmt* );
983
984
985/*---------------------------------------------------------------*/
986/*--- Helper functions for the IR                             ---*/
987/*---------------------------------------------------------------*/
988
989/* For messing with IR type environments */
990extern IRTypeEnv* emptyIRTypeEnv  ( void );
991
992/* What is the type of this expression? */
993extern IRType typeOfIRConst ( IRConst* );
994extern IRType typeOfIRTemp  ( IRTypeEnv*, IRTemp );
995extern IRType typeOfIRExpr  ( IRTypeEnv*, IRExpr* );
996
997/* Sanity check a BB of IR */
998extern void sanityCheckIRBB ( IRBB*  bb,
999                              HChar* caller,
1000                              Bool   require_flatness,
1001                              IRType guest_word_size );
1002extern Bool isFlatIRStmt ( IRStmt* );
1003
1004/* Is this any value actually in the enumeration 'IRType' ? */
1005extern Bool isPlausibleIRType ( IRType ty );
1006
1007#endif /* ndef __LIBVEX_IR_H */
1008
1009
1010/*---------------------------------------------------------------*/
1011/*---                                             libvex_ir.h ---*/
1012/*---------------------------------------------------------------*/
1013