drd/tests/tsan_thread_wrappers_pthread.h: Fix MyThread::ThreadBody()
[valgrind.git] / VEX / priv / host_mips_defs.h
blob494ba4ea218144d77252843b2b71c527d2d68fa4
2 /*---------------------------------------------------------------*/
3 /*--- begin host_mips_defs.h ---*/
4 /*---------------------------------------------------------------*/
6 /*
7 This file is part of Valgrind, a dynamic binary instrumentation
8 framework.
10 Copyright (C) 2010-2017 RT-RK
11 mips-valgrind@rt-rk.com
13 This program is free software; you can redistribute it and/or
14 modify it under the terms of the GNU General Public License as
15 published by the Free Software Foundation; either version 2 of the
16 License, or (at your option) any later version.
18 This program is distributed in the hope that it will be useful, but
19 WITHOUT ANY WARRANTY; without even the implied warranty of
20 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
21 General Public License for more details.
23 You should have received a copy of the GNU General Public License
24 along with this program; if not, write to the Free Software
25 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
26 02111-1307, USA.
28 The GNU General Public License is contained in the file COPYING.
31 #ifndef __VEX_HOST_MIPS_DEFS_H
32 #define __VEX_HOST_MIPS_DEFS_H
34 #include "libvex_basictypes.h"
35 #include "libvex.h" /* VexArch */
36 #include "host_generic_regs.h" /* HReg */
39 /* --------- Registers. --------- */
41 #define ST_IN static inline
43 #define GPR(_mode64, _enc, _ix64, _ix32) \
44 mkHReg(False, (_mode64) ? HRcInt64 : HRcInt32, \
45 (_enc), (_mode64) ? (_ix64) : (_ix32))
47 #define FR(_mode64, _enc, _ix64, _ix32) \
48 mkHReg(False, (_mode64) ? HRcFlt64 : HRcFlt32, \
49 (_enc), (_mode64) ? (_ix64) : (_ix32))
51 #define DR(_mode64, _enc, _ix64, _ix32) \
52 mkHReg(False, HRcFlt64, \
53 (_enc), (_mode64) ? (_ix64) : (_ix32))
55 #define VEC(_mode64, _enc, _ix64, _ix32) \
56 mkHReg(False, HRcVec128, \
57 (_enc), (_mode64) ? (_ix64) : (_ix32))
59 ST_IN HReg hregMIPS_GPR16 ( Bool mode64 ) { return GPR(mode64, 16, 0, 0); }
60 ST_IN HReg hregMIPS_GPR17 ( Bool mode64 ) { return GPR(mode64, 17, 1, 1); }
61 ST_IN HReg hregMIPS_GPR18 ( Bool mode64 ) { return GPR(mode64, 18, 2, 2); }
62 ST_IN HReg hregMIPS_GPR19 ( Bool mode64 ) { return GPR(mode64, 19, 3, 3); }
63 ST_IN HReg hregMIPS_GPR20 ( Bool mode64 ) { return GPR(mode64, 20, 4, 4); }
64 ST_IN HReg hregMIPS_GPR21 ( Bool mode64 ) { return GPR(mode64, 21, 5, 5); }
65 ST_IN HReg hregMIPS_GPR22 ( Bool mode64 ) { return GPR(mode64, 22, 6, 6); }
67 ST_IN HReg hregMIPS_GPR12 ( Bool mode64 ) { return GPR(mode64, 12, 7, 7); }
68 ST_IN HReg hregMIPS_GPR13 ( Bool mode64 ) { return GPR(mode64, 13, 8, 8); }
69 ST_IN HReg hregMIPS_GPR14 ( Bool mode64 ) { return GPR(mode64, 14, 9, 9); }
70 ST_IN HReg hregMIPS_GPR15 ( Bool mode64 ) { return GPR(mode64, 15, 10, 10); }
71 ST_IN HReg hregMIPS_GPR24 ( Bool mode64 ) { return GPR(mode64, 24, 11, 11); }
73 ST_IN HReg hregMIPS_F16 ( Bool mode64 ) { return FR (mode64, 16, 12, 12); }
74 ST_IN HReg hregMIPS_F18 ( Bool mode64 ) { return FR (mode64, 18, 13, 13); }
75 ST_IN HReg hregMIPS_F20 ( Bool mode64 ) { return FR (mode64, 20, 14, 14); }
76 ST_IN HReg hregMIPS_F22 ( Bool mode64 ) { return FR (mode64, 22, 15, 15); }
77 ST_IN HReg hregMIPS_F24 ( Bool mode64 ) { return FR (mode64, 24, 16, 16); }
78 ST_IN HReg hregMIPS_F26 ( Bool mode64 ) { return FR (mode64, 26, 17, 17); }
79 ST_IN HReg hregMIPS_F28 ( Bool mode64 ) { return FR (mode64, 28, 18, 18); }
80 ST_IN HReg hregMIPS_F30 ( Bool mode64 ) { return FR (mode64, 30, 19, 19); }
82 ST_IN HReg hregMIPS_W16 ( Bool mode64 ) { return VEC(mode64, 1, 20, 20); }
83 ST_IN HReg hregMIPS_W17 ( Bool mode64 ) { return VEC(mode64, 3, 21, 21); }
84 ST_IN HReg hregMIPS_W18 ( Bool mode64 ) { return VEC(mode64, 5, 22, 22); }
85 ST_IN HReg hregMIPS_W19 ( Bool mode64 ) { return VEC(mode64, 7, 23, 23); }
86 ST_IN HReg hregMIPS_W20 ( Bool mode64 ) { return VEC(mode64, 9, 24, 24); }
87 ST_IN HReg hregMIPS_W21 ( Bool mode64 ) { return VEC(mode64, 11, 25, 25); }
88 ST_IN HReg hregMIPS_W22 ( Bool mode64 ) { return VEC(mode64, 13, 26, 26); }
89 ST_IN HReg hregMIPS_W23 ( Bool mode64 ) { return VEC(mode64, 15, 27, 27); }
90 ST_IN HReg hregMIPS_W24 ( Bool mode64 ) { return VEC(mode64, 17, 28, 28); }
91 ST_IN HReg hregMIPS_W25 ( Bool mode64 ) { return VEC(mode64, 19, 29, 29); }
92 ST_IN HReg hregMIPS_W26 ( Bool mode64 ) { return VEC(mode64, 21, 30, 30); }
93 ST_IN HReg hregMIPS_W27 ( Bool mode64 ) { return VEC(mode64, 23, 31, 31); }
94 ST_IN HReg hregMIPS_W28 ( Bool mode64 ) { return VEC(mode64, 25, 32, 32); }
95 ST_IN HReg hregMIPS_W29 ( Bool mode64 ) { return VEC(mode64, 27, 33, 33); }
96 ST_IN HReg hregMIPS_W30 ( Bool mode64 ) { return VEC(mode64, 29, 34, 34); }
97 ST_IN HReg hregMIPS_W31 ( Bool mode64 ) { return VEC(mode64, 31, 35, 35); }
99 // DRs are only allocatable in 32-bit mode, so the 64-bit index numbering
100 // doesn't advance here.
101 ST_IN HReg hregMIPS_D0 ( Bool mode64 ) { vassert(!mode64);
102 return DR (mode64, 0, 0, 36); }
103 ST_IN HReg hregMIPS_D1 ( Bool mode64 ) { vassert(!mode64);
104 return DR (mode64, 2, 0, 37); }
105 ST_IN HReg hregMIPS_D2 ( Bool mode64 ) { vassert(!mode64);
106 return DR (mode64, 4, 0, 38); }
107 ST_IN HReg hregMIPS_D3 ( Bool mode64 ) { vassert(!mode64);
108 return DR (mode64, 6, 0, 39); }
109 ST_IN HReg hregMIPS_D4 ( Bool mode64 ) { vassert(!mode64);
110 return DR (mode64, 8, 0, 40); }
111 ST_IN HReg hregMIPS_D5 ( Bool mode64 ) { vassert(!mode64);
112 return DR (mode64, 10, 0, 41); }
113 ST_IN HReg hregMIPS_D6 ( Bool mode64 ) { vassert(!mode64);
114 return DR (mode64, 12, 0, 42); }
115 ST_IN HReg hregMIPS_D7 ( Bool mode64 ) { vassert(!mode64);
116 return DR (mode64, 14, 0, 43); }
118 ST_IN HReg hregMIPS_HI ( Bool mode64 ) { return FR (mode64, 33, 36, 44); }
119 ST_IN HReg hregMIPS_LO ( Bool mode64 ) { return FR (mode64, 34, 37, 45); }
121 ST_IN HReg hregMIPS_GPR0 ( Bool mode64 ) { return GPR(mode64, 0, 38, 46); }
122 ST_IN HReg hregMIPS_GPR1 ( Bool mode64 ) { return GPR(mode64, 1, 39, 47); }
123 ST_IN HReg hregMIPS_GPR2 ( Bool mode64 ) { return GPR(mode64, 2, 40, 48); }
124 ST_IN HReg hregMIPS_GPR3 ( Bool mode64 ) { return GPR(mode64, 3, 41, 49); }
125 ST_IN HReg hregMIPS_GPR4 ( Bool mode64 ) { return GPR(mode64, 4, 42, 50); }
126 ST_IN HReg hregMIPS_GPR5 ( Bool mode64 ) { return GPR(mode64, 5, 43, 51); }
127 ST_IN HReg hregMIPS_GPR6 ( Bool mode64 ) { return GPR(mode64, 6, 44, 52); }
128 ST_IN HReg hregMIPS_GPR7 ( Bool mode64 ) { return GPR(mode64, 7, 45, 53); }
129 ST_IN HReg hregMIPS_GPR8 ( Bool mode64 ) { return GPR(mode64, 8, 46, 54); }
130 ST_IN HReg hregMIPS_GPR9 ( Bool mode64 ) { return GPR(mode64, 9, 47, 55); }
131 ST_IN HReg hregMIPS_GPR10 ( Bool mode64 ) { return GPR(mode64, 10, 48, 56); }
132 ST_IN HReg hregMIPS_GPR11 ( Bool mode64 ) { return GPR(mode64, 11, 49, 57); }
133 ST_IN HReg hregMIPS_GPR23 ( Bool mode64 ) { return GPR(mode64, 23, 50, 58); }
134 ST_IN HReg hregMIPS_GPR25 ( Bool mode64 ) { return GPR(mode64, 25, 51, 59); }
135 ST_IN HReg hregMIPS_GPR29 ( Bool mode64 ) { return GPR(mode64, 29, 52, 60); }
136 ST_IN HReg hregMIPS_GPR31 ( Bool mode64 ) { return GPR(mode64, 31, 53, 61); }
138 #undef ST_IN
139 #undef GPR
140 #undef FR
141 #undef DR
142 #undef VEC
144 #define GuestStatePointer(_mode64) hregMIPS_GPR23(_mode64)
145 #define StackFramePointer(_mode64) hregMIPS_GPR30(_mode64)
146 #define StackPointer(_mode64) hregMIPS_GPR29(_mode64)
147 #define Zero(_mode64) hregMIPS_GPR0(_mode64)
149 /* guest_COND offset */
150 #define COND_OFFSET(_mode64) ((_mode64) ? 588 : 448)
152 /* guest_MSACSR offset */
153 #define MSACSR_OFFSET(_mode64) ((_mode64) ? 1144 : 1016)
155 /* Num registers used for function calls */
156 #if defined(VGP_mips32_linux)
157 /* a0, a1, a2, a3 */
158 # define MIPS_N_REGPARMS 4
159 #else
160 /* a0, a1, a2, a3, a4, a5, a6, a7 */
161 # define MIPS_N_REGPARMS 8
162 #endif
164 extern UInt ppHRegMIPS ( HReg, Bool );
166 #define OPC_MSA 0x78000000
168 /* --------- Condition codes, Intel encoding. --------- */
169 typedef enum {
170 MIPScc_EQ = 0, /* equal */
171 MIPScc_NE = 1, /* not equal */
173 MIPScc_HS = 2, /* >=u (higher or same) */
174 MIPScc_LO = 3, /* <u (lower) */
176 MIPScc_MI = 4, /* minus (negative) */
177 MIPScc_PL = 5, /* plus (zero or +ve) */
179 MIPScc_VS = 6, /* overflow */
180 MIPScc_VC = 7, /* no overflow */
182 MIPScc_HI = 8, /* >u (higher) */
183 MIPScc_LS = 9, /* <=u (lower or same) */
185 MIPScc_GE = 10, /* >=s (signed greater or equal) */
186 MIPScc_LT = 11, /* <s (signed less than) */
188 MIPScc_GT = 12, /* >s (signed greater) */
189 MIPScc_LE = 13, /* <=s (signed less or equal) */
191 MIPScc_AL = 14, /* always (unconditional) */
192 MIPScc_NV = 15 /* never (unconditional): */
193 } MIPSCondCode;
195 extern const HChar *showMIPSCondCode(MIPSCondCode);
197 /* --------- Memory address expressions (amodes). --------- */
198 typedef enum {
199 Mam_IR, /* Immediate (signed 16-bit) + Reg */
200 Mam_RR /* Reg1 + Reg2 */
201 } MIPSAModeTag;
203 typedef struct {
204 MIPSAModeTag tag;
205 union {
206 struct {
207 HReg base;
208 Int index;
209 } IR;
210 struct {
211 HReg base;
212 HReg index;
213 } RR;
214 } Mam;
215 } MIPSAMode;
217 extern MIPSAMode *MIPSAMode_IR(Int, HReg);
218 extern MIPSAMode *MIPSAMode_RR(HReg, HReg);
220 extern MIPSAMode *dopyMIPSAMode(MIPSAMode *);
221 extern MIPSAMode *nextMIPSAModeFloat(MIPSAMode *);
222 extern MIPSAMode *nextMIPSAModeInt(MIPSAMode *);
224 extern void ppMIPSAMode(MIPSAMode *, Bool);
226 /* --------- Operand, which can be a reg or a u16/s16. --------- */
227 /* ("RH" == "Register or Halfword immediate") */
228 typedef enum {
229 Mrh_Imm,
230 Mrh_Reg
231 } MIPSRHTag;
233 typedef struct {
234 MIPSRHTag tag;
235 union {
236 struct {
237 Bool syned;
238 UShort imm16;
239 } Imm;
240 struct {
241 HReg reg;
242 } Reg;
243 } Mrh;
244 } MIPSRH;
246 extern void ppMIPSRH(MIPSRH *, Bool);
248 extern MIPSRH *MIPSRH_Imm(Bool, UShort);
249 extern MIPSRH *MIPSRH_Reg(HReg);
251 /* --------- Instructions. --------- */
253 /*Tags for operations*/
255 /* --------- */
256 typedef enum {
257 Mun_CLO,
258 Mun_CLZ,
259 Mun_DCLO,
260 Mun_DCLZ,
261 Mun_NOP,
262 } MIPSUnaryOp;
264 extern const HChar *showMIPSUnaryOp(MIPSUnaryOp);
265 /* --------- */
267 /* --------- */
269 typedef enum {
270 Malu_INVALID,
271 Malu_ADD, Malu_SUB,
272 Malu_AND, Malu_OR, Malu_NOR, Malu_XOR,
273 Malu_DADD, Malu_DSUB,
274 Malu_SLT
275 } MIPSAluOp;
277 extern const HChar *showMIPSAluOp(MIPSAluOp,
278 Bool /* is the 2nd operand an immediate? */ );
280 /* --------- */
281 typedef enum {
282 Mshft_INVALID,
283 Mshft_SLL, Mshft_SRL,
284 Mshft_SRA
285 } MIPSShftOp;
287 extern const HChar *showMIPSShftOp(MIPSShftOp,
288 Bool /* is the 2nd operand an immediate? */ ,
289 Bool /* is this a 32bit or 64bit op? */ );
291 /* --------- */
292 typedef enum {
293 Macc_ADD,
294 Macc_SUB
295 } MIPSMaccOp;
297 extern const HChar *showMIPSMaccOp(MIPSMaccOp, Bool);
298 /* --------- */
300 typedef enum {
301 MSA_LD = 8,
302 MSA_ST = 9
303 } MSAMI10Op;
305 extern const HChar *showMsaMI10op(MSAMI10Op);
307 typedef enum {
308 MSA_SLDI = 0,
309 MSA_COPY_S = 2,
310 MSA_COPY_U = 3,
311 MSA_INSERT = 4,
312 MSA_INSVE = 5,
313 MSA_MOVE = 0xBE,
314 MSA_CFCMSA = 0x7E,
315 MSA_CTCMSA = 0x3E
316 } MSAELMOp;
318 extern const HChar *showMsaElmOp(MSAELMOp);
320 typedef enum {
321 MSA_FILL = 0xC0,
322 MSA_PCNT = 0xC1,
323 MSA_NLOC = 0xC2,
324 MSA_NLZC = 0xC3
325 } MSA2ROp;
327 extern const HChar *showMsa2ROp(MSA2ROp);
329 typedef enum {
330 MSA_FTRUNC_S = 0x191,
331 MSA_FTRUNC_U = 0x192,
332 MSA_FFINT_S = 0x19E,
333 MSA_FFINT_U = 0x19F,
334 MSA_FSQRT = 0x193,
335 MSA_FRSQRT = 0x194,
336 MSA_FRCP = 0x195,
337 MSA_FLOG2 = 0x197,
338 MSA_FEXUPR = 0x199,
339 MSA_FTINT_U = 0x19D,
340 MSA_FTINT_S = 0x19C,
341 } MSA2RFOp;
343 extern const HChar *showMsa2RFOp(MSA2RFOp);
345 typedef enum {
346 MSA_SLL = 0xD,
347 MSA_ADDV,
348 MSA_CEQ,
349 MSA_ADD_A,
350 MSA_SUBS_S,
351 MSA_SLD = 0x14,
352 MSA_SRA = 0x80000D,
353 MSA_SUBV,
354 MSA_SUBS_U = 0x800011,
355 MSA_SRL = 0x100000D,
356 MSA_MAX_S,
357 MSA_CLT_S,
358 MSA_ADDS_S,
359 MSA_PCKEV = 0x1000014,
360 MSA_MAX_U = 0x180000E,
361 MSA_CLT_U,
362 MSA_ADDS_U,
363 MSA_PCKOD = 0x1800014,
364 MSA_MIN_S = 0x200000E,
365 MSA_ILVL = 0x2000014,
366 MSA_MIN_U = 0x280000E,
367 MSA_ILVR = 0x2800014,
368 MSA_AVER_S = 0x3000010,
369 MSA_ILVEV = 0x3000014,
370 MSA_AVER_U = 0x3800010,
371 MSA_ILVOD = 0x3800014,
372 MSA_MULV = 0x0000012,
373 MSA_SPLAT = 0x0800014,
374 MSA_DIVS = 0x2000012,
375 MSA_DIVU = 0x2800012,
376 MSA_VSHF = 0x0000015,
377 } MSA3ROp;
379 extern const HChar *showMsa3ROp(MSA3ROp);
381 typedef enum {
382 MSA_FADD = 0x000001B,
383 MSA_FCUN = 0x040001A,
384 MSA_FSUB = 0x040001B,
385 MSA_FCEQ = 0x080001A,
386 MSA_FMUL = 0x080001B,
387 MSA_FDIV = 0x0C0001B,
388 MSA_FMADD = 0x100001B,
389 MSA_FCLT = 0x100001A,
390 MSA_FMSUB = 0x140001B,
391 MSA_FEXP2 = 0x1C0001B,
392 MSA_FMIN = 0x300001B,
393 MSA_FMIN_A = 0x340001B,
394 MSA_FMAX = 0x380001B,
395 MSA_MUL_Q = 0x100001C,
396 MSA_FCLE = 0x180001A,
397 MSA_FTQ = 0x280001B,
398 MSA_FEXDO = 0x200001B,
399 MSA_MULR_Q = 0x300001C,
400 } MSA3RFOp;
402 extern const HChar *showMsa3RFOp(MSA3RFOp);
404 typedef enum {
405 MSA_ANDV,
406 MSA_ORV,
407 MSA_NORV,
408 MSA_XORV
409 } MSAVECOp;
411 extern const HChar *showMsaVecOp(MSAVECOp);
413 typedef enum {
414 MSA_SLLI = 9,
415 MSA_SAT_S,
416 MSA_SRAI = 0x800009,
417 MSA_SRLI = 0x1000009,
418 MSA_SRARI = 0x100000A
419 } MSABITOp;
421 extern const HChar *showMsaBitOp(MSABITOp);
423 typedef enum {
424 MSA_B = 0,
425 MSA_H = 1,
426 MSA_W = 2,
427 MSA_D = 3,
428 } MSADF;
430 extern HChar showMsaDF(MSADF df);
432 typedef enum {
433 MSA_DFN_B = 0x00,
434 MSA_DFN_H = 0x20,
435 MSA_DFN_W = 0x30,
436 MSA_DFN_D = 0x38,
437 } MSADFNMask;
439 typedef enum {
440 MSA_F_WH = 0,
441 MSA_F_DW = 1,
442 } MSADFFlx;
444 extern HChar showMsaDFF(MSADFFlx df, int op);
447 /* ----- Instruction tags ----- */
448 typedef enum {
449 Min_LI, /* load word (32/64-bit) immediate (fake insn) */
450 Min_Alu, /* word add/sub/and/or/xor/nor/others? */
451 Min_Shft, /* word sll/srl/sra */
452 Min_Unary, /* clo, clz, nop, neg */
453 Min_Ext, /* ext / dext, dextm, dextu */
454 Min_Rotx,
456 Min_Cmp, /* word compare (fake insn) */
458 Min_Mul, /* non-widening, 32-bit, signed multiply */
459 Min_Mult, /* widening multiply */
460 Min_Mulr6,
461 Min_Div, /* div */
462 Min_Divr6,
464 Min_Call, /* call to address in register */
466 /* The following 5 insns are mandated by translation chaining */
467 Min_XDirect, /* direct transfer to GA */
468 Min_XIndir, /* indirect transfer to GA */
469 Min_XAssisted, /* assisted transfer to GA */
470 Min_EvCheck, /* Event check */
471 Min_ProfInc, /* 64-bit profile counter increment */
473 Min_RdWrLR, /* Read/Write Link Register */
474 Min_Mthi, /* Move to HI from GP register */
475 Min_Mtlo, /* Move to LO from GP register */
476 Min_Mfhi, /* Move from HI to GP register */
477 Min_Mflo, /* Move from LO to GP register */
478 Min_Macc, /* Multiply and accumulate */
480 Min_Load, /* zero-extending load a 8|16|32 bit value from mem */
481 Min_Store, /* store a 8|16|32 bit value to mem */
482 Min_Cas, /* compare and swap */
483 Min_LoadL, /* mips Load Linked Word - LL */
484 Min_StoreC, /* mips Store Conditional Word - SC */
486 Min_FpUnary, /* FP unary op */
487 Min_FpBinary, /* FP binary op */
488 Min_FpTernary, /* FP ternary op */
489 Min_FpConvert, /* FP conversion op */
490 Min_FpMulAcc, /* FP multipy-accumulate style op */
491 Min_FpLdSt, /* FP load/store */
492 Min_FpSTFIW, /* stfiwx */
493 Min_FpRSP, /* FP round IEEE754 double to IEEE754 single */
494 Min_FpCftI, /* fcfid/fctid/fctiw */
495 Min_FpCMov, /* FP floating point conditional move */
496 Min_MtFCSR, /* set FCSR register */
497 Min_MfFCSR, /* get FCSR register */
498 Min_FpCompare, /* FP compare, generating value into int reg */
499 Min_FpMinMax, /* FP r6 min and max*/
501 Min_FpGpMove, /* Move from/to fpr to/from gpr */
502 Min_MoveCond, /* Move Conditional */
504 Msa_MI10,
505 Msa_ELM,
506 Msa_3R,
507 Msa_2R,
508 Msa_VEC,
509 Msa_BIT,
510 Msa_3RF,
511 Msa_2RF,
512 } MIPSInstrTag;
514 /* --------- */
515 typedef enum {
516 Mfp_INVALID,
518 /* Ternary */
519 Mfp_MADDD, Mfp_MSUBD,
520 Mfp_MADDS, Mfp_MSUBS,
522 /* Binary */
523 Mfp_ADDD, Mfp_SUBD, Mfp_MULD, Mfp_DIVD,
524 Mfp_ADDS, Mfp_SUBS, Mfp_MULS, Mfp_DIVS,
526 /* Unary */
527 Mfp_SQRTS, Mfp_SQRTD,
528 Mfp_ABSS, Mfp_ABSD, Mfp_NEGS, Mfp_NEGD, Mfp_MOVS, Mfp_MOVD,
530 /* FP convert */
531 Mfp_CVTSD, Mfp_CVTSW, Mfp_CVTWD,
532 Mfp_CVTWS, Mfp_CVTDL, Mfp_CVTSL, Mfp_CVTLS, Mfp_CVTLD, Mfp_TRULS, Mfp_TRULD,
533 Mfp_TRUWS, Mfp_TRUWD, Mfp_FLOORWS, Mfp_FLOORWD, Mfp_ROUNDWS, Mfp_ROUNDWD,
534 Mfp_CVTDW, Mfp_CEILWS, Mfp_CEILWD, Mfp_CEILLS, Mfp_CEILLD, Mfp_CVTDS,
535 Mfp_ROUNDLD, Mfp_FLOORLD, Mfp_RINTS, Mfp_RINTD,
537 /* FP compare */
538 Mfp_CMP_UN, Mfp_CMP_EQ, Mfp_CMP_LT, Mfp_CMP_NGT,
540 Mfp_CMP_UN_S, Mfp_CMP_EQ_S, Mfp_CMP_LT_S, Mfp_CMP_NGT_S,
542 /*MAX and MIN*/
543 Mfp_MAXS, Mfp_MAXD, Mfp_MINS, Mfp_MIND
545 } MIPSFpOp;
547 extern const HChar *showMIPSFpOp(MIPSFpOp);
549 typedef enum {
550 Rotx32,
551 Rotx64
552 } MIPSRotxOp;
554 extern const HChar *showRotxOp(MIPSRotxOp);
556 /* Move from/to fpr to/from gpr */
557 typedef enum {
558 MFpGpMove_mfc1, /* Move Word From Floating Point - MIPS32 */
559 MFpGpMove_dmfc1, /* Doubleword Move from Floating Point - MIPS64 */
560 MFpGpMove_mtc1, /* Move Word to Floating Point - MIPS32 */
561 MFpGpMove_dmtc1 /* Doubleword Move to Floating Point - MIPS64 */
562 } MIPSFpGpMoveOp;
564 extern const HChar *showMIPSFpGpMoveOp ( MIPSFpGpMoveOp );
566 /* Move Conditional */
567 typedef enum {
568 MFpMoveCond_movns, /* FP Move Conditional on Not Zero - MIPS32 */
569 MFpMoveCond_movnd,
570 MMoveCond_movn, /* Move Conditional on Not Zero */
571 MSeleqz, /* r6 instructions */
572 MSelnez,
573 MFpSels,
574 MFpSeld
575 } MIPSMoveCondOp;
577 extern const HChar *showMIPSMoveCondOp ( MIPSMoveCondOp );
579 /*--------- Structure for instructions ----------*/
580 /* Destinations are on the LEFT (first operand) */
582 typedef struct {
583 MIPSInstrTag tag;
584 union {
585 /* Get a 32/64-bit literal into a register.
586 May turn into a number of real insns. */
587 struct {
588 HReg dst;
589 ULong imm;
590 } LI;
591 /* Integer add/sub/and/or/xor. Limitations:
592 - For add, the immediate, if it exists, is a signed 16.
593 - For sub, the immediate, if it exists, is a signed 16
594 which may not be -32768, since no such instruction
595 exists, and so we have to emit addi with +32768, but
596 that is not possible.
597 - For and/or/xor, the immediate, if it exists,
598 is an unsigned 16.
600 struct {
601 MIPSAluOp op;
602 HReg dst;
603 HReg srcL;
604 MIPSRH *srcR;
605 } Alu;
606 /* Integer shl/shr/sar.
607 Limitations: the immediate, if it exists,
608 is a signed 5-bit value between 1 and 31 inclusive.
610 struct {
611 MIPSShftOp op;
612 Bool sz32; /* mode64 has both 32 and 64bit shft */
613 HReg dst;
614 HReg srcL;
615 MIPSRH *srcR;
616 } Shft;
617 struct {
618 MIPSRotxOp op;
619 HReg rd;
620 HReg rt;
621 HReg shift;
622 HReg shiftx;
623 HReg stripe;
624 } Rotx;
625 /* Clz, Clo, nop */
626 struct {
627 MIPSUnaryOp op;
628 HReg dst;
629 HReg src;
630 } Unary;
631 /* Bit extract */
632 struct {
633 HReg dst;
634 HReg src;
635 UInt pos;
636 UInt size;
637 } Ext;
638 /* Word compare. Fake instruction, used for basic block ending */
639 struct {
640 Bool syned;
641 Bool sz32;
642 HReg dst;
643 HReg srcL;
644 HReg srcR;
646 MIPSCondCode cond;
647 } Cmp;
648 struct {
649 Bool widening; /* True => widening, False => non-widening */
650 Bool syned; /* signed/unsigned - meaningless if widenind = False */
651 Bool sz32;
652 HReg dst;
653 HReg srcL;
654 HReg srcR;
655 } Mul;
656 struct {
657 Bool syned; /* signed/unsigned */
658 HReg srcL;
659 HReg srcR;
660 } Mult;
661 struct {
662 Bool syned; /* signed/unsigned - meaningless if widenind = False */
663 Bool sz32;
664 Bool low;
665 HReg dst;
666 HReg srcL;
667 HReg srcR;
668 } Mulr6;
669 struct {
670 Bool syned; /* signed/unsigned - meaningless if widenind = False */
671 Bool sz32;
672 HReg srcL;
673 HReg srcR;
674 } Div;
675 struct {
676 Bool syned; /* signed/unsigned - meaningless if widenind = False */
677 Bool sz32;
678 Bool mod;
679 HReg dst;
680 HReg srcL;
681 HReg srcR;
682 } Divr6;
683 /* Pseudo-insn. Call target (an absolute address), on given
684 condition (which could be Mcc_ALWAYS). argiregs indicates
685 which of $4 .. $7 (mips32) or $4 .. $11 (mips64)
686 carries argument values for this call,
687 using a bit mask (1<<N is set if $N holds an arg, for N in
688 $4 .. $7 or $4 .. $11 inclusive).
689 If cond is != Mcc_ALWAYS, src is checked.
690 Otherwise, unconditional call */
691 struct {
692 MIPSCondCode cond;
693 Addr64 target;
694 UInt argiregs;
695 HReg src;
696 RetLoc rloc; /* where the return value will be */
697 } Call;
698 /* Update the guest EIP value, then exit requesting to chain
699 to it. May be conditional. Urr, use of Addr32 implicitly
700 assumes that wordsize(guest) == wordsize(host). */
701 struct {
702 Addr64 dstGA; /* next guest address */
703 MIPSAMode* amPC; /* amode in guest state for PC */
704 MIPSCondCode cond; /* can be MIPScc_AL */
705 Bool toFastEP; /* chain to the slow or fast point? */
706 } XDirect;
707 /* Boring transfer to a guest address not known at JIT time.
708 Not chainable. May be conditional. */
709 struct {
710 HReg dstGA;
711 MIPSAMode* amPC;
712 MIPSCondCode cond; /* can be MIPScc_AL */
713 } XIndir;
714 /* Assisted transfer to a guest address, most general case.
715 Not chainable. May be conditional. */
716 struct {
717 HReg dstGA;
718 MIPSAMode* amPC;
719 MIPSCondCode cond; /* can be MIPScc_AL */
720 IRJumpKind jk;
721 } XAssisted;
722 /* Zero extending loads. Dst size is host word size */
723 struct {
724 UChar sz; /* 1|2|4|8 */
725 HReg dst;
726 MIPSAMode *src;
727 } Load;
728 struct {
729 HReg data;
730 HReg addr;
731 } MsaLoad;
732 /* 64/32/16/8 bit stores */
733 struct {
734 UChar sz; /* 1|2|4|8 */
735 MIPSAMode *dst;
736 HReg src;
737 } Store;
738 struct {
739 UChar sz; /* 4|8 */
740 HReg dst;
741 MIPSAMode *src;
742 } LoadL;
743 struct {
744 UChar sz; /* 4|8 */
745 HReg old;
746 HReg addr;
747 HReg expd;
748 HReg data;
749 } Cas;
750 struct {
751 UChar sz; /* 4|8 */
752 MIPSAMode *dst;
753 HReg src;
754 } StoreC;
755 /* Move from HI/LO register to GP register. */
756 struct {
757 HReg dst;
758 } MfHL;
760 /* Move to HI/LO register from GP register. */
761 struct {
762 HReg src;
763 } MtHL;
765 /* Read/Write Link Register */
766 struct {
767 Bool wrLR;
768 HReg gpr;
769 } RdWrLR;
771 /* MIPS Multiply and accumulate instructions. */
772 struct {
773 MIPSMaccOp op;
774 Bool syned;
776 HReg srcL;
777 HReg srcR;
778 } Macc;
780 /* MIPS Floating point */
781 struct {
782 MIPSFpOp op;
783 HReg dst;
784 HReg src;
785 } FpUnary;
786 struct {
787 MIPSFpOp op;
788 HReg dst;
789 HReg srcL;
790 HReg srcR;
791 } FpBinary;
792 struct {
793 MIPSFpOp op;
794 HReg dst;
795 HReg src1;
796 HReg src2;
797 HReg src3;
798 } FpTernary;
799 struct {
800 MIPSFpOp op;
801 HReg dst;
802 HReg srcML;
803 HReg srcMR;
804 HReg srcAcc;
805 } FpMulAcc;
806 struct {
807 Bool isLoad;
808 UChar sz; /* only 4 (IEEE single) or 8 (IEEE double) */
809 HReg reg;
810 MIPSAMode *addr;
811 } FpLdSt;
813 struct {
814 MIPSFpOp op;
815 HReg dst;
816 HReg src;
817 } FpConvert;
818 struct {
819 MIPSFpOp op;
820 HReg dst;
821 HReg srcL;
822 HReg srcR;
823 UChar cond1;
824 } FpCompare;
825 struct {
826 MIPSFpOp op;
827 HReg dst;
828 HReg srcL;
829 HReg srcR;
830 } FpMinMax;
831 /* Move from GP register to FCSR register. */
832 struct {
833 HReg src;
834 } MtFCSR;
835 /* Move from FCSR register to GP register. */
836 struct {
837 HReg dst;
838 } MfFCSR;
839 struct {
840 MIPSAMode* amCounter;
841 MIPSAMode* amFailAddr;
842 } EvCheck;
843 struct {
844 /* No fields. The address of the counter to inc is
845 installed later, post-translation, by patching it in,
846 as it is not known at translation time. */
847 } ProfInc;
849 /* Move from/to fpr to/from gpr */
850 struct {
851 MIPSFpGpMoveOp op;
852 HReg dst;
853 HReg src;
854 } FpGpMove;
855 struct {
856 MIPSMoveCondOp op;
857 HReg dst;
858 HReg src;
859 HReg cond;
860 } MoveCond;
861 struct {
862 MSAMI10Op op;
863 UInt s10;
864 HReg rs;
865 HReg wd;
866 MSADF df;
867 } MsaMi10;
868 struct {
869 MSAELMOp op;
870 HReg ws;
871 HReg wd;
872 UInt dfn;
873 } MsaElm;
874 struct {
875 MSA2ROp op;
876 MSADF df;
877 HReg ws;
878 HReg wd;
879 } Msa2R;
880 struct {
881 MSA3ROp op;
882 MSADF df;
883 HReg wt;
884 HReg ws;
885 HReg wd;
886 } Msa3R;
887 struct {
888 MSAVECOp op;
889 HReg wt;
890 HReg ws;
891 HReg wd;
892 } MsaVec;
893 struct {
894 MSABITOp op;
895 MSADF df;
896 UChar ms;
897 HReg ws;
898 HReg wd;
899 }MsaBit;
900 struct {
901 MSA3RFOp op;
902 MSADFFlx df;
903 HReg wt;
904 HReg ws;
905 HReg wd;
906 } Msa3RF;
907 struct {
908 MSA2RFOp op;
909 MSADFFlx df;
910 HReg ws;
911 HReg wd;
912 } Msa2RF;
914 } Min;
915 } MIPSInstr;
917 extern MIPSInstr *MIPSInstr_LI(HReg, ULong);
918 extern MIPSInstr *MIPSInstr_Alu(MIPSAluOp, HReg, HReg, MIPSRH *);
919 extern MIPSInstr *MIPSInstr_Shft(MIPSShftOp, Bool sz32, HReg, HReg, MIPSRH *);
920 extern MIPSInstr *MIPSInstr_Unary(MIPSUnaryOp op, HReg dst, HReg src);
921 extern MIPSInstr *MIPSInstr_Ext(HReg, HReg, UInt, UInt);
922 extern MIPSInstr *MIPSInstr_Cmp(Bool, Bool, HReg, HReg, HReg, MIPSCondCode);
923 extern MIPSInstr *MIPSInstr_Mul(HReg, HReg, HReg);
924 extern MIPSInstr *MIPSInstr_Mult(Bool, HReg, HReg);
925 extern MIPSInstr *MIPSInstr_Mulr6(Bool syned, Bool sz32, Bool low,
926 HReg, HReg, HReg);
927 extern MIPSInstr *MIPSInstr_Div(Bool syned, Bool sz32, HReg, HReg);
928 extern MIPSInstr *MIPSInstr_Divr6(Bool syned, Bool sz32, Bool mod,
929 HReg, HReg, HReg);
930 extern MIPSInstr *MIPSInstr_Madd(Bool, HReg, HReg);
931 extern MIPSInstr *MIPSInstr_Msub(Bool, HReg, HReg);
933 extern MIPSInstr *MIPSInstr_Load(UChar sz, HReg dst, MIPSAMode * src,
934 Bool mode64);
935 extern MIPSInstr *MIPSInstr_Store(UChar sz, MIPSAMode * dst, HReg src,
936 Bool mode64);
938 extern MIPSInstr *MIPSInstr_LoadL(UChar sz, HReg dst, MIPSAMode * src,
939 Bool mode64);
940 extern MIPSInstr *MIPSInstr_StoreC(UChar sz, MIPSAMode * dst, HReg src,
941 Bool mode64);
942 extern MIPSInstr *MIPSInstr_Cas(UChar sz, HReg old, HReg addr,
943 HReg expd, HReg data, Bool mode64);
945 extern MIPSInstr *MIPSInstr_Call ( MIPSCondCode, Addr64, UInt, HReg, RetLoc );
946 extern MIPSInstr *MIPSInstr_CallAlways ( MIPSCondCode, Addr64, UInt, RetLoc );
948 extern MIPSInstr *MIPSInstr_XDirect ( Addr64 dstGA, MIPSAMode* amPC,
949 MIPSCondCode cond, Bool toFastEP );
950 extern MIPSInstr *MIPSInstr_XIndir(HReg dstGA, MIPSAMode* amPC,
951 MIPSCondCode cond);
952 extern MIPSInstr *MIPSInstr_XAssisted(HReg dstGA, MIPSAMode* amPC,
953 MIPSCondCode cond, IRJumpKind jk);
955 extern MIPSInstr *MIPSInstr_FpUnary(MIPSFpOp op, HReg dst, HReg src);
956 extern MIPSInstr *MIPSInstr_FpBinary(MIPSFpOp op, HReg dst, HReg srcL,
957 HReg srcR);
958 extern MIPSInstr *MIPSInstr_FpTernary ( MIPSFpOp op, HReg dst, HReg src1,
959 HReg src2, HReg src3 );
960 extern MIPSInstr *MIPSInstr_FpConvert(MIPSFpOp op, HReg dst, HReg src);
961 extern MIPSInstr *MIPSInstr_FpCompare(MIPSFpOp op, HReg dst, HReg srcL,
962 HReg srcR);
963 extern MIPSInstr *MIPSInstr_FpMinMax(MIPSFpOp op, HReg dst, HReg srcL,
964 HReg srcR);
965 extern MIPSInstr *MIPSInstr_FpMulAcc(MIPSFpOp op, HReg dst, HReg srcML,
966 HReg srcMR, HReg srcAcc);
967 extern MIPSInstr *MIPSInstr_FpLdSt(Bool isLoad, UChar sz, HReg, MIPSAMode *);
968 extern MIPSInstr *MIPSInstr_FpSTFIW(HReg addr, HReg data);
969 extern MIPSInstr *MIPSInstr_FpRSP(HReg dst, HReg src);
970 extern MIPSInstr *MIPSInstr_FpCftI(Bool fromI, Bool int32, HReg dst, HReg src);
971 extern MIPSInstr *MIPSInstr_FpCMov(MIPSCondCode, HReg dst, HReg src);
972 extern MIPSInstr *MIPSInstr_MtFCSR(HReg src);
973 extern MIPSInstr *MIPSInstr_MfFCSR(HReg dst);
974 extern MIPSInstr *MIPSInstr_FpCmp(HReg dst, HReg srcL, HReg srcR);
976 extern MIPSInstr *MIPSInstr_Mfhi(HReg dst);
977 extern MIPSInstr *MIPSInstr_Mflo(HReg dst);
978 extern MIPSInstr *MIPSInstr_Mthi(HReg src);
979 extern MIPSInstr *MIPSInstr_Mtlo(HReg src);
981 extern MIPSInstr *MIPSInstr_RdWrLR(Bool wrLR, HReg gpr);
983 extern MIPSInstr *MIPSInstr_MoveCond ( MIPSMoveCondOp op, HReg dst,
984 HReg src, HReg cond );
986 extern MIPSInstr *MIPSInstr_FpGpMove ( MIPSFpGpMoveOp op, HReg dst, HReg src );
988 extern MIPSInstr *MIPSInstr_EvCheck(MIPSAMode* amCounter,
989 MIPSAMode* amFailAddr );
990 extern MIPSInstr *MIPSInstr_ProfInc( void );
992 extern MIPSInstr* MIPSInstr_MsaMi10(MSAMI10Op op, UInt s10, HReg rs, HReg wd, MSADF df);
993 extern MIPSInstr* MIPSInstr_MsaElm(MSAELMOp op, HReg ws, HReg wd, UInt dfn);
994 extern MIPSInstr* MIPSInstr_Msa3R(MSA3ROp op, MSADF df, HReg wd, HReg ws, HReg wt);
995 extern MIPSInstr* MIPSInstr_Msa2R(MSA2ROp op, MSADF df, HReg ws, HReg wd);
996 extern MIPSInstr* MIPSInstr_MsaVec(MSAVECOp op, HReg wt, HReg ws, HReg wd);
997 extern MIPSInstr* MIPSInstr_MsaBit(MSABITOp op, MSADF df, UChar ms, HReg ws, HReg wd);
998 extern MIPSInstr* MIPSInstr_Msa3RF(MSA3RFOp op, MSADFFlx df, HReg wd, HReg ws, HReg wt);
999 extern MIPSInstr* MIPSInstr_Msa2RF(MSA2RFOp op, MSADFFlx df, HReg wd, HReg ws);
1001 extern MIPSInstr* MIPSInstr_Bitswap(MIPSRotxOp, HReg, HReg, HReg, HReg, HReg);
1003 extern void ppMIPSInstr(const MIPSInstr *, Bool mode64);
1005 /* Some functions that insulate the register allocator from details
1006 of the underlying instruction set. */
1007 extern void getRegUsage_MIPSInstr (HRegUsage *, const MIPSInstr *, Bool);
1008 extern void mapRegs_MIPSInstr (HRegRemap *, MIPSInstr *, Bool mode64);
1009 extern Int emit_MIPSInstr (/*MB_MOD*/Bool* is_profInc,
1010 UChar* buf, Int nbuf, const MIPSInstr* i,
1011 Bool mode64,
1012 VexEndness endness_host,
1013 const void* disp_cp_chain_me_to_slowEP,
1014 const void* disp_cp_chain_me_to_fastEP,
1015 const void* disp_cp_xindir,
1016 const void* disp_cp_xassisted );
1018 extern void genSpill_MIPS ( /*OUT*/ HInstr ** i1, /*OUT*/ HInstr ** i2,
1019 HReg rreg, Int offset, Bool);
1020 extern void genReload_MIPS( /*OUT*/ HInstr ** i1, /*OUT*/ HInstr ** i2,
1021 HReg rreg, Int offset, Bool);
1022 extern MIPSInstr* genMove_MIPS(HReg from, HReg to, Bool mode64);
1024 extern const RRegUniverse* getRRegUniverse_MIPS ( Bool mode64 );
1026 extern HInstrArray *iselSB_MIPS ( const IRSB*,
1027 VexArch,
1028 const VexArchInfo*,
1029 const VexAbiInfo*,
1030 Int offs_Host_EvC_Counter,
1031 Int offs_Host_EvC_FailAddr,
1032 Bool chainingAllowed,
1033 Bool addProfInc,
1034 Addr max_ga );
1036 /* How big is an event check? This is kind of a kludge because it
1037 depends on the offsets of host_EvC_FAILADDR and host_EvC_COUNTER,
1038 and so assumes that they are both <= 128, and so can use the short
1039 offset encoding. This is all checked with assertions, so in the
1040 worst case we will merely assert at startup. */
1041 extern Int evCheckSzB_MIPS (void);
1043 /* Perform a chaining and unchaining of an XDirect jump. */
1044 extern VexInvalRange chainXDirect_MIPS ( VexEndness endness_host,
1045 void* place_to_chain,
1046 const void* disp_cp_chain_me_EXPECTED,
1047 const void* place_to_jump_to,
1048 Bool mode64 );
1050 extern VexInvalRange unchainXDirect_MIPS ( VexEndness endness_host,
1051 void* place_to_unchain,
1052 const void* place_to_jump_to_EXPECTED,
1053 const void* disp_cp_chain_me,
1054 Bool mode64 );
1056 /* Patch the counter location into an existing ProfInc point. */
1057 extern VexInvalRange patchProfInc_MIPS ( VexEndness endness_host,
1058 void* place_to_patch,
1059 const ULong* location_of_counter,
1060 Bool mode64 );
1063 #endif /* ndef __VEX_HOST_MIPS_DEFS_H */
1065 /*---------------------------------------------------------------*/
1066 /*--- end host-mips_defs.h ---*/
1067 /*---------------------------------------------------------------*/