Statistics
| Branch: | Revision:

root / target-mips / translate.c @ 08ba7963

History | View | Annotate | Download (226.2 kB)

1
/*
2
 *  MIPS32 emulation for qemu: main translation routines.
3
 *
4
 *  Copyright (c) 2004-2005 Jocelyn Mayer
5
 *  Copyright (c) 2006 Marius Groeger (FPU operations)
6
 *  Copyright (c) 2006 Thiemo Seufer (MIPS32R2 support)
7
 *
8
 * This library is free software; you can redistribute it and/or
9
 * modify it under the terms of the GNU Lesser General Public
10
 * License as published by the Free Software Foundation; either
11
 * version 2 of the License, or (at your option) any later version.
12
 *
13
 * This library is distributed in the hope that it will be useful,
14
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16
 * Lesser General Public License for more details.
17
 *
18
 * You should have received a copy of the GNU Lesser General Public
19
 * License along with this library; if not, write to the Free Software
20
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
21
 */
22

    
23
#include <stdarg.h>
24
#include <stdlib.h>
25
#include <stdio.h>
26
#include <string.h>
27
#include <inttypes.h>
28

    
29
#include "cpu.h"
30
#include "exec-all.h"
31
#include "disas.h"
32
#include "helper.h"
33
#include "tcg-op.h"
34
#include "qemu-common.h"
35

    
36
//#define MIPS_DEBUG_DISAS
37
//#define MIPS_DEBUG_SIGN_EXTENSIONS
38
//#define MIPS_SINGLE_STEP
39

    
40
/* MIPS major opcodes */
41
#define MASK_OP_MAJOR(op)  (op & (0x3F << 26))
42

    
43
enum {
44
    /* indirect opcode tables */
45
    OPC_SPECIAL  = (0x00 << 26),
46
    OPC_REGIMM   = (0x01 << 26),
47
    OPC_CP0      = (0x10 << 26),
48
    OPC_CP1      = (0x11 << 26),
49
    OPC_CP2      = (0x12 << 26),
50
    OPC_CP3      = (0x13 << 26),
51
    OPC_SPECIAL2 = (0x1C << 26),
52
    OPC_SPECIAL3 = (0x1F << 26),
53
    /* arithmetic with immediate */
54
    OPC_ADDI     = (0x08 << 26),
55
    OPC_ADDIU    = (0x09 << 26),
56
    OPC_SLTI     = (0x0A << 26),
57
    OPC_SLTIU    = (0x0B << 26),
58
    OPC_ANDI     = (0x0C << 26),
59
    OPC_ORI      = (0x0D << 26),
60
    OPC_XORI     = (0x0E << 26),
61
    OPC_LUI      = (0x0F << 26),
62
    OPC_DADDI    = (0x18 << 26),
63
    OPC_DADDIU   = (0x19 << 26),
64
    /* Jump and branches */
65
    OPC_J        = (0x02 << 26),
66
    OPC_JAL      = (0x03 << 26),
67
    OPC_BEQ      = (0x04 << 26),  /* Unconditional if rs = rt = 0 (B) */
68
    OPC_BEQL     = (0x14 << 26),
69
    OPC_BNE      = (0x05 << 26),
70
    OPC_BNEL     = (0x15 << 26),
71
    OPC_BLEZ     = (0x06 << 26),
72
    OPC_BLEZL    = (0x16 << 26),
73
    OPC_BGTZ     = (0x07 << 26),
74
    OPC_BGTZL    = (0x17 << 26),
75
    OPC_JALX     = (0x1D << 26),  /* MIPS 16 only */
76
    /* Load and stores */
77
    OPC_LDL      = (0x1A << 26),
78
    OPC_LDR      = (0x1B << 26),
79
    OPC_LB       = (0x20 << 26),
80
    OPC_LH       = (0x21 << 26),
81
    OPC_LWL      = (0x22 << 26),
82
    OPC_LW       = (0x23 << 26),
83
    OPC_LBU      = (0x24 << 26),
84
    OPC_LHU      = (0x25 << 26),
85
    OPC_LWR      = (0x26 << 26),
86
    OPC_LWU      = (0x27 << 26),
87
    OPC_SB       = (0x28 << 26),
88
    OPC_SH       = (0x29 << 26),
89
    OPC_SWL      = (0x2A << 26),
90
    OPC_SW       = (0x2B << 26),
91
    OPC_SDL      = (0x2C << 26),
92
    OPC_SDR      = (0x2D << 26),
93
    OPC_SWR      = (0x2E << 26),
94
    OPC_LL       = (0x30 << 26),
95
    OPC_LLD      = (0x34 << 26),
96
    OPC_LD       = (0x37 << 26),
97
    OPC_SC       = (0x38 << 26),
98
    OPC_SCD      = (0x3C << 26),
99
    OPC_SD       = (0x3F << 26),
100
    /* Floating point load/store */
101
    OPC_LWC1     = (0x31 << 26),
102
    OPC_LWC2     = (0x32 << 26),
103
    OPC_LDC1     = (0x35 << 26),
104
    OPC_LDC2     = (0x36 << 26),
105
    OPC_SWC1     = (0x39 << 26),
106
    OPC_SWC2     = (0x3A << 26),
107
    OPC_SDC1     = (0x3D << 26),
108
    OPC_SDC2     = (0x3E << 26),
109
    /* MDMX ASE specific */
110
    OPC_MDMX     = (0x1E << 26),
111
    /* Cache and prefetch */
112
    OPC_CACHE    = (0x2F << 26),
113
    OPC_PREF     = (0x33 << 26),
114
    /* Reserved major opcode */
115
    OPC_MAJOR3B_RESERVED = (0x3B << 26),
116
};
117

    
118
/* MIPS special opcodes */
119
#define MASK_SPECIAL(op)   MASK_OP_MAJOR(op) | (op & 0x3F)
120

    
121
enum {
122
    /* Shifts */
123
    OPC_SLL      = 0x00 | OPC_SPECIAL,
124
    /* NOP is SLL r0, r0, 0   */
125
    /* SSNOP is SLL r0, r0, 1 */
126
    /* EHB is SLL r0, r0, 3 */
127
    OPC_SRL      = 0x02 | OPC_SPECIAL, /* also ROTR */
128
    OPC_SRA      = 0x03 | OPC_SPECIAL,
129
    OPC_SLLV     = 0x04 | OPC_SPECIAL,
130
    OPC_SRLV     = 0x06 | OPC_SPECIAL, /* also ROTRV */
131
    OPC_SRAV     = 0x07 | OPC_SPECIAL,
132
    OPC_DSLLV    = 0x14 | OPC_SPECIAL,
133
    OPC_DSRLV    = 0x16 | OPC_SPECIAL, /* also DROTRV */
134
    OPC_DSRAV    = 0x17 | OPC_SPECIAL,
135
    OPC_DSLL     = 0x38 | OPC_SPECIAL,
136
    OPC_DSRL     = 0x3A | OPC_SPECIAL, /* also DROTR */
137
    OPC_DSRA     = 0x3B | OPC_SPECIAL,
138
    OPC_DSLL32   = 0x3C | OPC_SPECIAL,
139
    OPC_DSRL32   = 0x3E | OPC_SPECIAL, /* also DROTR32 */
140
    OPC_DSRA32   = 0x3F | OPC_SPECIAL,
141
    /* Multiplication / division */
142
    OPC_MULT     = 0x18 | OPC_SPECIAL,
143
    OPC_MULTU    = 0x19 | OPC_SPECIAL,
144
    OPC_DIV      = 0x1A | OPC_SPECIAL,
145
    OPC_DIVU     = 0x1B | OPC_SPECIAL,
146
    OPC_DMULT    = 0x1C | OPC_SPECIAL,
147
    OPC_DMULTU   = 0x1D | OPC_SPECIAL,
148
    OPC_DDIV     = 0x1E | OPC_SPECIAL,
149
    OPC_DDIVU    = 0x1F | OPC_SPECIAL,
150
    /* 2 registers arithmetic / logic */
151
    OPC_ADD      = 0x20 | OPC_SPECIAL,
152
    OPC_ADDU     = 0x21 | OPC_SPECIAL,
153
    OPC_SUB      = 0x22 | OPC_SPECIAL,
154
    OPC_SUBU     = 0x23 | OPC_SPECIAL,
155
    OPC_AND      = 0x24 | OPC_SPECIAL,
156
    OPC_OR       = 0x25 | OPC_SPECIAL,
157
    OPC_XOR      = 0x26 | OPC_SPECIAL,
158
    OPC_NOR      = 0x27 | OPC_SPECIAL,
159
    OPC_SLT      = 0x2A | OPC_SPECIAL,
160
    OPC_SLTU     = 0x2B | OPC_SPECIAL,
161
    OPC_DADD     = 0x2C | OPC_SPECIAL,
162
    OPC_DADDU    = 0x2D | OPC_SPECIAL,
163
    OPC_DSUB     = 0x2E | OPC_SPECIAL,
164
    OPC_DSUBU    = 0x2F | OPC_SPECIAL,
165
    /* Jumps */
166
    OPC_JR       = 0x08 | OPC_SPECIAL, /* Also JR.HB */
167
    OPC_JALR     = 0x09 | OPC_SPECIAL, /* Also JALR.HB */
168
    /* Traps */
169
    OPC_TGE      = 0x30 | OPC_SPECIAL,
170
    OPC_TGEU     = 0x31 | OPC_SPECIAL,
171
    OPC_TLT      = 0x32 | OPC_SPECIAL,
172
    OPC_TLTU     = 0x33 | OPC_SPECIAL,
173
    OPC_TEQ      = 0x34 | OPC_SPECIAL,
174
    OPC_TNE      = 0x36 | OPC_SPECIAL,
175
    /* HI / LO registers load & stores */
176
    OPC_MFHI     = 0x10 | OPC_SPECIAL,
177
    OPC_MTHI     = 0x11 | OPC_SPECIAL,
178
    OPC_MFLO     = 0x12 | OPC_SPECIAL,
179
    OPC_MTLO     = 0x13 | OPC_SPECIAL,
180
    /* Conditional moves */
181
    OPC_MOVZ     = 0x0A | OPC_SPECIAL,
182
    OPC_MOVN     = 0x0B | OPC_SPECIAL,
183

    
184
    OPC_MOVCI    = 0x01 | OPC_SPECIAL,
185

    
186
    /* Special */
187
    OPC_PMON     = 0x05 | OPC_SPECIAL, /* inofficial */
188
    OPC_SYSCALL  = 0x0C | OPC_SPECIAL,
189
    OPC_BREAK    = 0x0D | OPC_SPECIAL,
190
    OPC_SPIM     = 0x0E | OPC_SPECIAL, /* inofficial */
191
    OPC_SYNC     = 0x0F | OPC_SPECIAL,
192

    
193
    OPC_SPECIAL15_RESERVED = 0x15 | OPC_SPECIAL,
194
    OPC_SPECIAL28_RESERVED = 0x28 | OPC_SPECIAL,
195
    OPC_SPECIAL29_RESERVED = 0x29 | OPC_SPECIAL,
196
    OPC_SPECIAL35_RESERVED = 0x35 | OPC_SPECIAL,
197
    OPC_SPECIAL37_RESERVED = 0x37 | OPC_SPECIAL,
198
    OPC_SPECIAL39_RESERVED = 0x39 | OPC_SPECIAL,
199
    OPC_SPECIAL3D_RESERVED = 0x3D | OPC_SPECIAL,
200
};
201

    
202
/* Multiplication variants of the vr54xx. */
203
#define MASK_MUL_VR54XX(op)   MASK_SPECIAL(op) | (op & (0x1F << 6))
204

    
205
enum {
206
    OPC_VR54XX_MULS    = (0x03 << 6) | OPC_MULT,
207
    OPC_VR54XX_MULSU   = (0x03 << 6) | OPC_MULTU,
208
    OPC_VR54XX_MACC    = (0x05 << 6) | OPC_MULT,
209
    OPC_VR54XX_MACCU   = (0x05 << 6) | OPC_MULTU,
210
    OPC_VR54XX_MSAC    = (0x07 << 6) | OPC_MULT,
211
    OPC_VR54XX_MSACU   = (0x07 << 6) | OPC_MULTU,
212
    OPC_VR54XX_MULHI   = (0x09 << 6) | OPC_MULT,
213
    OPC_VR54XX_MULHIU  = (0x09 << 6) | OPC_MULTU,
214
    OPC_VR54XX_MULSHI  = (0x0B << 6) | OPC_MULT,
215
    OPC_VR54XX_MULSHIU = (0x0B << 6) | OPC_MULTU,
216
    OPC_VR54XX_MACCHI  = (0x0D << 6) | OPC_MULT,
217
    OPC_VR54XX_MACCHIU = (0x0D << 6) | OPC_MULTU,
218
    OPC_VR54XX_MSACHI  = (0x0F << 6) | OPC_MULT,
219
    OPC_VR54XX_MSACHIU = (0x0F << 6) | OPC_MULTU,
220
};
221

    
222
/* REGIMM (rt field) opcodes */
223
#define MASK_REGIMM(op)    MASK_OP_MAJOR(op) | (op & (0x1F << 16))
224

    
225
enum {
226
    OPC_BLTZ     = (0x00 << 16) | OPC_REGIMM,
227
    OPC_BLTZL    = (0x02 << 16) | OPC_REGIMM,
228
    OPC_BGEZ     = (0x01 << 16) | OPC_REGIMM,
229
    OPC_BGEZL    = (0x03 << 16) | OPC_REGIMM,
230
    OPC_BLTZAL   = (0x10 << 16) | OPC_REGIMM,
231
    OPC_BLTZALL  = (0x12 << 16) | OPC_REGIMM,
232
    OPC_BGEZAL   = (0x11 << 16) | OPC_REGIMM,
233
    OPC_BGEZALL  = (0x13 << 16) | OPC_REGIMM,
234
    OPC_TGEI     = (0x08 << 16) | OPC_REGIMM,
235
    OPC_TGEIU    = (0x09 << 16) | OPC_REGIMM,
236
    OPC_TLTI     = (0x0A << 16) | OPC_REGIMM,
237
    OPC_TLTIU    = (0x0B << 16) | OPC_REGIMM,
238
    OPC_TEQI     = (0x0C << 16) | OPC_REGIMM,
239
    OPC_TNEI     = (0x0E << 16) | OPC_REGIMM,
240
    OPC_SYNCI    = (0x1F << 16) | OPC_REGIMM,
241
};
242

    
243
/* Special2 opcodes */
244
#define MASK_SPECIAL2(op)  MASK_OP_MAJOR(op) | (op & 0x3F)
245

    
246
enum {
247
    /* Multiply & xxx operations */
248
    OPC_MADD     = 0x00 | OPC_SPECIAL2,
249
    OPC_MADDU    = 0x01 | OPC_SPECIAL2,
250
    OPC_MUL      = 0x02 | OPC_SPECIAL2,
251
    OPC_MSUB     = 0x04 | OPC_SPECIAL2,
252
    OPC_MSUBU    = 0x05 | OPC_SPECIAL2,
253
    /* Misc */
254
    OPC_CLZ      = 0x20 | OPC_SPECIAL2,
255
    OPC_CLO      = 0x21 | OPC_SPECIAL2,
256
    OPC_DCLZ     = 0x24 | OPC_SPECIAL2,
257
    OPC_DCLO     = 0x25 | OPC_SPECIAL2,
258
    /* Special */
259
    OPC_SDBBP    = 0x3F | OPC_SPECIAL2,
260
};
261

    
262
/* Special3 opcodes */
263
#define MASK_SPECIAL3(op)  MASK_OP_MAJOR(op) | (op & 0x3F)
264

    
265
enum {
266
    OPC_EXT      = 0x00 | OPC_SPECIAL3,
267
    OPC_DEXTM    = 0x01 | OPC_SPECIAL3,
268
    OPC_DEXTU    = 0x02 | OPC_SPECIAL3,
269
    OPC_DEXT     = 0x03 | OPC_SPECIAL3,
270
    OPC_INS      = 0x04 | OPC_SPECIAL3,
271
    OPC_DINSM    = 0x05 | OPC_SPECIAL3,
272
    OPC_DINSU    = 0x06 | OPC_SPECIAL3,
273
    OPC_DINS     = 0x07 | OPC_SPECIAL3,
274
    OPC_FORK     = 0x08 | OPC_SPECIAL3,
275
    OPC_YIELD    = 0x09 | OPC_SPECIAL3,
276
    OPC_BSHFL    = 0x20 | OPC_SPECIAL3,
277
    OPC_DBSHFL   = 0x24 | OPC_SPECIAL3,
278
    OPC_RDHWR    = 0x3B | OPC_SPECIAL3,
279
};
280

    
281
/* BSHFL opcodes */
282
#define MASK_BSHFL(op)     MASK_SPECIAL3(op) | (op & (0x1F << 6))
283

    
284
enum {
285
    OPC_WSBH     = (0x02 << 6) | OPC_BSHFL,
286
    OPC_SEB      = (0x10 << 6) | OPC_BSHFL,
287
    OPC_SEH      = (0x18 << 6) | OPC_BSHFL,
288
};
289

    
290
/* DBSHFL opcodes */
291
#define MASK_DBSHFL(op)    MASK_SPECIAL3(op) | (op & (0x1F << 6))
292

    
293
enum {
294
    OPC_DSBH     = (0x02 << 6) | OPC_DBSHFL,
295
    OPC_DSHD     = (0x05 << 6) | OPC_DBSHFL,
296
};
297

    
298
/* Coprocessor 0 (rs field) */
299
#define MASK_CP0(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
300

    
301
enum {
302
    OPC_MFC0     = (0x00 << 21) | OPC_CP0,
303
    OPC_DMFC0    = (0x01 << 21) | OPC_CP0,
304
    OPC_MTC0     = (0x04 << 21) | OPC_CP0,
305
    OPC_DMTC0    = (0x05 << 21) | OPC_CP0,
306
    OPC_MFTR     = (0x08 << 21) | OPC_CP0,
307
    OPC_RDPGPR   = (0x0A << 21) | OPC_CP0,
308
    OPC_MFMC0    = (0x0B << 21) | OPC_CP0,
309
    OPC_MTTR     = (0x0C << 21) | OPC_CP0,
310
    OPC_WRPGPR   = (0x0E << 21) | OPC_CP0,
311
    OPC_C0       = (0x10 << 21) | OPC_CP0,
312
    OPC_C0_FIRST = (0x10 << 21) | OPC_CP0,
313
    OPC_C0_LAST  = (0x1F << 21) | OPC_CP0,
314
};
315

    
316
/* MFMC0 opcodes */
317
#define MASK_MFMC0(op)     MASK_CP0(op) | (op & 0xFFFF)
318

    
319
enum {
320
    OPC_DMT      = 0x01 | (0 << 5) | (0x0F << 6) | (0x01 << 11) | OPC_MFMC0,
321
    OPC_EMT      = 0x01 | (1 << 5) | (0x0F << 6) | (0x01 << 11) | OPC_MFMC0,
322
    OPC_DVPE     = 0x01 | (0 << 5) | OPC_MFMC0,
323
    OPC_EVPE     = 0x01 | (1 << 5) | OPC_MFMC0,
324
    OPC_DI       = (0 << 5) | (0x0C << 11) | OPC_MFMC0,
325
    OPC_EI       = (1 << 5) | (0x0C << 11) | OPC_MFMC0,
326
};
327

    
328
/* Coprocessor 0 (with rs == C0) */
329
#define MASK_C0(op)        MASK_CP0(op) | (op & 0x3F)
330

    
331
enum {
332
    OPC_TLBR     = 0x01 | OPC_C0,
333
    OPC_TLBWI    = 0x02 | OPC_C0,
334
    OPC_TLBWR    = 0x06 | OPC_C0,
335
    OPC_TLBP     = 0x08 | OPC_C0,
336
    OPC_RFE      = 0x10 | OPC_C0,
337
    OPC_ERET     = 0x18 | OPC_C0,
338
    OPC_DERET    = 0x1F | OPC_C0,
339
    OPC_WAIT     = 0x20 | OPC_C0,
340
};
341

    
342
/* Coprocessor 1 (rs field) */
343
#define MASK_CP1(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
344

    
345
enum {
346
    OPC_MFC1     = (0x00 << 21) | OPC_CP1,
347
    OPC_DMFC1    = (0x01 << 21) | OPC_CP1,
348
    OPC_CFC1     = (0x02 << 21) | OPC_CP1,
349
    OPC_MFHC1    = (0x03 << 21) | OPC_CP1,
350
    OPC_MTC1     = (0x04 << 21) | OPC_CP1,
351
    OPC_DMTC1    = (0x05 << 21) | OPC_CP1,
352
    OPC_CTC1     = (0x06 << 21) | OPC_CP1,
353
    OPC_MTHC1    = (0x07 << 21) | OPC_CP1,
354
    OPC_BC1      = (0x08 << 21) | OPC_CP1, /* bc */
355
    OPC_BC1ANY2  = (0x09 << 21) | OPC_CP1,
356
    OPC_BC1ANY4  = (0x0A << 21) | OPC_CP1,
357
    OPC_S_FMT    = (0x10 << 21) | OPC_CP1, /* 16: fmt=single fp */
358
    OPC_D_FMT    = (0x11 << 21) | OPC_CP1, /* 17: fmt=double fp */
359
    OPC_E_FMT    = (0x12 << 21) | OPC_CP1, /* 18: fmt=extended fp */
360
    OPC_Q_FMT    = (0x13 << 21) | OPC_CP1, /* 19: fmt=quad fp */
361
    OPC_W_FMT    = (0x14 << 21) | OPC_CP1, /* 20: fmt=32bit fixed */
362
    OPC_L_FMT    = (0x15 << 21) | OPC_CP1, /* 21: fmt=64bit fixed */
363
    OPC_PS_FMT   = (0x16 << 21) | OPC_CP1, /* 22: fmt=paired single fp */
364
};
365

    
366
#define MASK_CP1_FUNC(op)       MASK_CP1(op) | (op & 0x3F)
367
#define MASK_BC1(op)            MASK_CP1(op) | (op & (0x3 << 16))
368

    
369
enum {
370
    OPC_BC1F     = (0x00 << 16) | OPC_BC1,
371
    OPC_BC1T     = (0x01 << 16) | OPC_BC1,
372
    OPC_BC1FL    = (0x02 << 16) | OPC_BC1,
373
    OPC_BC1TL    = (0x03 << 16) | OPC_BC1,
374
};
375

    
376
enum {
377
    OPC_BC1FANY2     = (0x00 << 16) | OPC_BC1ANY2,
378
    OPC_BC1TANY2     = (0x01 << 16) | OPC_BC1ANY2,
379
};
380

    
381
enum {
382
    OPC_BC1FANY4     = (0x00 << 16) | OPC_BC1ANY4,
383
    OPC_BC1TANY4     = (0x01 << 16) | OPC_BC1ANY4,
384
};
385

    
386
#define MASK_CP2(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
387

    
388
enum {
389
    OPC_MFC2    = (0x00 << 21) | OPC_CP2,
390
    OPC_DMFC2   = (0x01 << 21) | OPC_CP2,
391
    OPC_CFC2    = (0x02 << 21) | OPC_CP2,
392
    OPC_MFHC2   = (0x03 << 21) | OPC_CP2,
393
    OPC_MTC2    = (0x04 << 21) | OPC_CP2,
394
    OPC_DMTC2   = (0x05 << 21) | OPC_CP2,
395
    OPC_CTC2    = (0x06 << 21) | OPC_CP2,
396
    OPC_MTHC2   = (0x07 << 21) | OPC_CP2,
397
    OPC_BC2     = (0x08 << 21) | OPC_CP2,
398
};
399

    
400
#define MASK_CP3(op)       MASK_OP_MAJOR(op) | (op & 0x3F)
401

    
402
enum {
403
    OPC_LWXC1   = 0x00 | OPC_CP3,
404
    OPC_LDXC1   = 0x01 | OPC_CP3,
405
    OPC_LUXC1   = 0x05 | OPC_CP3,
406
    OPC_SWXC1   = 0x08 | OPC_CP3,
407
    OPC_SDXC1   = 0x09 | OPC_CP3,
408
    OPC_SUXC1   = 0x0D | OPC_CP3,
409
    OPC_PREFX   = 0x0F | OPC_CP3,
410
    OPC_ALNV_PS = 0x1E | OPC_CP3,
411
    OPC_MADD_S  = 0x20 | OPC_CP3,
412
    OPC_MADD_D  = 0x21 | OPC_CP3,
413
    OPC_MADD_PS = 0x26 | OPC_CP3,
414
    OPC_MSUB_S  = 0x28 | OPC_CP3,
415
    OPC_MSUB_D  = 0x29 | OPC_CP3,
416
    OPC_MSUB_PS = 0x2E | OPC_CP3,
417
    OPC_NMADD_S = 0x30 | OPC_CP3,
418
    OPC_NMADD_D = 0x31 | OPC_CP3,
419
    OPC_NMADD_PS= 0x36 | OPC_CP3,
420
    OPC_NMSUB_S = 0x38 | OPC_CP3,
421
    OPC_NMSUB_D = 0x39 | OPC_CP3,
422
    OPC_NMSUB_PS= 0x3E | OPC_CP3,
423
};
424

    
425
/* global register indices */
426
static TCGv cpu_env, current_tc_gprs, current_tc_hi, current_fpu, cpu_T[2];
427

    
428
/* FPU TNs, global for now. */
429
static TCGv fpu32_T[3], fpu64_T[3], fpu32h_T[3];
430

    
431
static inline void tcg_gen_helper_0_1i(void *func, TCGv arg)
432
{
433
    TCGv t = tcg_const_i32(arg);
434

    
435
    tcg_gen_helper_0_1(func, t);
436
    tcg_temp_free(t);
437
}
438

    
439
static inline void tcg_gen_helper_0_2ii(void *func, TCGv arg1, TCGv arg2)
440
{
441
    TCGv t1 = tcg_const_i32(arg1);
442
    TCGv t2 = tcg_const_i32(arg2);
443

    
444
    tcg_gen_helper_0_2(func, t1, t2);
445
    tcg_temp_free(t1);
446
    tcg_temp_free(t2);
447
}
448

    
449
typedef struct DisasContext {
450
    struct TranslationBlock *tb;
451
    target_ulong pc, saved_pc;
452
    uint32_t opcode;
453
    uint32_t fp_status;
454
    /* Routine used to access memory */
455
    int mem_idx;
456
    uint32_t hflags, saved_hflags;
457
    int bstate;
458
    target_ulong btarget;
459
} DisasContext;
460

    
461
enum {
462
    BS_NONE     = 0, /* We go out of the TB without reaching a branch or an
463
                      * exception condition
464
                      */
465
    BS_STOP     = 1, /* We want to stop translation for any reason */
466
    BS_BRANCH   = 2, /* We reached a branch condition     */
467
    BS_EXCP     = 3, /* We reached an exception condition */
468
};
469

    
470
static const char *regnames[] =
471
    { "r0", "at", "v0", "v1", "a0", "a1", "a2", "a3",
472
      "t0", "t1", "t2", "t3", "t4", "t5", "t6", "t7",
473
      "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7",
474
      "t8", "t9", "k0", "k1", "gp", "sp", "s8", "ra", };
475

    
476
static const char *fregnames[] =
477
    { "f0",  "f1",  "f2",  "f3",  "f4",  "f5",  "f6",  "f7",
478
      "f8",  "f9",  "f10", "f11", "f12", "f13", "f14", "f15",
479
      "f16", "f17", "f18", "f19", "f20", "f21", "f22", "f23",
480
      "f24", "f25", "f26", "f27", "f28", "f29", "f30", "f31", };
481

    
482
#ifdef MIPS_DEBUG_DISAS
483
#define MIPS_DEBUG(fmt, args...)                                              \
484
do {                                                                          \
485
    if (loglevel & CPU_LOG_TB_IN_ASM) {                                       \
486
        fprintf(logfile, TARGET_FMT_lx ": %08x " fmt "\n",                    \
487
                ctx->pc, ctx->opcode , ##args);                               \
488
    }                                                                         \
489
} while (0)
490
#else
491
#define MIPS_DEBUG(fmt, args...) do { } while(0)
492
#endif
493

    
494
#define MIPS_INVAL(op)                                                        \
495
do {                                                                          \
496
    MIPS_DEBUG("Invalid %s %03x %03x %03x", op, ctx->opcode >> 26,            \
497
               ctx->opcode & 0x3F, ((ctx->opcode >> 16) & 0x1F));             \
498
} while (0)
499

    
500
/* General purpose registers moves. */
501
static inline void gen_load_gpr (TCGv t, int reg)
502
{
503
    if (reg == 0)
504
        tcg_gen_movi_tl(t, 0);
505
    else
506
        tcg_gen_ld_tl(t, current_tc_gprs, sizeof(target_ulong) * reg);
507
}
508

    
509
static inline void gen_store_gpr (TCGv t, int reg)
510
{
511
    if (reg != 0)
512
        tcg_gen_st_tl(t, current_tc_gprs, sizeof(target_ulong) * reg);
513
}
514

    
515
/* Moves to/from HI and LO registers.  */
516
static inline void gen_load_LO (TCGv t, int reg)
517
{
518
    tcg_gen_ld_tl(t, current_tc_hi,
519
                  offsetof(CPUState, LO)
520
                  - offsetof(CPUState, HI)
521
                  + sizeof(target_ulong) * reg);
522
}
523

    
524
static inline void gen_store_LO (TCGv t, int reg)
525
{
526
    tcg_gen_st_tl(t, current_tc_hi,
527
                  offsetof(CPUState, LO)
528
                  - offsetof(CPUState, HI)
529
                  + sizeof(target_ulong) * reg);
530
}
531

    
532
static inline void gen_load_HI (TCGv t, int reg)
533
{
534
    tcg_gen_ld_tl(t, current_tc_hi, sizeof(target_ulong) * reg);
535
}
536

    
537
static inline void gen_store_HI (TCGv t, int reg)
538
{
539
    tcg_gen_st_tl(t, current_tc_hi, sizeof(target_ulong) * reg);
540
}
541

    
542
/* Moves to/from shadow registers. */
543
static inline void gen_load_srsgpr (TCGv t, int reg)
544
{
545
    if (reg == 0)
546
        tcg_gen_movi_tl(t, 0);
547
    else {
548
        TCGv r_tmp = tcg_temp_new(TCG_TYPE_I32);
549

    
550
        tcg_gen_ld_i32(r_tmp, cpu_env, offsetof(CPUState, CP0_SRSCtl));
551
        tcg_gen_shri_i32(r_tmp, r_tmp, CP0SRSCtl_PSS);
552
        tcg_gen_andi_i32(r_tmp, r_tmp, 0xf);
553
        tcg_gen_muli_i32(r_tmp, r_tmp, sizeof(target_ulong) * 32);
554
        tcg_gen_add_i32(r_tmp, cpu_env, r_tmp);
555

    
556
        tcg_gen_ld_tl(t, r_tmp, sizeof(target_ulong) * reg);
557
        tcg_temp_free(r_tmp);
558
    }
559
}
560

    
561
static inline void gen_store_srsgpr (TCGv t, int reg)
562
{
563
    if (reg != 0) {
564
        TCGv r_tmp = tcg_temp_new(TCG_TYPE_I32);
565

    
566
        tcg_gen_ld_i32(r_tmp, cpu_env, offsetof(CPUState, CP0_SRSCtl));
567
        tcg_gen_shri_i32(r_tmp, r_tmp, CP0SRSCtl_PSS);
568
        tcg_gen_andi_i32(r_tmp, r_tmp, 0xf);
569
        tcg_gen_muli_i32(r_tmp, r_tmp, sizeof(target_ulong) * 32);
570
        tcg_gen_add_i32(r_tmp, cpu_env, r_tmp);
571

    
572
        tcg_gen_st_tl(t, r_tmp, sizeof(target_ulong) * reg);
573
        tcg_temp_free(r_tmp);
574
    }
575
}
576

    
577
/* Floating point register moves. */
578
static inline void gen_load_fpr32 (TCGv t, int reg)
579
{
580
    tcg_gen_ld_i32(t, current_fpu, 8 * reg + 4 * FP_ENDIAN_IDX);
581
}
582

    
583
static inline void gen_store_fpr32 (TCGv t, int reg)
584
{
585
    tcg_gen_st_i32(t, current_fpu, 8 * reg + 4 * FP_ENDIAN_IDX);
586
}
587

    
588
static inline void gen_load_fpr64 (DisasContext *ctx, TCGv t, int reg)
589
{
590
    if (ctx->hflags & MIPS_HFLAG_F64) {
591
        tcg_gen_ld_i64(t, current_fpu, 8 * reg);
592
    } else {
593
        TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
594
        TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
595

    
596
        tcg_gen_ld_i32(r_tmp1, current_fpu, 8 * (reg | 1) + 4 * FP_ENDIAN_IDX);
597
        tcg_gen_extu_i32_i64(t, r_tmp1);
598
        tcg_gen_shli_i64(t, t, 32);
599
        tcg_gen_ld_i32(r_tmp1, current_fpu, 8 * (reg & ~1) + 4 * FP_ENDIAN_IDX);
600
        tcg_gen_extu_i32_i64(r_tmp2, r_tmp1);
601
        tcg_gen_or_i64(t, t, r_tmp2);
602
        tcg_temp_free(r_tmp1);
603
        tcg_temp_free(r_tmp2);
604
    }
605
}
606

    
607
static inline void gen_store_fpr64 (DisasContext *ctx, TCGv t, int reg)
608
{
609
    if (ctx->hflags & MIPS_HFLAG_F64) {
610
        tcg_gen_st_i64(t, current_fpu, 8 * reg);
611
    } else {
612
        TCGv r_tmp = tcg_temp_new(TCG_TYPE_I32);
613

    
614
        tcg_gen_trunc_i64_i32(r_tmp, t);
615
        tcg_gen_st_i32(r_tmp, current_fpu, 8 * (reg & ~1) + 4 * FP_ENDIAN_IDX);
616
        tcg_gen_shri_i64(t, t, 32);
617
        tcg_gen_trunc_i64_i32(r_tmp, t);
618
        tcg_gen_st_i32(r_tmp, current_fpu, 8 * (reg | 1) + 4 * FP_ENDIAN_IDX);
619
        tcg_temp_free(r_tmp);
620
    }
621
}
622

    
623
static inline void gen_load_fpr32h (TCGv t, int reg)
624
{
625
    tcg_gen_ld_i32(t, current_fpu, 8 * reg + 4 * !FP_ENDIAN_IDX);
626
}
627

    
628
static inline void gen_store_fpr32h (TCGv t, int reg)
629
{
630
    tcg_gen_st_i32(t, current_fpu, 8 * reg + 4 * !FP_ENDIAN_IDX);
631
}
632

    
633
#define FOP_CONDS(type, fmt)                                              \
634
static GenOpFunc1 * fcmp ## type ## _ ## fmt ## _table[16] = {            \
635
    do_cmp ## type ## _ ## fmt ## _f,                                     \
636
    do_cmp ## type ## _ ## fmt ## _un,                                    \
637
    do_cmp ## type ## _ ## fmt ## _eq,                                    \
638
    do_cmp ## type ## _ ## fmt ## _ueq,                                   \
639
    do_cmp ## type ## _ ## fmt ## _olt,                                   \
640
    do_cmp ## type ## _ ## fmt ## _ult,                                   \
641
    do_cmp ## type ## _ ## fmt ## _ole,                                   \
642
    do_cmp ## type ## _ ## fmt ## _ule,                                   \
643
    do_cmp ## type ## _ ## fmt ## _sf,                                    \
644
    do_cmp ## type ## _ ## fmt ## _ngle,                                  \
645
    do_cmp ## type ## _ ## fmt ## _seq,                                   \
646
    do_cmp ## type ## _ ## fmt ## _ngl,                                   \
647
    do_cmp ## type ## _ ## fmt ## _lt,                                    \
648
    do_cmp ## type ## _ ## fmt ## _nge,                                   \
649
    do_cmp ## type ## _ ## fmt ## _le,                                    \
650
    do_cmp ## type ## _ ## fmt ## _ngt,                                   \
651
};                                                                        \
652
static inline void gen_cmp ## type ## _ ## fmt(int n, long cc)            \
653
{                                                                         \
654
    tcg_gen_helper_0_1i(fcmp ## type ## _ ## fmt ## _table[n], cc);       \
655
}
656

    
657
FOP_CONDS(, d)
658
FOP_CONDS(abs, d)
659
FOP_CONDS(, s)
660
FOP_CONDS(abs, s)
661
FOP_CONDS(, ps)
662
FOP_CONDS(abs, ps)
663
#undef FOP_CONDS
664

    
665
/* Tests */
666
#define OP_COND(name, cond)                                   \
667
void glue(gen_op_, name) (void)                               \
668
{                                                             \
669
    int l1 = gen_new_label();                                 \
670
    int l2 = gen_new_label();                                 \
671
                                                              \
672
    tcg_gen_brcond_tl(cond, cpu_T[0], cpu_T[1], l1);          \
673
    tcg_gen_movi_tl(cpu_T[0], 0);                             \
674
    tcg_gen_br(l2);                                           \
675
    gen_set_label(l1);                                        \
676
    tcg_gen_movi_tl(cpu_T[0], 1);                             \
677
    gen_set_label(l2);                                        \
678
}
679
OP_COND(eq, TCG_COND_EQ);
680
OP_COND(ne, TCG_COND_NE);
681
OP_COND(ge, TCG_COND_GE);
682
OP_COND(geu, TCG_COND_GEU);
683
OP_COND(lt, TCG_COND_LT);
684
OP_COND(ltu, TCG_COND_LTU);
685
#undef OP_COND
686

    
687
#define OP_CONDI(name, cond)                                  \
688
void glue(gen_op_, name) (target_ulong val)                   \
689
{                                                             \
690
    int l1 = gen_new_label();                                 \
691
    int l2 = gen_new_label();                                 \
692
                                                              \
693
    tcg_gen_brcondi_tl(cond, cpu_T[0], val, l1);              \
694
    tcg_gen_movi_tl(cpu_T[0], 0);                             \
695
    tcg_gen_br(l2);                                           \
696
    gen_set_label(l1);                                        \
697
    tcg_gen_movi_tl(cpu_T[0], 1);                             \
698
    gen_set_label(l2);                                        \
699
}
700
OP_CONDI(lti, TCG_COND_LT);
701
OP_CONDI(ltiu, TCG_COND_LTU);
702
#undef OP_CONDI
703

    
704
#define OP_CONDZ(name, cond)                                  \
705
void glue(gen_op_, name) (void)                               \
706
{                                                             \
707
    int l1 = gen_new_label();                                 \
708
    int l2 = gen_new_label();                                 \
709
                                                              \
710
    tcg_gen_brcondi_tl(cond, cpu_T[0], 0, l1);                \
711
    tcg_gen_movi_tl(cpu_T[0], 0);                             \
712
    tcg_gen_br(l2);                                           \
713
    gen_set_label(l1);                                        \
714
    tcg_gen_movi_tl(cpu_T[0], 1);                             \
715
    gen_set_label(l2);                                        \
716
}
717
OP_CONDZ(gez, TCG_COND_GE);
718
OP_CONDZ(gtz, TCG_COND_GT);
719
OP_CONDZ(lez, TCG_COND_LE);
720
OP_CONDZ(ltz, TCG_COND_LT);
721
#undef OP_CONDZ
722

    
723
static inline void gen_save_pc(target_ulong pc)
724
{
725
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_TL);
726
    TCGv r_tc_off = tcg_temp_new(TCG_TYPE_I32);
727
    TCGv r_tc_off_ptr = tcg_temp_new(TCG_TYPE_PTR);
728
    TCGv r_ptr = tcg_temp_new(TCG_TYPE_PTR);
729

    
730
    tcg_gen_movi_tl(r_tmp, pc);
731
    tcg_gen_ld_i32(r_tc_off, cpu_env, offsetof(CPUState, current_tc));
732
    tcg_gen_muli_i32(r_tc_off, r_tc_off, sizeof(target_ulong));
733
    tcg_gen_ext_i32_ptr(r_tc_off_ptr, r_tc_off);
734
    tcg_gen_add_ptr(r_ptr, cpu_env, r_tc_off_ptr);
735
    tcg_gen_st_tl(r_tmp, r_ptr, offsetof(CPUState, PC));
736
    tcg_temp_free(r_tc_off);
737
    tcg_temp_free(r_tc_off_ptr);
738
    tcg_temp_free(r_ptr);
739
    tcg_temp_free(r_tmp);
740
}
741

    
742
static inline void gen_breg_pc(void)
743
{
744
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_TL);
745
    TCGv r_tc_off = tcg_temp_new(TCG_TYPE_I32);
746
    TCGv r_tc_off_ptr = tcg_temp_new(TCG_TYPE_PTR);
747
    TCGv r_ptr = tcg_temp_new(TCG_TYPE_PTR);
748

    
749
    tcg_gen_ld_tl(r_tmp, cpu_env, offsetof(CPUState, btarget));
750
    tcg_gen_ld_i32(r_tc_off, cpu_env, offsetof(CPUState, current_tc));
751
    tcg_gen_muli_i32(r_tc_off, r_tc_off, sizeof(target_ulong));
752
    tcg_gen_ext_i32_ptr(r_tc_off_ptr, r_tc_off);
753
    tcg_gen_add_ptr(r_ptr, cpu_env, r_tc_off_ptr);
754
    tcg_gen_st_tl(r_tmp, r_ptr, offsetof(CPUState, PC));
755
    tcg_temp_free(r_tc_off);
756
    tcg_temp_free(r_tc_off_ptr);
757
    tcg_temp_free(r_ptr);
758
    tcg_temp_free(r_tmp);
759
}
760

    
761
static inline void gen_save_btarget(target_ulong btarget)
762
{
763
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_TL);
764

    
765
    tcg_gen_movi_tl(r_tmp, btarget);
766
    tcg_gen_st_tl(r_tmp, cpu_env, offsetof(CPUState, btarget));
767
    tcg_temp_free(r_tmp);
768
}
769

    
770
static always_inline void gen_save_breg_target(int reg)
771
{
772
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_TL);
773

    
774
    gen_load_gpr(r_tmp, reg);
775
    tcg_gen_st_tl(r_tmp, cpu_env, offsetof(CPUState, btarget));
776
    tcg_temp_free(r_tmp);
777
}
778

    
779
static always_inline void save_cpu_state (DisasContext *ctx, int do_save_pc)
780
{
781
#if defined MIPS_DEBUG_DISAS
782
    if (loglevel & CPU_LOG_TB_IN_ASM) {
783
            fprintf(logfile, "hflags %08x saved %08x\n",
784
                    ctx->hflags, ctx->saved_hflags);
785
    }
786
#endif
787
    if (do_save_pc && ctx->pc != ctx->saved_pc) {
788
        gen_save_pc(ctx->pc);
789
        ctx->saved_pc = ctx->pc;
790
    }
791
    if (ctx->hflags != ctx->saved_hflags) {
792
        TCGv r_tmp = tcg_temp_new(TCG_TYPE_I32);
793

    
794
        tcg_gen_movi_i32(r_tmp, ctx->hflags);
795
        tcg_gen_st_i32(r_tmp, cpu_env, offsetof(CPUState, hflags));
796
        tcg_temp_free(r_tmp);
797
        ctx->saved_hflags = ctx->hflags;
798
        switch (ctx->hflags & MIPS_HFLAG_BMASK) {
799
        case MIPS_HFLAG_BR:
800
            break;
801
        case MIPS_HFLAG_BC:
802
        case MIPS_HFLAG_BL:
803
        case MIPS_HFLAG_B:
804
            gen_save_btarget(ctx->btarget);
805
            break;
806
        }
807
    }
808
}
809

    
810
static always_inline void restore_cpu_state (CPUState *env, DisasContext *ctx)
811
{
812
    ctx->saved_hflags = ctx->hflags;
813
    switch (ctx->hflags & MIPS_HFLAG_BMASK) {
814
    case MIPS_HFLAG_BR:
815
        break;
816
    case MIPS_HFLAG_BC:
817
    case MIPS_HFLAG_BL:
818
    case MIPS_HFLAG_B:
819
        ctx->btarget = env->btarget;
820
        break;
821
    }
822
}
823

    
824
static always_inline void
825
generate_exception_err (DisasContext *ctx, int excp, int err)
826
{
827
    save_cpu_state(ctx, 1);
828
    tcg_gen_helper_0_2ii(do_raise_exception_err, excp, err);
829
    tcg_gen_helper_0_0(do_interrupt_restart);
830
    tcg_gen_exit_tb(0);
831
}
832

    
833
static always_inline void
834
generate_exception (DisasContext *ctx, int excp)
835
{
836
    save_cpu_state(ctx, 1);
837
    tcg_gen_helper_0_1i(do_raise_exception, excp);
838
    tcg_gen_helper_0_0(do_interrupt_restart);
839
    tcg_gen_exit_tb(0);
840
}
841

    
842
/* Addresses computation */
843
static inline void gen_op_addr_add (void)
844
{
845
    tcg_gen_add_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
846

    
847
#if defined(TARGET_MIPS64)
848
    /* For compatibility with 32-bit code, data reference in user mode
849
       with Status_UX = 0 should be casted to 32-bit and sign extended.
850
       See the MIPS64 PRA manual, section 4.10. */
851
    {
852
        int l1 = gen_new_label();
853
        TCGv r_tmp = tcg_temp_local_new(TCG_TYPE_I32);
854

    
855
        tcg_gen_ld_i32(r_tmp, cpu_env, offsetof(CPUState, hflags));
856
        tcg_gen_andi_i32(r_tmp, r_tmp, MIPS_HFLAG_KSU);
857
        tcg_gen_brcondi_i32(TCG_COND_NE, r_tmp, MIPS_HFLAG_UM, l1);
858
        tcg_gen_ld_i32(r_tmp, cpu_env, offsetof(CPUState, CP0_Status));
859
        tcg_gen_andi_i32(r_tmp, r_tmp, (1 << CP0St_UX));
860
        tcg_gen_brcondi_i32(TCG_COND_NE, r_tmp, 0, l1);
861
        tcg_temp_free(r_tmp);
862
        tcg_gen_ext32s_i64(cpu_T[0], cpu_T[0]);
863
        gen_set_label(l1);
864
    }
865
#endif
866
}
867

    
868
static always_inline void check_cp0_enabled(DisasContext *ctx)
869
{
870
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_CP0)))
871
        generate_exception_err(ctx, EXCP_CpU, 1);
872
}
873

    
874
static always_inline void check_cp1_enabled(DisasContext *ctx)
875
{
876
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_FPU)))
877
        generate_exception_err(ctx, EXCP_CpU, 1);
878
}
879

    
880
/* Verify that the processor is running with COP1X instructions enabled.
881
   This is associated with the nabla symbol in the MIPS32 and MIPS64
882
   opcode tables.  */
883

    
884
static always_inline void check_cop1x(DisasContext *ctx)
885
{
886
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_COP1X)))
887
        generate_exception(ctx, EXCP_RI);
888
}
889

    
890
/* Verify that the processor is running with 64-bit floating-point
891
   operations enabled.  */
892

    
893
static always_inline void check_cp1_64bitmode(DisasContext *ctx)
894
{
895
    if (unlikely(~ctx->hflags & (MIPS_HFLAG_F64 | MIPS_HFLAG_COP1X)))
896
        generate_exception(ctx, EXCP_RI);
897
}
898

    
899
/*
900
 * Verify if floating point register is valid; an operation is not defined
901
 * if bit 0 of any register specification is set and the FR bit in the
902
 * Status register equals zero, since the register numbers specify an
903
 * even-odd pair of adjacent coprocessor general registers. When the FR bit
904
 * in the Status register equals one, both even and odd register numbers
905
 * are valid. This limitation exists only for 64 bit wide (d,l,ps) registers.
906
 *
907
 * Multiple 64 bit wide registers can be checked by calling
908
 * gen_op_cp1_registers(freg1 | freg2 | ... | fregN);
909
 */
910
void check_cp1_registers(DisasContext *ctx, int regs)
911
{
912
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_F64) && (regs & 1)))
913
        generate_exception(ctx, EXCP_RI);
914
}
915

    
916
/* This code generates a "reserved instruction" exception if the
917
   CPU does not support the instruction set corresponding to flags. */
918
static always_inline void check_insn(CPUState *env, DisasContext *ctx, int flags)
919
{
920
    if (unlikely(!(env->insn_flags & flags)))
921
        generate_exception(ctx, EXCP_RI);
922
}
923

    
924
/* This code generates a "reserved instruction" exception if 64-bit
925
   instructions are not enabled. */
926
static always_inline void check_mips_64(DisasContext *ctx)
927
{
928
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_64)))
929
        generate_exception(ctx, EXCP_RI);
930
}
931

    
932
/* load/store instructions. */
933
#if defined(CONFIG_USER_ONLY)
934
#define op_ldst(name)        gen_op_##name##_raw()
935
#define OP_LD_TABLE(width)
936
#define OP_ST_TABLE(width)
937
#else
938
#define op_ldst(name)        (*gen_op_##name[ctx->mem_idx])()
939
#define OP_LD_TABLE(width)                                                    \
940
static GenOpFunc *gen_op_l##width[] = {                                       \
941
    &gen_op_l##width##_kernel,                                                \
942
    &gen_op_l##width##_super,                                                 \
943
    &gen_op_l##width##_user,                                                  \
944
}
945
#define OP_ST_TABLE(width)                                                    \
946
static GenOpFunc *gen_op_s##width[] = {                                       \
947
    &gen_op_s##width##_kernel,                                                \
948
    &gen_op_s##width##_super,                                                 \
949
    &gen_op_s##width##_user,                                                  \
950
}
951
#endif
952

    
953
#if defined(TARGET_MIPS64)
954
OP_LD_TABLE(dl);
955
OP_LD_TABLE(dr);
956
OP_ST_TABLE(dl);
957
OP_ST_TABLE(dr);
958
#endif
959
OP_LD_TABLE(wl);
960
OP_LD_TABLE(wr);
961
OP_ST_TABLE(wl);
962
OP_ST_TABLE(wr);
963
OP_LD_TABLE(uxc1);
964
OP_ST_TABLE(uxc1);
965

    
966
#define OP_LD(insn,fname)                                        \
967
void inline op_ldst_##insn(DisasContext *ctx)                    \
968
{                                                                \
969
    tcg_gen_qemu_##fname(cpu_T[0], cpu_T[0], ctx->mem_idx);      \
970
}
971
OP_LD(lb,ld8s);
972
OP_LD(lbu,ld8u);
973
OP_LD(lh,ld16s);
974
OP_LD(lhu,ld16u);
975
OP_LD(lw,ld32s);
976
#if defined(TARGET_MIPS64)
977
OP_LD(lwu,ld32u);
978
OP_LD(ld,ld64);
979
#endif
980
#undef OP_LD
981

    
982
#define OP_ST(insn,fname)                                        \
983
void inline op_ldst_##insn(DisasContext *ctx)                    \
984
{                                                                \
985
    tcg_gen_qemu_##fname(cpu_T[1], cpu_T[0], ctx->mem_idx);      \
986
}
987
OP_ST(sb,st8);
988
OP_ST(sh,st16);
989
OP_ST(sw,st32);
990
#if defined(TARGET_MIPS64)
991
OP_ST(sd,st64);
992
#endif
993
#undef OP_ST
994

    
995
#define OP_LD_ATOMIC(insn,fname)                                        \
996
void inline op_ldst_##insn(DisasContext *ctx)                           \
997
{                                                                       \
998
    tcg_gen_mov_tl(cpu_T[1], cpu_T[0]);                                 \
999
    tcg_gen_qemu_##fname(cpu_T[0], cpu_T[0], ctx->mem_idx);             \
1000
    tcg_gen_st_tl(cpu_T[1], cpu_env, offsetof(CPUState, CP0_LLAddr));   \
1001
}
1002
OP_LD_ATOMIC(ll,ld32s);
1003
#if defined(TARGET_MIPS64)
1004
OP_LD_ATOMIC(lld,ld64);
1005
#endif
1006
#undef OP_LD_ATOMIC
1007

    
1008
#define OP_ST_ATOMIC(insn,fname,almask)                                 \
1009
void inline op_ldst_##insn(DisasContext *ctx)                           \
1010
{                                                                       \
1011
    TCGv r_tmp = tcg_temp_local_new(TCG_TYPE_TL);                       \
1012
    int l1 = gen_new_label();                                           \
1013
    int l2 = gen_new_label();                                           \
1014
    int l3 = gen_new_label();                                           \
1015
                                                                        \
1016
    tcg_gen_andi_tl(r_tmp, cpu_T[0], almask);                           \
1017
    tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp, 0, l1);                      \
1018
    tcg_gen_st_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_BadVAddr)); \
1019
    generate_exception(ctx, EXCP_AdES);                                 \
1020
    gen_set_label(l1);                                                  \
1021
    tcg_gen_ld_tl(r_tmp, cpu_env, offsetof(CPUState, CP0_LLAddr));      \
1022
    tcg_gen_brcond_tl(TCG_COND_NE, cpu_T[0], r_tmp, l2);                \
1023
    tcg_temp_free(r_tmp);                                               \
1024
    tcg_gen_qemu_##fname(cpu_T[1], cpu_T[0], ctx->mem_idx);             \
1025
    tcg_gen_movi_tl(cpu_T[0], 1);                                       \
1026
    tcg_gen_br(l3);                                                     \
1027
    gen_set_label(l2);                                                  \
1028
    tcg_gen_movi_tl(cpu_T[0], 0);                                       \
1029
    gen_set_label(l3);                                                  \
1030
}
1031
OP_ST_ATOMIC(sc,st32,0x3);
1032
#if defined(TARGET_MIPS64)
1033
OP_ST_ATOMIC(scd,st64,0x7);
1034
#endif
1035
#undef OP_ST_ATOMIC
1036

    
1037
/* Load and store */
1038
static void gen_ldst (DisasContext *ctx, uint32_t opc, int rt,
1039
                      int base, int16_t offset)
1040
{
1041
    const char *opn = "ldst";
1042

    
1043
    if (base == 0) {
1044
        tcg_gen_movi_tl(cpu_T[0], offset);
1045
    } else if (offset == 0) {
1046
        gen_load_gpr(cpu_T[0], base);
1047
    } else {
1048
        gen_load_gpr(cpu_T[0], base);
1049
        tcg_gen_movi_tl(cpu_T[1], offset);
1050
        gen_op_addr_add();
1051
    }
1052
    /* Don't do NOP if destination is zero: we must perform the actual
1053
       memory access. */
1054
    switch (opc) {
1055
#if defined(TARGET_MIPS64)
1056
    case OPC_LWU:
1057
        op_ldst_lwu(ctx);
1058
        gen_store_gpr(cpu_T[0], rt);
1059
        opn = "lwu";
1060
        break;
1061
    case OPC_LD:
1062
        op_ldst_ld(ctx);
1063
        gen_store_gpr(cpu_T[0], rt);
1064
        opn = "ld";
1065
        break;
1066
    case OPC_LLD:
1067
        op_ldst_lld(ctx);
1068
        gen_store_gpr(cpu_T[0], rt);
1069
        opn = "lld";
1070
        break;
1071
    case OPC_SD:
1072
        gen_load_gpr(cpu_T[1], rt);
1073
        op_ldst_sd(ctx);
1074
        opn = "sd";
1075
        break;
1076
    case OPC_SCD:
1077
        save_cpu_state(ctx, 1);
1078
        gen_load_gpr(cpu_T[1], rt);
1079
        op_ldst_scd(ctx);
1080
        gen_store_gpr(cpu_T[0], rt);
1081
        opn = "scd";
1082
        break;
1083
    case OPC_LDL:
1084
        gen_load_gpr(cpu_T[1], rt);
1085
        op_ldst(ldl);
1086
        gen_store_gpr(cpu_T[1], rt);
1087
        opn = "ldl";
1088
        break;
1089
    case OPC_SDL:
1090
        gen_load_gpr(cpu_T[1], rt);
1091
        op_ldst(sdl);
1092
        opn = "sdl";
1093
        break;
1094
    case OPC_LDR:
1095
        gen_load_gpr(cpu_T[1], rt);
1096
        op_ldst(ldr);
1097
        gen_store_gpr(cpu_T[1], rt);
1098
        opn = "ldr";
1099
        break;
1100
    case OPC_SDR:
1101
        gen_load_gpr(cpu_T[1], rt);
1102
        op_ldst(sdr);
1103
        opn = "sdr";
1104
        break;
1105
#endif
1106
    case OPC_LW:
1107
        op_ldst_lw(ctx);
1108
        gen_store_gpr(cpu_T[0], rt);
1109
        opn = "lw";
1110
        break;
1111
    case OPC_SW:
1112
        gen_load_gpr(cpu_T[1], rt);
1113
        op_ldst_sw(ctx);
1114
        opn = "sw";
1115
        break;
1116
    case OPC_LH:
1117
        op_ldst_lh(ctx);
1118
        gen_store_gpr(cpu_T[0], rt);
1119
        opn = "lh";
1120
        break;
1121
    case OPC_SH:
1122
        gen_load_gpr(cpu_T[1], rt);
1123
        op_ldst_sh(ctx);
1124
        opn = "sh";
1125
        break;
1126
    case OPC_LHU:
1127
        op_ldst_lhu(ctx);
1128
        gen_store_gpr(cpu_T[0], rt);
1129
        opn = "lhu";
1130
        break;
1131
    case OPC_LB:
1132
        op_ldst_lb(ctx);
1133
        gen_store_gpr(cpu_T[0], rt);
1134
        opn = "lb";
1135
        break;
1136
    case OPC_SB:
1137
        gen_load_gpr(cpu_T[1], rt);
1138
        op_ldst_sb(ctx);
1139
        opn = "sb";
1140
        break;
1141
    case OPC_LBU:
1142
        op_ldst_lbu(ctx);
1143
        gen_store_gpr(cpu_T[0], rt);
1144
        opn = "lbu";
1145
        break;
1146
    case OPC_LWL:
1147
        gen_load_gpr(cpu_T[1], rt);
1148
        op_ldst(lwl);
1149
        gen_store_gpr(cpu_T[1], rt);
1150
        opn = "lwl";
1151
        break;
1152
    case OPC_SWL:
1153
        gen_load_gpr(cpu_T[1], rt);
1154
        op_ldst(swl);
1155
        opn = "swr";
1156
        break;
1157
    case OPC_LWR:
1158
        gen_load_gpr(cpu_T[1], rt);
1159
        op_ldst(lwr);
1160
        gen_store_gpr(cpu_T[1], rt);
1161
        opn = "lwr";
1162
        break;
1163
    case OPC_SWR:
1164
        gen_load_gpr(cpu_T[1], rt);
1165
        op_ldst(swr);
1166
        opn = "swr";
1167
        break;
1168
    case OPC_LL:
1169
        op_ldst_ll(ctx);
1170
        gen_store_gpr(cpu_T[0], rt);
1171
        opn = "ll";
1172
        break;
1173
    case OPC_SC:
1174
        save_cpu_state(ctx, 1);
1175
        gen_load_gpr(cpu_T[1], rt);
1176
        op_ldst_sc(ctx);
1177
        gen_store_gpr(cpu_T[0], rt);
1178
        opn = "sc";
1179
        break;
1180
    default:
1181
        MIPS_INVAL(opn);
1182
        generate_exception(ctx, EXCP_RI);
1183
        return;
1184
    }
1185
    MIPS_DEBUG("%s %s, %d(%s)", opn, regnames[rt], offset, regnames[base]);
1186
}
1187

    
1188
/* Load and store */
1189
static void gen_flt_ldst (DisasContext *ctx, uint32_t opc, int ft,
1190
                      int base, int16_t offset)
1191
{
1192
    const char *opn = "flt_ldst";
1193

    
1194
    if (base == 0) {
1195
        tcg_gen_movi_tl(cpu_T[0], offset);
1196
    } else if (offset == 0) {
1197
        gen_load_gpr(cpu_T[0], base);
1198
    } else {
1199
        gen_load_gpr(cpu_T[0], base);
1200
        tcg_gen_movi_tl(cpu_T[1], offset);
1201
        gen_op_addr_add();
1202
    }
1203
    /* Don't do NOP if destination is zero: we must perform the actual
1204
       memory access. */
1205
    switch (opc) {
1206
    case OPC_LWC1:
1207
        tcg_gen_qemu_ld32s(fpu32_T[0], cpu_T[0], ctx->mem_idx);
1208
        gen_store_fpr32(fpu32_T[0], ft);
1209
        opn = "lwc1";
1210
        break;
1211
    case OPC_SWC1:
1212
        gen_load_fpr32(fpu32_T[0], ft);
1213
        tcg_gen_qemu_st32(fpu32_T[0], cpu_T[0], ctx->mem_idx);
1214
        opn = "swc1";
1215
        break;
1216
    case OPC_LDC1:
1217
        tcg_gen_qemu_ld64(fpu64_T[0], cpu_T[0], ctx->mem_idx);
1218
        gen_store_fpr64(ctx, fpu64_T[0], ft);
1219
        opn = "ldc1";
1220
        break;
1221
    case OPC_SDC1:
1222
        gen_load_fpr64(ctx, fpu64_T[0], ft);
1223
        tcg_gen_qemu_st64(fpu64_T[0], cpu_T[0], ctx->mem_idx);
1224
        opn = "sdc1";
1225
        break;
1226
    default:
1227
        MIPS_INVAL(opn);
1228
        generate_exception(ctx, EXCP_RI);
1229
        return;
1230
    }
1231
    MIPS_DEBUG("%s %s, %d(%s)", opn, fregnames[ft], offset, regnames[base]);
1232
}
1233

    
1234
/* Arithmetic with immediate operand */
1235
static void gen_arith_imm (CPUState *env, DisasContext *ctx, uint32_t opc,
1236
                           int rt, int rs, int16_t imm)
1237
{
1238
    target_ulong uimm;
1239
    const char *opn = "imm arith";
1240

    
1241
    if (rt == 0 && opc != OPC_ADDI && opc != OPC_DADDI) {
1242
        /* If no destination, treat it as a NOP.
1243
           For addi, we must generate the overflow exception when needed. */
1244
        MIPS_DEBUG("NOP");
1245
        return;
1246
    }
1247
    uimm = (uint16_t)imm;
1248
    switch (opc) {
1249
    case OPC_ADDI:
1250
    case OPC_ADDIU:
1251
#if defined(TARGET_MIPS64)
1252
    case OPC_DADDI:
1253
    case OPC_DADDIU:
1254
#endif
1255
    case OPC_SLTI:
1256
    case OPC_SLTIU:
1257
        uimm = (target_long)imm; /* Sign extend to 32/64 bits */
1258
        tcg_gen_movi_tl(cpu_T[1], uimm);
1259
        /* Fall through. */
1260
    case OPC_ANDI:
1261
    case OPC_ORI:
1262
    case OPC_XORI:
1263
        gen_load_gpr(cpu_T[0], rs);
1264
        break;
1265
    case OPC_LUI:
1266
        tcg_gen_movi_tl(cpu_T[0], imm << 16);
1267
        break;
1268
    case OPC_SLL:
1269
    case OPC_SRA:
1270
    case OPC_SRL:
1271
#if defined(TARGET_MIPS64)
1272
    case OPC_DSLL:
1273
    case OPC_DSRA:
1274
    case OPC_DSRL:
1275
    case OPC_DSLL32:
1276
    case OPC_DSRA32:
1277
    case OPC_DSRL32:
1278
#endif
1279
        uimm &= 0x1f;
1280
        gen_load_gpr(cpu_T[0], rs);
1281
        break;
1282
    }
1283
    switch (opc) {
1284
    case OPC_ADDI:
1285
        {
1286
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1287
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1288
            int l1 = gen_new_label();
1289

    
1290
            save_cpu_state(ctx, 1);
1291
            tcg_gen_ext32s_tl(r_tmp1, cpu_T[0]);
1292
            tcg_gen_addi_tl(cpu_T[0], r_tmp1, uimm);
1293

    
1294
            tcg_gen_xori_tl(r_tmp1, r_tmp1, uimm);
1295
            tcg_gen_xori_tl(r_tmp1, r_tmp1, -1);
1296
            tcg_gen_xori_tl(r_tmp2, cpu_T[0], uimm);
1297
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1298
            tcg_temp_free(r_tmp2);
1299
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 31);
1300
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1301
            tcg_temp_free(r_tmp1);
1302
            /* operands of same sign, result different sign */
1303
            generate_exception(ctx, EXCP_OVERFLOW);
1304
            gen_set_label(l1);
1305

    
1306
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1307
        }
1308
        opn = "addi";
1309
        break;
1310
    case OPC_ADDIU:
1311
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1312
        tcg_gen_addi_tl(cpu_T[0], cpu_T[0], uimm);
1313
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1314
        opn = "addiu";
1315
        break;
1316
#if defined(TARGET_MIPS64)
1317
    case OPC_DADDI:
1318
        {
1319
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1320
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1321
            int l1 = gen_new_label();
1322

    
1323
            save_cpu_state(ctx, 1);
1324
            tcg_gen_mov_tl(r_tmp1, cpu_T[0]);
1325
            tcg_gen_addi_tl(cpu_T[0], cpu_T[0], uimm);
1326

    
1327
            tcg_gen_xori_tl(r_tmp1, r_tmp1, uimm);
1328
            tcg_gen_xori_tl(r_tmp1, r_tmp1, -1);
1329
            tcg_gen_xori_tl(r_tmp2, cpu_T[0], uimm);
1330
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1331
            tcg_temp_free(r_tmp2);
1332
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 63);
1333
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1334
            tcg_temp_free(r_tmp1);
1335
            /* operands of same sign, result different sign */
1336
            generate_exception(ctx, EXCP_OVERFLOW);
1337
            gen_set_label(l1);
1338
        }
1339
        opn = "daddi";
1340
        break;
1341
    case OPC_DADDIU:
1342
        tcg_gen_addi_tl(cpu_T[0], cpu_T[0], uimm);
1343
        opn = "daddiu";
1344
        break;
1345
#endif
1346
    case OPC_SLTI:
1347
        gen_op_lti(uimm);
1348
        opn = "slti";
1349
        break;
1350
    case OPC_SLTIU:
1351
        gen_op_ltiu(uimm);
1352
        opn = "sltiu";
1353
        break;
1354
    case OPC_ANDI:
1355
        tcg_gen_andi_tl(cpu_T[0], cpu_T[0], uimm);
1356
        opn = "andi";
1357
        break;
1358
    case OPC_ORI:
1359
        tcg_gen_ori_tl(cpu_T[0], cpu_T[0], uimm);
1360
        opn = "ori";
1361
        break;
1362
    case OPC_XORI:
1363
        tcg_gen_xori_tl(cpu_T[0], cpu_T[0], uimm);
1364
        opn = "xori";
1365
        break;
1366
    case OPC_LUI:
1367
        opn = "lui";
1368
        break;
1369
    case OPC_SLL:
1370
        tcg_gen_ext32u_tl(cpu_T[0], cpu_T[0]);
1371
        tcg_gen_shli_tl(cpu_T[0], cpu_T[0], uimm);
1372
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1373
        opn = "sll";
1374
        break;
1375
    case OPC_SRA:
1376
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1377
        tcg_gen_sari_tl(cpu_T[0], cpu_T[0], uimm);
1378
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1379
        opn = "sra";
1380
        break;
1381
    case OPC_SRL:
1382
        switch ((ctx->opcode >> 21) & 0x1f) {
1383
        case 0:
1384
            tcg_gen_ext32u_tl(cpu_T[0], cpu_T[0]);
1385
            tcg_gen_shri_tl(cpu_T[0], cpu_T[0], uimm);
1386
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1387
            opn = "srl";
1388
            break;
1389
        case 1:
1390
            /* rotr is decoded as srl on non-R2 CPUs */
1391
            if (env->insn_flags & ISA_MIPS32R2) {
1392
                if (uimm != 0) {
1393
                    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
1394
                    TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
1395

    
1396
                    tcg_gen_trunc_tl_i32(r_tmp1, cpu_T[0]);
1397
                    tcg_gen_movi_i32(r_tmp2, 0x20);
1398
                    tcg_gen_subi_i32(r_tmp2, r_tmp2, uimm);
1399
                    tcg_gen_shl_i32(r_tmp2, r_tmp1, r_tmp2);
1400
                    tcg_gen_shri_i32(r_tmp1, r_tmp1, uimm);
1401
                    tcg_gen_or_i32(r_tmp1, r_tmp1, r_tmp2);
1402
                    tcg_gen_ext_i32_tl(cpu_T[0], r_tmp1);
1403
                    tcg_temp_free(r_tmp1);
1404
                    tcg_temp_free(r_tmp2);
1405
                }
1406
                opn = "rotr";
1407
            } else {
1408
                tcg_gen_ext32u_tl(cpu_T[0], cpu_T[0]);
1409
                tcg_gen_shri_tl(cpu_T[0], cpu_T[0], uimm);
1410
                tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1411
                opn = "srl";
1412
            }
1413
            break;
1414
        default:
1415
            MIPS_INVAL("invalid srl flag");
1416
            generate_exception(ctx, EXCP_RI);
1417
            break;
1418
        }
1419
        break;
1420
#if defined(TARGET_MIPS64)
1421
    case OPC_DSLL:
1422
        tcg_gen_shli_tl(cpu_T[0], cpu_T[0], uimm);
1423
        opn = "dsll";
1424
        break;
1425
    case OPC_DSRA:
1426
        tcg_gen_sari_tl(cpu_T[0], cpu_T[0], uimm);
1427
        opn = "dsra";
1428
        break;
1429
    case OPC_DSRL:
1430
        switch ((ctx->opcode >> 21) & 0x1f) {
1431
        case 0:
1432
            tcg_gen_shri_tl(cpu_T[0], cpu_T[0], uimm);
1433
            opn = "dsrl";
1434
            break;
1435
        case 1:
1436
            /* drotr is decoded as dsrl on non-R2 CPUs */
1437
            if (env->insn_flags & ISA_MIPS32R2) {
1438
                if (uimm != 0) {
1439
                    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_TL);
1440

    
1441
                    tcg_gen_movi_tl(r_tmp1, 0x40);
1442
                    tcg_gen_subi_tl(r_tmp1, r_tmp1, uimm);
1443
                    tcg_gen_shl_tl(r_tmp1, cpu_T[0], r_tmp1);
1444
                    tcg_gen_shri_tl(cpu_T[0], cpu_T[0], uimm);
1445
                    tcg_gen_or_tl(cpu_T[0], cpu_T[0], r_tmp1);
1446
                    tcg_temp_free(r_tmp1);
1447
                }
1448
                opn = "drotr";
1449
            } else {
1450
                tcg_gen_shri_tl(cpu_T[0], cpu_T[0], uimm);
1451
                opn = "dsrl";
1452
            }
1453
            break;
1454
        default:
1455
            MIPS_INVAL("invalid dsrl flag");
1456
            generate_exception(ctx, EXCP_RI);
1457
            break;
1458
        }
1459
        break;
1460
    case OPC_DSLL32:
1461
        tcg_gen_shli_tl(cpu_T[0], cpu_T[0], uimm + 32);
1462
        opn = "dsll32";
1463
        break;
1464
    case OPC_DSRA32:
1465
        tcg_gen_sari_tl(cpu_T[0], cpu_T[0], uimm + 32);
1466
        opn = "dsra32";
1467
        break;
1468
    case OPC_DSRL32:
1469
        switch ((ctx->opcode >> 21) & 0x1f) {
1470
        case 0:
1471
            tcg_gen_shri_tl(cpu_T[0], cpu_T[0], uimm + 32);
1472
            opn = "dsrl32";
1473
            break;
1474
        case 1:
1475
            /* drotr32 is decoded as dsrl32 on non-R2 CPUs */
1476
            if (env->insn_flags & ISA_MIPS32R2) {
1477
                TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_TL);
1478
                TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1479

    
1480
                tcg_gen_movi_tl(r_tmp1, 0x40);
1481
                tcg_gen_movi_tl(r_tmp2, 32);
1482
                tcg_gen_addi_tl(r_tmp2, r_tmp2, uimm);
1483
                tcg_gen_sub_tl(r_tmp1, r_tmp1, r_tmp2);
1484
                tcg_gen_shl_tl(r_tmp1, cpu_T[0], r_tmp1);
1485
                tcg_gen_shr_tl(cpu_T[0], cpu_T[0], r_tmp2);
1486
                tcg_gen_or_tl(cpu_T[0], cpu_T[0], r_tmp1);
1487
                tcg_temp_free(r_tmp1);
1488
                tcg_temp_free(r_tmp2);
1489
                opn = "drotr32";
1490
            } else {
1491
                tcg_gen_shri_tl(cpu_T[0], cpu_T[0], uimm + 32);
1492
                opn = "dsrl32";
1493
            }
1494
            break;
1495
        default:
1496
            MIPS_INVAL("invalid dsrl32 flag");
1497
            generate_exception(ctx, EXCP_RI);
1498
            break;
1499
        }
1500
        break;
1501
#endif
1502
    default:
1503
        MIPS_INVAL(opn);
1504
        generate_exception(ctx, EXCP_RI);
1505
        return;
1506
    }
1507
    gen_store_gpr(cpu_T[0], rt);
1508
    MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1509
}
1510

    
1511
/* Arithmetic */
1512
static void gen_arith (CPUState *env, DisasContext *ctx, uint32_t opc,
1513
                       int rd, int rs, int rt)
1514
{
1515
    const char *opn = "arith";
1516

    
1517
    if (rd == 0 && opc != OPC_ADD && opc != OPC_SUB
1518
       && opc != OPC_DADD && opc != OPC_DSUB) {
1519
        /* If no destination, treat it as a NOP.
1520
           For add & sub, we must generate the overflow exception when needed. */
1521
        MIPS_DEBUG("NOP");
1522
        return;
1523
    }
1524
    gen_load_gpr(cpu_T[0], rs);
1525
    /* Specialcase the conventional move operation. */
1526
    if (rt == 0 && (opc == OPC_ADDU || opc == OPC_DADDU
1527
                    || opc == OPC_SUBU || opc == OPC_DSUBU)) {
1528
        gen_store_gpr(cpu_T[0], rd);
1529
        return;
1530
    }
1531
    gen_load_gpr(cpu_T[1], rt);
1532
    switch (opc) {
1533
    case OPC_ADD:
1534
        {
1535
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1536
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1537
            int l1 = gen_new_label();
1538

    
1539
            save_cpu_state(ctx, 1);
1540
            tcg_gen_ext32s_tl(r_tmp1, cpu_T[0]);
1541
            tcg_gen_ext32s_tl(r_tmp2, cpu_T[1]);
1542
            tcg_gen_add_tl(cpu_T[0], r_tmp1, r_tmp2);
1543

    
1544
            tcg_gen_xor_tl(r_tmp1, r_tmp1, cpu_T[1]);
1545
            tcg_gen_xori_tl(r_tmp1, r_tmp1, -1);
1546
            tcg_gen_xor_tl(r_tmp2, cpu_T[0], cpu_T[1]);
1547
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1548
            tcg_temp_free(r_tmp2);
1549
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 31);
1550
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1551
            tcg_temp_free(r_tmp1);
1552
            /* operands of same sign, result different sign */
1553
            generate_exception(ctx, EXCP_OVERFLOW);
1554
            gen_set_label(l1);
1555

    
1556
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1557
        }
1558
        opn = "add";
1559
        break;
1560
    case OPC_ADDU:
1561
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1562
        tcg_gen_ext32s_tl(cpu_T[1], cpu_T[1]);
1563
        tcg_gen_add_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1564
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1565
        opn = "addu";
1566
        break;
1567
    case OPC_SUB:
1568
        {
1569
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1570
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1571
            int l1 = gen_new_label();
1572

    
1573
            save_cpu_state(ctx, 1);
1574
            tcg_gen_ext32s_tl(r_tmp1, cpu_T[0]);
1575
            tcg_gen_ext32s_tl(r_tmp2, cpu_T[1]);
1576
            tcg_gen_sub_tl(cpu_T[0], r_tmp1, r_tmp2);
1577

    
1578
            tcg_gen_xor_tl(r_tmp2, r_tmp1, cpu_T[1]);
1579
            tcg_gen_xor_tl(r_tmp1, r_tmp1, cpu_T[0]);
1580
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1581
            tcg_temp_free(r_tmp2);
1582
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 31);
1583
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1584
            tcg_temp_free(r_tmp1);
1585
            /* operands of different sign, first operand and result different sign */
1586
            generate_exception(ctx, EXCP_OVERFLOW);
1587
            gen_set_label(l1);
1588

    
1589
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1590
        }
1591
        opn = "sub";
1592
        break;
1593
    case OPC_SUBU:
1594
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1595
        tcg_gen_ext32s_tl(cpu_T[1], cpu_T[1]);
1596
        tcg_gen_sub_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1597
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1598
        opn = "subu";
1599
        break;
1600
#if defined(TARGET_MIPS64)
1601
    case OPC_DADD:
1602
        {
1603
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1604
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1605
            int l1 = gen_new_label();
1606

    
1607
            save_cpu_state(ctx, 1);
1608
            tcg_gen_mov_tl(r_tmp1, cpu_T[0]);
1609
            tcg_gen_add_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1610

    
1611
            tcg_gen_xor_tl(r_tmp1, r_tmp1, cpu_T[1]);
1612
            tcg_gen_xori_tl(r_tmp1, r_tmp1, -1);
1613
            tcg_gen_xor_tl(r_tmp2, cpu_T[0], cpu_T[1]);
1614
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1615
            tcg_temp_free(r_tmp2);
1616
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 63);
1617
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1618
            tcg_temp_free(r_tmp1);
1619
            /* operands of same sign, result different sign */
1620
            generate_exception(ctx, EXCP_OVERFLOW);
1621
            gen_set_label(l1);
1622
        }
1623
        opn = "dadd";
1624
        break;
1625
    case OPC_DADDU:
1626
        tcg_gen_add_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1627
        opn = "daddu";
1628
        break;
1629
    case OPC_DSUB:
1630
        {
1631
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1632
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1633
            int l1 = gen_new_label();
1634

    
1635
            save_cpu_state(ctx, 1);
1636
            tcg_gen_mov_tl(r_tmp1, cpu_T[0]);
1637
            tcg_gen_sub_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1638

    
1639
            tcg_gen_xor_tl(r_tmp2, r_tmp1, cpu_T[1]);
1640
            tcg_gen_xor_tl(r_tmp1, r_tmp1, cpu_T[0]);
1641
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1642
            tcg_temp_free(r_tmp2);
1643
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 63);
1644
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1645
            tcg_temp_free(r_tmp1);
1646
            /* operands of different sign, first operand and result different sign */
1647
            generate_exception(ctx, EXCP_OVERFLOW);
1648
            gen_set_label(l1);
1649
        }
1650
        opn = "dsub";
1651
        break;
1652
    case OPC_DSUBU:
1653
        tcg_gen_sub_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1654
        opn = "dsubu";
1655
        break;
1656
#endif
1657
    case OPC_SLT:
1658
        gen_op_lt();
1659
        opn = "slt";
1660
        break;
1661
    case OPC_SLTU:
1662
        gen_op_ltu();
1663
        opn = "sltu";
1664
        break;
1665
    case OPC_AND:
1666
        tcg_gen_and_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1667
        opn = "and";
1668
        break;
1669
    case OPC_NOR:
1670
        tcg_gen_or_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1671
        tcg_gen_not_tl(cpu_T[0], cpu_T[0]);
1672
        opn = "nor";
1673
        break;
1674
    case OPC_OR:
1675
        tcg_gen_or_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1676
        opn = "or";
1677
        break;
1678
    case OPC_XOR:
1679
        tcg_gen_xor_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1680
        opn = "xor";
1681
        break;
1682
    case OPC_MUL:
1683
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1684
        tcg_gen_ext32s_tl(cpu_T[1], cpu_T[1]);
1685
        tcg_gen_mul_tl(cpu_T[0], cpu_T[0], cpu_T[1]);
1686
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1687
        opn = "mul";
1688
        break;
1689
    case OPC_MOVN:
1690
        {
1691
            int l1 = gen_new_label();
1692

    
1693
            tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_T[1], 0, l1);
1694
            gen_store_gpr(cpu_T[0], rd);
1695
            gen_set_label(l1);
1696
        }
1697
        opn = "movn";
1698
        goto print;
1699
    case OPC_MOVZ:
1700
        {
1701
            int l1 = gen_new_label();
1702

    
1703
            tcg_gen_brcondi_tl(TCG_COND_NE, cpu_T[1], 0, l1);
1704
            gen_store_gpr(cpu_T[0], rd);
1705
            gen_set_label(l1);
1706
        }
1707
        opn = "movz";
1708
        goto print;
1709
    case OPC_SLLV:
1710
        tcg_gen_ext32u_tl(cpu_T[0], cpu_T[0]);
1711
        tcg_gen_ext32u_tl(cpu_T[1], cpu_T[1]);
1712
        tcg_gen_andi_tl(cpu_T[0], cpu_T[0], 0x1f);
1713
        tcg_gen_shl_tl(cpu_T[0], cpu_T[1], cpu_T[0]);
1714
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1715
        opn = "sllv";
1716
        break;
1717
    case OPC_SRAV:
1718
        tcg_gen_ext32s_tl(cpu_T[1], cpu_T[1]);
1719
        tcg_gen_andi_tl(cpu_T[0], cpu_T[0], 0x1f);
1720
        tcg_gen_sar_tl(cpu_T[0], cpu_T[1], cpu_T[0]);
1721
        tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1722
        opn = "srav";
1723
        break;
1724
    case OPC_SRLV:
1725
        switch ((ctx->opcode >> 6) & 0x1f) {
1726
        case 0:
1727
            tcg_gen_ext32u_tl(cpu_T[1], cpu_T[1]);
1728
            tcg_gen_andi_tl(cpu_T[0], cpu_T[0], 0x1f);
1729
            tcg_gen_shr_tl(cpu_T[0], cpu_T[1], cpu_T[0]);
1730
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1731
            opn = "srlv";
1732
            break;
1733
        case 1:
1734
            /* rotrv is decoded as srlv on non-R2 CPUs */
1735
            if (env->insn_flags & ISA_MIPS32R2) {
1736
                int l1 = gen_new_label();
1737
                int l2 = gen_new_label();
1738

    
1739
                tcg_gen_andi_tl(cpu_T[0], cpu_T[0], 0x1f);
1740
                tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_T[0], 0, l1);
1741
                {
1742
                    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
1743
                    TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
1744
                    TCGv r_tmp3 = tcg_temp_new(TCG_TYPE_I32);
1745

    
1746
                    tcg_gen_trunc_tl_i32(r_tmp1, cpu_T[0]);
1747
                    tcg_gen_trunc_tl_i32(r_tmp2, cpu_T[1]);
1748
                    tcg_gen_movi_i32(r_tmp3, 0x20);
1749
                    tcg_gen_sub_i32(r_tmp3, r_tmp3, r_tmp1);
1750
                    tcg_gen_shl_i32(r_tmp3, r_tmp2, r_tmp3);
1751
                    tcg_gen_shr_i32(r_tmp1, r_tmp2, r_tmp1);
1752
                    tcg_gen_or_i32(r_tmp1, r_tmp1, r_tmp3);
1753
                    tcg_gen_ext_i32_tl(cpu_T[0], r_tmp1);
1754
                    tcg_temp_free(r_tmp1);
1755
                    tcg_temp_free(r_tmp2);
1756
                    tcg_temp_free(r_tmp3);
1757
                    tcg_gen_br(l2);
1758
                }
1759
                gen_set_label(l1);
1760
                tcg_gen_mov_tl(cpu_T[0], cpu_T[1]);
1761
                gen_set_label(l2);
1762
                opn = "rotrv";
1763
            } else {
1764
                tcg_gen_ext32u_tl(cpu_T[1], cpu_T[1]);
1765
                tcg_gen_andi_tl(cpu_T[0], cpu_T[0], 0x1f);
1766
                tcg_gen_shr_tl(cpu_T[0], cpu_T[1], cpu_T[0]);
1767
                tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1768
                opn = "srlv";
1769
            }
1770
            break;
1771
        default:
1772
            MIPS_INVAL("invalid srlv flag");
1773
            generate_exception(ctx, EXCP_RI);
1774
            break;
1775
        }
1776
        break;
1777
#if defined(TARGET_MIPS64)
1778
    case OPC_DSLLV:
1779
        tcg_gen_andi_tl(cpu_T[0], cpu_T[0], 0x3f);
1780
        tcg_gen_shl_tl(cpu_T[0], cpu_T[1], cpu_T[0]);
1781
        opn = "dsllv";
1782
        break;
1783
    case OPC_DSRAV:
1784
        tcg_gen_andi_tl(cpu_T[0], cpu_T[0], 0x3f);
1785
        tcg_gen_sar_tl(cpu_T[0], cpu_T[1], cpu_T[0]);
1786
        opn = "dsrav";
1787
        break;
1788
    case OPC_DSRLV:
1789
        switch ((ctx->opcode >> 6) & 0x1f) {
1790
        case 0:
1791
            tcg_gen_andi_tl(cpu_T[0], cpu_T[0], 0x3f);
1792
            tcg_gen_shr_tl(cpu_T[0], cpu_T[1], cpu_T[0]);
1793
            opn = "dsrlv";
1794
            break;
1795
        case 1:
1796
            /* drotrv is decoded as dsrlv on non-R2 CPUs */
1797
            if (env->insn_flags & ISA_MIPS32R2) {
1798
                int l1 = gen_new_label();
1799
                int l2 = gen_new_label();
1800

    
1801
                tcg_gen_andi_tl(cpu_T[0], cpu_T[0], 0x3f);
1802
                tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_T[0], 0, l1);
1803
                {
1804
                    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_TL);
1805

    
1806
                    tcg_gen_movi_tl(r_tmp1, 0x40);
1807
                    tcg_gen_sub_tl(r_tmp1, r_tmp1, cpu_T[0]);
1808
                    tcg_gen_shl_tl(r_tmp1, cpu_T[1], r_tmp1);
1809
                    tcg_gen_shr_tl(cpu_T[0], cpu_T[1], cpu_T[0]);
1810
                    tcg_gen_or_tl(cpu_T[0], cpu_T[0], r_tmp1);
1811
                    tcg_temp_free(r_tmp1);
1812
                    tcg_gen_br(l2);
1813
                }
1814
                gen_set_label(l1);
1815
                tcg_gen_mov_tl(cpu_T[0], cpu_T[1]);
1816
                gen_set_label(l2);
1817
                opn = "drotrv";
1818
            } else {
1819
                tcg_gen_andi_tl(cpu_T[0], cpu_T[0], 0x3f);
1820
                tcg_gen_shr_tl(cpu_T[0], cpu_T[1], cpu_T[0]);
1821
                opn = "dsrlv";
1822
            }
1823
            break;
1824
        default:
1825
            MIPS_INVAL("invalid dsrlv flag");
1826
            generate_exception(ctx, EXCP_RI);
1827
            break;
1828
        }
1829
        break;
1830
#endif
1831
    default:
1832
        MIPS_INVAL(opn);
1833
        generate_exception(ctx, EXCP_RI);
1834
        return;
1835
    }
1836
    gen_store_gpr(cpu_T[0], rd);
1837
 print:
1838
    MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1839
}
1840

    
1841
/* Arithmetic on HI/LO registers */
1842
static void gen_HILO (DisasContext *ctx, uint32_t opc, int reg)
1843
{
1844
    const char *opn = "hilo";
1845

    
1846
    if (reg == 0 && (opc == OPC_MFHI || opc == OPC_MFLO)) {
1847
        /* Treat as NOP. */
1848
        MIPS_DEBUG("NOP");
1849
        return;
1850
    }
1851
    switch (opc) {
1852
    case OPC_MFHI:
1853
        gen_load_HI(cpu_T[0], 0);
1854
        gen_store_gpr(cpu_T[0], reg);
1855
        opn = "mfhi";
1856
        break;
1857
    case OPC_MFLO:
1858
        gen_load_LO(cpu_T[0], 0);
1859
        gen_store_gpr(cpu_T[0], reg);
1860
        opn = "mflo";
1861
        break;
1862
    case OPC_MTHI:
1863
        gen_load_gpr(cpu_T[0], reg);
1864
        gen_store_HI(cpu_T[0], 0);
1865
        opn = "mthi";
1866
        break;
1867
    case OPC_MTLO:
1868
        gen_load_gpr(cpu_T[0], reg);
1869
        gen_store_LO(cpu_T[0], 0);
1870
        opn = "mtlo";
1871
        break;
1872
    default:
1873
        MIPS_INVAL(opn);
1874
        generate_exception(ctx, EXCP_RI);
1875
        return;
1876
    }
1877
    MIPS_DEBUG("%s %s", opn, regnames[reg]);
1878
}
1879

    
1880
static void gen_muldiv (DisasContext *ctx, uint32_t opc,
1881
                        int rs, int rt)
1882
{
1883
    const char *opn = "mul/div";
1884

    
1885
    gen_load_gpr(cpu_T[0], rs);
1886
    gen_load_gpr(cpu_T[1], rt);
1887
    switch (opc) {
1888
    case OPC_DIV:
1889
        {
1890
            int l1 = gen_new_label();
1891

    
1892
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1893
            tcg_gen_ext32s_tl(cpu_T[1], cpu_T[1]);
1894
            tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_T[1], 0, l1);
1895
            {
1896
                TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
1897
                TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
1898
                TCGv r_tmp3 = tcg_temp_new(TCG_TYPE_I64);
1899

    
1900
                tcg_gen_ext_tl_i64(r_tmp1, cpu_T[0]);
1901
                tcg_gen_ext_tl_i64(r_tmp2, cpu_T[1]);
1902
                tcg_gen_div_i64(r_tmp3, r_tmp1, r_tmp2);
1903
                tcg_gen_rem_i64(r_tmp2, r_tmp1, r_tmp2);
1904
                tcg_gen_trunc_i64_tl(cpu_T[0], r_tmp3);
1905
                tcg_gen_trunc_i64_tl(cpu_T[1], r_tmp2);
1906
                tcg_temp_free(r_tmp1);
1907
                tcg_temp_free(r_tmp2);
1908
                tcg_temp_free(r_tmp3);
1909
                tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
1910
                tcg_gen_ext32s_tl(cpu_T[1], cpu_T[1]);
1911
                gen_store_LO(cpu_T[0], 0);
1912
                gen_store_HI(cpu_T[1], 0);
1913
            }
1914
            gen_set_label(l1);
1915
        }
1916
        opn = "div";
1917
        break;
1918
    case OPC_DIVU:
1919
        {
1920
            int l1 = gen_new_label();
1921

    
1922
            tcg_gen_ext32s_tl(cpu_T[1], cpu_T[1]);
1923
            tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_T[1], 0, l1);
1924
            {
1925
                TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
1926
                TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
1927
                TCGv r_tmp3 = tcg_temp_new(TCG_TYPE_I32);
1928

    
1929
                tcg_gen_trunc_tl_i32(r_tmp1, cpu_T[0]);
1930
                tcg_gen_trunc_tl_i32(r_tmp2, cpu_T[1]);
1931
                tcg_gen_divu_i32(r_tmp3, r_tmp1, r_tmp2);
1932
                tcg_gen_remu_i32(r_tmp1, r_tmp1, r_tmp2);
1933
                tcg_gen_ext_i32_tl(cpu_T[0], r_tmp3);
1934
                tcg_gen_ext_i32_tl(cpu_T[1], r_tmp1);
1935
                tcg_temp_free(r_tmp1);
1936
                tcg_temp_free(r_tmp2);
1937
                tcg_temp_free(r_tmp3);
1938
                gen_store_LO(cpu_T[0], 0);
1939
                gen_store_HI(cpu_T[1], 0);
1940
            }
1941
            gen_set_label(l1);
1942
        }
1943
        opn = "divu";
1944
        break;
1945
    case OPC_MULT:
1946
        gen_op_mult();
1947
        opn = "mult";
1948
        break;
1949
    case OPC_MULTU:
1950
        gen_op_multu();
1951
        opn = "multu";
1952
        break;
1953
#if defined(TARGET_MIPS64)
1954
    case OPC_DDIV:
1955
        {
1956
            int l1 = gen_new_label();
1957

    
1958
            tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_T[1], 0, l1);
1959
            {
1960
                int l2 = gen_new_label();
1961

    
1962
                tcg_gen_brcondi_tl(TCG_COND_NE, cpu_T[0], -1LL << 63, l2);
1963
                tcg_gen_brcondi_tl(TCG_COND_NE, cpu_T[1], -1LL, l2);
1964
                {
1965
                    tcg_gen_movi_tl(cpu_T[1], 0);
1966
                    gen_store_LO(cpu_T[0], 0);
1967
                    gen_store_HI(cpu_T[1], 0);
1968
                    tcg_gen_br(l1);
1969
                }
1970
                gen_set_label(l2);
1971
                {
1972
                    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
1973
                    TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
1974

    
1975
                    tcg_gen_div_i64(r_tmp1, cpu_T[0], cpu_T[1]);
1976
                    tcg_gen_rem_i64(r_tmp2, cpu_T[0], cpu_T[1]);
1977
                    gen_store_LO(r_tmp1, 0);
1978
                    gen_store_HI(r_tmp2, 0);
1979
                    tcg_temp_free(r_tmp1);
1980
                    tcg_temp_free(r_tmp2);
1981
                }
1982
            }
1983
            gen_set_label(l1);
1984
        }
1985
        opn = "ddiv";
1986
        break;
1987
    case OPC_DDIVU:
1988
        {
1989
            int l1 = gen_new_label();
1990

    
1991
            tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_T[1], 0, l1);
1992
            {
1993
                TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
1994
                TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
1995

    
1996
                tcg_gen_divu_i64(r_tmp1, cpu_T[0], cpu_T[1]);
1997
                tcg_gen_remu_i64(r_tmp2, cpu_T[0], cpu_T[1]);
1998
                tcg_temp_free(r_tmp1);
1999
                tcg_temp_free(r_tmp2);
2000
                gen_store_LO(r_tmp1, 0);
2001
                gen_store_HI(r_tmp2, 0);
2002
            }
2003
            gen_set_label(l1);
2004
        }
2005
        opn = "ddivu";
2006
        break;
2007
    case OPC_DMULT:
2008
        gen_op_dmult();
2009
        opn = "dmult";
2010
        break;
2011
    case OPC_DMULTU:
2012
        gen_op_dmultu();
2013
        opn = "dmultu";
2014
        break;
2015
#endif
2016
    case OPC_MADD:
2017
        gen_op_madd();
2018
        opn = "madd";
2019
        break;
2020
    case OPC_MADDU:
2021
        gen_op_maddu();
2022
        opn = "maddu";
2023
        break;
2024
    case OPC_MSUB:
2025
        gen_op_msub();
2026
        opn = "msub";
2027
        break;
2028
    case OPC_MSUBU:
2029
        gen_op_msubu();
2030
        opn = "msubu";
2031
        break;
2032
    default:
2033
        MIPS_INVAL(opn);
2034
        generate_exception(ctx, EXCP_RI);
2035
        return;
2036
    }
2037
    MIPS_DEBUG("%s %s %s", opn, regnames[rs], regnames[rt]);
2038
}
2039

    
2040
static void gen_mul_vr54xx (DisasContext *ctx, uint32_t opc,
2041
                            int rd, int rs, int rt)
2042
{
2043
    const char *opn = "mul vr54xx";
2044

    
2045
    gen_load_gpr(cpu_T[0], rs);
2046
    gen_load_gpr(cpu_T[1], rt);
2047

    
2048
    switch (opc) {
2049
    case OPC_VR54XX_MULS:
2050
        gen_op_muls();
2051
        opn = "muls";
2052
        break;
2053
    case OPC_VR54XX_MULSU:
2054
        gen_op_mulsu();
2055
        opn = "mulsu";
2056
        break;
2057
    case OPC_VR54XX_MACC:
2058
        gen_op_macc();
2059
        opn = "macc";
2060
        break;
2061
    case OPC_VR54XX_MACCU:
2062
        gen_op_maccu();
2063
        opn = "maccu";
2064
        break;
2065
    case OPC_VR54XX_MSAC:
2066
        gen_op_msac();
2067
        opn = "msac";
2068
        break;
2069
    case OPC_VR54XX_MSACU:
2070
        gen_op_msacu();
2071
        opn = "msacu";
2072
        break;
2073
    case OPC_VR54XX_MULHI:
2074
        gen_op_mulhi();
2075
        opn = "mulhi";
2076
        break;
2077
    case OPC_VR54XX_MULHIU:
2078
        gen_op_mulhiu();
2079
        opn = "mulhiu";
2080
        break;
2081
    case OPC_VR54XX_MULSHI:
2082
        gen_op_mulshi();
2083
        opn = "mulshi";
2084
        break;
2085
    case OPC_VR54XX_MULSHIU:
2086
        gen_op_mulshiu();
2087
        opn = "mulshiu";
2088
        break;
2089
    case OPC_VR54XX_MACCHI:
2090
        gen_op_macchi();
2091
        opn = "macchi";
2092
        break;
2093
    case OPC_VR54XX_MACCHIU:
2094
        gen_op_macchiu();
2095
        opn = "macchiu";
2096
        break;
2097
    case OPC_VR54XX_MSACHI:
2098
        gen_op_msachi();
2099
        opn = "msachi";
2100
        break;
2101
    case OPC_VR54XX_MSACHIU:
2102
        gen_op_msachiu();
2103
        opn = "msachiu";
2104
        break;
2105
    default:
2106
        MIPS_INVAL("mul vr54xx");
2107
        generate_exception(ctx, EXCP_RI);
2108
        return;
2109
    }
2110
    gen_store_gpr(cpu_T[0], rd);
2111
    MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
2112
}
2113

    
2114
static void gen_cl (DisasContext *ctx, uint32_t opc,
2115
                    int rd, int rs)
2116
{
2117
    const char *opn = "CLx";
2118
    if (rd == 0) {
2119
        /* Treat as NOP. */
2120
        MIPS_DEBUG("NOP");
2121
        return;
2122
    }
2123
    gen_load_gpr(cpu_T[0], rs);
2124
    switch (opc) {
2125
    case OPC_CLO:
2126
        tcg_gen_helper_0_0(do_clo);
2127
        opn = "clo";
2128
        break;
2129
    case OPC_CLZ:
2130
        tcg_gen_helper_0_0(do_clz);
2131
        opn = "clz";
2132
        break;
2133
#if defined(TARGET_MIPS64)
2134
    case OPC_DCLO:
2135
        tcg_gen_helper_0_0(do_dclo);
2136
        opn = "dclo";
2137
        break;
2138
    case OPC_DCLZ:
2139
        tcg_gen_helper_0_0(do_dclz);
2140
        opn = "dclz";
2141
        break;
2142
#endif
2143
    default:
2144
        MIPS_INVAL(opn);
2145
        generate_exception(ctx, EXCP_RI);
2146
        return;
2147
    }
2148
    gen_store_gpr(cpu_T[0], rd);
2149
    MIPS_DEBUG("%s %s, %s", opn, regnames[rd], regnames[rs]);
2150
}
2151

    
2152
/* Traps */
2153
static void gen_trap (DisasContext *ctx, uint32_t opc,
2154
                      int rs, int rt, int16_t imm)
2155
{
2156
    int cond;
2157

    
2158
    cond = 0;
2159
    /* Load needed operands */
2160
    switch (opc) {
2161
    case OPC_TEQ:
2162
    case OPC_TGE:
2163
    case OPC_TGEU:
2164
    case OPC_TLT:
2165
    case OPC_TLTU:
2166
    case OPC_TNE:
2167
        /* Compare two registers */
2168
        if (rs != rt) {
2169
            gen_load_gpr(cpu_T[0], rs);
2170
            gen_load_gpr(cpu_T[1], rt);
2171
            cond = 1;
2172
        }
2173
        break;
2174
    case OPC_TEQI:
2175
    case OPC_TGEI:
2176
    case OPC_TGEIU:
2177
    case OPC_TLTI:
2178
    case OPC_TLTIU:
2179
    case OPC_TNEI:
2180
        /* Compare register to immediate */
2181
        if (rs != 0 || imm != 0) {
2182
            gen_load_gpr(cpu_T[0], rs);
2183
            tcg_gen_movi_tl(cpu_T[1], (int32_t)imm);
2184
            cond = 1;
2185
        }
2186
        break;
2187
    }
2188
    if (cond == 0) {
2189
        switch (opc) {
2190
        case OPC_TEQ:   /* rs == rs */
2191
        case OPC_TEQI:  /* r0 == 0  */
2192
        case OPC_TGE:   /* rs >= rs */
2193
        case OPC_TGEI:  /* r0 >= 0  */
2194
        case OPC_TGEU:  /* rs >= rs unsigned */
2195
        case OPC_TGEIU: /* r0 >= 0  unsigned */
2196
            /* Always trap */
2197
            tcg_gen_movi_tl(cpu_T[0], 1);
2198
            break;
2199
        case OPC_TLT:   /* rs < rs           */
2200
        case OPC_TLTI:  /* r0 < 0            */
2201
        case OPC_TLTU:  /* rs < rs unsigned  */
2202
        case OPC_TLTIU: /* r0 < 0  unsigned  */
2203
        case OPC_TNE:   /* rs != rs          */
2204
        case OPC_TNEI:  /* r0 != 0           */
2205
            /* Never trap: treat as NOP. */
2206
            return;
2207
        default:
2208
            MIPS_INVAL("trap");
2209
            generate_exception(ctx, EXCP_RI);
2210
            return;
2211
        }
2212
    } else {
2213
        switch (opc) {
2214
        case OPC_TEQ:
2215
        case OPC_TEQI:
2216
            gen_op_eq();
2217
            break;
2218
        case OPC_TGE:
2219
        case OPC_TGEI:
2220
            gen_op_ge();
2221
            break;
2222
        case OPC_TGEU:
2223
        case OPC_TGEIU:
2224
            gen_op_geu();
2225
            break;
2226
        case OPC_TLT:
2227
        case OPC_TLTI:
2228
            gen_op_lt();
2229
            break;
2230
        case OPC_TLTU:
2231
        case OPC_TLTIU:
2232
            gen_op_ltu();
2233
            break;
2234
        case OPC_TNE:
2235
        case OPC_TNEI:
2236
            gen_op_ne();
2237
            break;
2238
        default:
2239
            MIPS_INVAL("trap");
2240
            generate_exception(ctx, EXCP_RI);
2241
            return;
2242
        }
2243
    }
2244
    save_cpu_state(ctx, 1);
2245
    {
2246
        int l1 = gen_new_label();
2247

    
2248
        tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_T[0], 0, l1);
2249
        tcg_gen_helper_0_1i(do_raise_exception, EXCP_TRAP);
2250
        gen_set_label(l1);
2251
    }
2252
    ctx->bstate = BS_STOP;
2253
}
2254

    
2255
static always_inline void gen_goto_tb(DisasContext *ctx, int n, target_ulong dest)
2256
{
2257
    TranslationBlock *tb;
2258
    tb = ctx->tb;
2259
    if ((tb->pc & TARGET_PAGE_MASK) == (dest & TARGET_PAGE_MASK)) {
2260
        tcg_gen_goto_tb(n);
2261
        gen_save_pc(dest);
2262
        tcg_gen_exit_tb((long)tb + n);
2263
    } else {
2264
        gen_save_pc(dest);
2265
        tcg_gen_exit_tb(0);
2266
    }
2267
}
2268

    
2269
/* Branches (before delay slot) */
2270
static void gen_compute_branch (DisasContext *ctx, uint32_t opc,
2271
                                int rs, int rt, int32_t offset)
2272
{
2273
    target_ulong btarget = -1;
2274
    int blink = 0;
2275
    int bcond = 0;
2276

    
2277
    if (ctx->hflags & MIPS_HFLAG_BMASK) {
2278
#ifdef MIPS_DEBUG_DISAS
2279
        if (loglevel & CPU_LOG_TB_IN_ASM) {
2280
            fprintf(logfile,
2281
                    "Branch in delay slot at PC 0x" TARGET_FMT_lx "\n",
2282
                    ctx->pc);
2283
        }
2284
#endif
2285
        generate_exception(ctx, EXCP_RI);
2286
        return;
2287
    }
2288

    
2289
    /* Load needed operands */
2290
    switch (opc) {
2291
    case OPC_BEQ:
2292
    case OPC_BEQL:
2293
    case OPC_BNE:
2294
    case OPC_BNEL:
2295
        /* Compare two registers */
2296
        if (rs != rt) {
2297
            gen_load_gpr(cpu_T[0], rs);
2298
            gen_load_gpr(cpu_T[1], rt);
2299
            bcond = 1;
2300
        }
2301
        btarget = ctx->pc + 4 + offset;
2302
        break;
2303
    case OPC_BGEZ:
2304
    case OPC_BGEZAL:
2305
    case OPC_BGEZALL:
2306
    case OPC_BGEZL:
2307
    case OPC_BGTZ:
2308
    case OPC_BGTZL:
2309
    case OPC_BLEZ:
2310
    case OPC_BLEZL:
2311
    case OPC_BLTZ:
2312
    case OPC_BLTZAL:
2313
    case OPC_BLTZALL:
2314
    case OPC_BLTZL:
2315
        /* Compare to zero */
2316
        if (rs != 0) {
2317
            gen_load_gpr(cpu_T[0], rs);
2318
            bcond = 1;
2319
        }
2320
        btarget = ctx->pc + 4 + offset;
2321
        break;
2322
    case OPC_J:
2323
    case OPC_JAL:
2324
        /* Jump to immediate */
2325
        btarget = ((ctx->pc + 4) & (int32_t)0xF0000000) | (uint32_t)offset;
2326
        break;
2327
    case OPC_JR:
2328
    case OPC_JALR:
2329
        /* Jump to register */
2330
        if (offset != 0 && offset != 16) {
2331
            /* Hint = 0 is JR/JALR, hint 16 is JR.HB/JALR.HB, the
2332
               others are reserved. */
2333
            MIPS_INVAL("jump hint");
2334
            generate_exception(ctx, EXCP_RI);
2335
            return;
2336
        }
2337
        gen_save_breg_target(rs);
2338
        break;
2339
    default:
2340
        MIPS_INVAL("branch/jump");
2341
        generate_exception(ctx, EXCP_RI);
2342
        return;
2343
    }
2344
    if (bcond == 0) {
2345
        /* No condition to be computed */
2346
        switch (opc) {
2347
        case OPC_BEQ:     /* rx == rx        */
2348
        case OPC_BEQL:    /* rx == rx likely */
2349
        case OPC_BGEZ:    /* 0 >= 0          */
2350
        case OPC_BGEZL:   /* 0 >= 0 likely   */
2351
        case OPC_BLEZ:    /* 0 <= 0          */
2352
        case OPC_BLEZL:   /* 0 <= 0 likely   */
2353
            /* Always take */
2354
            ctx->hflags |= MIPS_HFLAG_B;
2355
            MIPS_DEBUG("balways");
2356
            break;
2357
        case OPC_BGEZAL:  /* 0 >= 0          */
2358
        case OPC_BGEZALL: /* 0 >= 0 likely   */
2359
            /* Always take and link */
2360
            blink = 31;
2361
            ctx->hflags |= MIPS_HFLAG_B;
2362
            MIPS_DEBUG("balways and link");
2363
            break;
2364
        case OPC_BNE:     /* rx != rx        */
2365
        case OPC_BGTZ:    /* 0 > 0           */
2366
        case OPC_BLTZ:    /* 0 < 0           */
2367
            /* Treat as NOP. */
2368
            MIPS_DEBUG("bnever (NOP)");
2369
            return;
2370
        case OPC_BLTZAL:  /* 0 < 0           */
2371
            tcg_gen_movi_tl(cpu_T[0], ctx->pc + 8);
2372
            gen_store_gpr(cpu_T[0], 31);
2373
            MIPS_DEBUG("bnever and link");
2374
            return;
2375
        case OPC_BLTZALL: /* 0 < 0 likely */
2376
            tcg_gen_movi_tl(cpu_T[0], ctx->pc + 8);
2377
            gen_store_gpr(cpu_T[0], 31);
2378
            /* Skip the instruction in the delay slot */
2379
            MIPS_DEBUG("bnever, link and skip");
2380
            ctx->pc += 4;
2381
            return;
2382
        case OPC_BNEL:    /* rx != rx likely */
2383
        case OPC_BGTZL:   /* 0 > 0 likely */
2384
        case OPC_BLTZL:   /* 0 < 0 likely */
2385
            /* Skip the instruction in the delay slot */
2386
            MIPS_DEBUG("bnever and skip");
2387
            ctx->pc += 4;
2388
            return;
2389
        case OPC_J:
2390
            ctx->hflags |= MIPS_HFLAG_B;
2391
            MIPS_DEBUG("j " TARGET_FMT_lx, btarget);
2392
            break;
2393
        case OPC_JAL:
2394
            blink = 31;
2395
            ctx->hflags |= MIPS_HFLAG_B;
2396
            MIPS_DEBUG("jal " TARGET_FMT_lx, btarget);
2397
            break;
2398
        case OPC_JR:
2399
            ctx->hflags |= MIPS_HFLAG_BR;
2400
            MIPS_DEBUG("jr %s", regnames[rs]);
2401
            break;
2402
        case OPC_JALR:
2403
            blink = rt;
2404
            ctx->hflags |= MIPS_HFLAG_BR;
2405
            MIPS_DEBUG("jalr %s, %s", regnames[rt], regnames[rs]);
2406
            break;
2407
        default:
2408
            MIPS_INVAL("branch/jump");
2409
            generate_exception(ctx, EXCP_RI);
2410
            return;
2411
        }
2412
    } else {
2413
        switch (opc) {
2414
        case OPC_BEQ:
2415
            gen_op_eq();
2416
            MIPS_DEBUG("beq %s, %s, " TARGET_FMT_lx,
2417
                       regnames[rs], regnames[rt], btarget);
2418
            goto not_likely;
2419
        case OPC_BEQL:
2420
            gen_op_eq();
2421
            MIPS_DEBUG("beql %s, %s, " TARGET_FMT_lx,
2422
                       regnames[rs], regnames[rt], btarget);
2423
            goto likely;
2424
        case OPC_BNE:
2425
            gen_op_ne();
2426
            MIPS_DEBUG("bne %s, %s, " TARGET_FMT_lx,
2427
                       regnames[rs], regnames[rt], btarget);
2428
            goto not_likely;
2429
        case OPC_BNEL:
2430
            gen_op_ne();
2431
            MIPS_DEBUG("bnel %s, %s, " TARGET_FMT_lx,
2432
                       regnames[rs], regnames[rt], btarget);
2433
            goto likely;
2434
        case OPC_BGEZ:
2435
            gen_op_gez();
2436
            MIPS_DEBUG("bgez %s, " TARGET_FMT_lx, regnames[rs], btarget);
2437
            goto not_likely;
2438
        case OPC_BGEZL:
2439
            gen_op_gez();
2440
            MIPS_DEBUG("bgezl %s, " TARGET_FMT_lx, regnames[rs], btarget);
2441
            goto likely;
2442
        case OPC_BGEZAL:
2443
            gen_op_gez();
2444
            MIPS_DEBUG("bgezal %s, " TARGET_FMT_lx, regnames[rs], btarget);
2445
            blink = 31;
2446
            goto not_likely;
2447
        case OPC_BGEZALL:
2448
            gen_op_gez();
2449
            blink = 31;
2450
            MIPS_DEBUG("bgezall %s, " TARGET_FMT_lx, regnames[rs], btarget);
2451
            goto likely;
2452
        case OPC_BGTZ:
2453
            gen_op_gtz();
2454
            MIPS_DEBUG("bgtz %s, " TARGET_FMT_lx, regnames[rs], btarget);
2455
            goto not_likely;
2456
        case OPC_BGTZL:
2457
            gen_op_gtz();
2458
            MIPS_DEBUG("bgtzl %s, " TARGET_FMT_lx, regnames[rs], btarget);
2459
            goto likely;
2460
        case OPC_BLEZ:
2461
            gen_op_lez();
2462
            MIPS_DEBUG("blez %s, " TARGET_FMT_lx, regnames[rs], btarget);
2463
            goto not_likely;
2464
        case OPC_BLEZL:
2465
            gen_op_lez();
2466
            MIPS_DEBUG("blezl %s, " TARGET_FMT_lx, regnames[rs], btarget);
2467
            goto likely;
2468
        case OPC_BLTZ:
2469
            gen_op_ltz();
2470
            MIPS_DEBUG("bltz %s, " TARGET_FMT_lx, regnames[rs], btarget);
2471
            goto not_likely;
2472
        case OPC_BLTZL:
2473
            gen_op_ltz();
2474
            MIPS_DEBUG("bltzl %s, " TARGET_FMT_lx, regnames[rs], btarget);
2475
            goto likely;
2476
        case OPC_BLTZAL:
2477
            gen_op_ltz();
2478
            blink = 31;
2479
            MIPS_DEBUG("bltzal %s, " TARGET_FMT_lx, regnames[rs], btarget);
2480
        not_likely:
2481
            ctx->hflags |= MIPS_HFLAG_BC;
2482
            tcg_gen_st_tl(cpu_T[0], cpu_env, offsetof(CPUState, bcond));
2483
            break;
2484
        case OPC_BLTZALL:
2485
            gen_op_ltz();
2486
            blink = 31;
2487
            MIPS_DEBUG("bltzall %s, " TARGET_FMT_lx, regnames[rs], btarget);
2488
        likely:
2489
            ctx->hflags |= MIPS_HFLAG_BL;
2490
            tcg_gen_st_tl(cpu_T[0], cpu_env, offsetof(CPUState, bcond));
2491
            break;
2492
        default:
2493
            MIPS_INVAL("conditional branch/jump");
2494
            generate_exception(ctx, EXCP_RI);
2495
            return;
2496
        }
2497
    }
2498
    MIPS_DEBUG("enter ds: link %d cond %02x target " TARGET_FMT_lx,
2499
               blink, ctx->hflags, btarget);
2500

    
2501
    ctx->btarget = btarget;
2502
    if (blink > 0) {
2503
        tcg_gen_movi_tl(cpu_T[0], ctx->pc + 8);
2504
        gen_store_gpr(cpu_T[0], blink);
2505
    }
2506
}
2507

    
2508
/* special3 bitfield operations */
2509
static void gen_bitops (DisasContext *ctx, uint32_t opc, int rt,
2510
                       int rs, int lsb, int msb)
2511
{
2512
    gen_load_gpr(cpu_T[1], rs);
2513
    switch (opc) {
2514
    case OPC_EXT:
2515
        if (lsb + msb > 31)
2516
            goto fail;
2517
        gen_op_ext(lsb, msb + 1);
2518
        break;
2519
#if defined(TARGET_MIPS64)
2520
    case OPC_DEXTM:
2521
        if (lsb + msb > 63)
2522
            goto fail;
2523
        gen_op_dext(lsb, msb + 1 + 32);
2524
        break;
2525
    case OPC_DEXTU:
2526
        if (lsb + msb > 63)
2527
            goto fail;
2528
        gen_op_dext(lsb + 32, msb + 1);
2529
        break;
2530
    case OPC_DEXT:
2531
        if (lsb + msb > 63)
2532
            goto fail;
2533
        gen_op_dext(lsb, msb + 1);
2534
        break;
2535
#endif
2536
    case OPC_INS:
2537
        if (lsb > msb)
2538
            goto fail;
2539
        gen_load_gpr(cpu_T[0], rt);
2540
        gen_op_ins(lsb, msb - lsb + 1);
2541
        break;
2542
#if defined(TARGET_MIPS64)
2543
    case OPC_DINSM:
2544
        if (lsb > msb)
2545
            goto fail;
2546
        gen_load_gpr(cpu_T[0], rt);
2547
        gen_op_dins(lsb, msb - lsb + 1 + 32);
2548
        break;
2549
    case OPC_DINSU:
2550
        if (lsb > msb)
2551
            goto fail;
2552
        gen_load_gpr(cpu_T[0], rt);
2553
        gen_op_dins(lsb + 32, msb - lsb + 1);
2554
        break;
2555
    case OPC_DINS:
2556
        if (lsb > msb)
2557
            goto fail;
2558
        gen_load_gpr(cpu_T[0], rt);
2559
        gen_op_dins(lsb, msb - lsb + 1);
2560
        break;
2561
#endif
2562
    default:
2563
fail:
2564
        MIPS_INVAL("bitops");
2565
        generate_exception(ctx, EXCP_RI);
2566
        return;
2567
    }
2568
    gen_store_gpr(cpu_T[0], rt);
2569
}
2570

    
2571
/* CP0 (MMU and control) */
2572
#ifndef CONFIG_USER_ONLY
2573
static inline void gen_mfc0_load32 (TCGv t, target_ulong off)
2574
{
2575
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_I32);
2576

    
2577
    tcg_gen_ld_i32(r_tmp, cpu_env, off);
2578
    tcg_gen_ext_i32_tl(t, r_tmp);
2579
    tcg_temp_free(r_tmp);
2580
}
2581

    
2582
static inline void gen_mfc0_load64 (TCGv t, target_ulong off)
2583
{
2584
    tcg_gen_ld_tl(t, cpu_env, off);
2585
    tcg_gen_ext32s_tl(t, t);
2586
}
2587

    
2588
static inline void gen_mtc0_store32 (TCGv t, target_ulong off)
2589
{
2590
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_I32);
2591

    
2592
    tcg_gen_trunc_tl_i32(r_tmp, t);
2593
    tcg_gen_st_i32(r_tmp, cpu_env, off);
2594
    tcg_temp_free(r_tmp);
2595
}
2596

    
2597
static inline void gen_mtc0_store64 (TCGv t, target_ulong off)
2598
{
2599
    tcg_gen_ext32s_tl(t, t);
2600
    tcg_gen_st_tl(t, cpu_env, off);
2601
}
2602

    
2603
static void gen_mfc0 (CPUState *env, DisasContext *ctx, int reg, int sel)
2604
{
2605
    const char *rn = "invalid";
2606

    
2607
    if (sel != 0)
2608
        check_insn(env, ctx, ISA_MIPS32);
2609

    
2610
    switch (reg) {
2611
    case 0:
2612
        switch (sel) {
2613
        case 0:
2614
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Index));
2615
            rn = "Index";
2616
            break;
2617
        case 1:
2618
            check_insn(env, ctx, ASE_MT);
2619
            tcg_gen_helper_0_0(do_mfc0_mvpcontrol);
2620
            rn = "MVPControl";
2621
            break;
2622
        case 2:
2623
            check_insn(env, ctx, ASE_MT);
2624
            tcg_gen_helper_0_0(do_mfc0_mvpconf0);
2625
            rn = "MVPConf0";
2626
            break;
2627
        case 3:
2628
            check_insn(env, ctx, ASE_MT);
2629
            tcg_gen_helper_0_0(do_mfc0_mvpconf1);
2630
            rn = "MVPConf1";
2631
            break;
2632
        default:
2633
            goto die;
2634
        }
2635
        break;
2636
    case 1:
2637
        switch (sel) {
2638
        case 0:
2639
            tcg_gen_helper_0_0(do_mfc0_random);
2640
            rn = "Random";
2641
            break;
2642
        case 1:
2643
            check_insn(env, ctx, ASE_MT);
2644
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_VPEControl));
2645
            rn = "VPEControl";
2646
            break;
2647
        case 2:
2648
            check_insn(env, ctx, ASE_MT);
2649
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_VPEConf0));
2650
            rn = "VPEConf0";
2651
            break;
2652
        case 3:
2653
            check_insn(env, ctx, ASE_MT);
2654
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_VPEConf1));
2655
            rn = "VPEConf1";
2656
            break;
2657
        case 4:
2658
            check_insn(env, ctx, ASE_MT);
2659
            gen_mfc0_load64(cpu_T[0], offsetof(CPUState, CP0_YQMask));
2660
            rn = "YQMask";
2661
            break;
2662
        case 5:
2663
            check_insn(env, ctx, ASE_MT);
2664
            gen_mfc0_load64(cpu_T[0], offsetof(CPUState, CP0_VPESchedule));
2665
            rn = "VPESchedule";
2666
            break;
2667
        case 6:
2668
            check_insn(env, ctx, ASE_MT);
2669
            gen_mfc0_load64(cpu_T[0], offsetof(CPUState, CP0_VPEScheFBack));
2670
            rn = "VPEScheFBack";
2671
            break;
2672
        case 7:
2673
            check_insn(env, ctx, ASE_MT);
2674
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_VPEOpt));
2675
            rn = "VPEOpt";
2676
            break;
2677
        default:
2678
            goto die;
2679
        }
2680
        break;
2681
    case 2:
2682
        switch (sel) {
2683
        case 0:
2684
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_EntryLo0));
2685
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
2686
            rn = "EntryLo0";
2687
            break;
2688
        case 1:
2689
            check_insn(env, ctx, ASE_MT);
2690
            tcg_gen_helper_0_0(do_mfc0_tcstatus);
2691
            rn = "TCStatus";
2692
            break;
2693
        case 2:
2694
            check_insn(env, ctx, ASE_MT);
2695
            tcg_gen_helper_0_0(do_mfc0_tcbind);
2696
            rn = "TCBind";
2697
            break;
2698
        case 3:
2699
            check_insn(env, ctx, ASE_MT);
2700
            tcg_gen_helper_0_0(do_mfc0_tcrestart);
2701
            rn = "TCRestart";
2702
            break;
2703
        case 4:
2704
            check_insn(env, ctx, ASE_MT);
2705
            tcg_gen_helper_0_0(do_mfc0_tchalt);
2706
            rn = "TCHalt";
2707
            break;
2708
        case 5:
2709
            check_insn(env, ctx, ASE_MT);
2710
            tcg_gen_helper_0_0(do_mfc0_tccontext);
2711
            rn = "TCContext";
2712
            break;
2713
        case 6:
2714
            check_insn(env, ctx, ASE_MT);
2715
            tcg_gen_helper_0_0(do_mfc0_tcschedule);
2716
            rn = "TCSchedule";
2717
            break;
2718
        case 7:
2719
            check_insn(env, ctx, ASE_MT);
2720
            tcg_gen_helper_0_0(do_mfc0_tcschefback);
2721
            rn = "TCScheFBack";
2722
            break;
2723
        default:
2724
            goto die;
2725
        }
2726
        break;
2727
    case 3:
2728
        switch (sel) {
2729
        case 0:
2730
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_EntryLo1));
2731
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
2732
            rn = "EntryLo1";
2733
            break;
2734
        default:
2735
            goto die;
2736
        }
2737
        break;
2738
    case 4:
2739
        switch (sel) {
2740
        case 0:
2741
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_Context));
2742
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
2743
            rn = "Context";
2744
            break;
2745
        case 1:
2746
//            tcg_gen_helper_0_0(do_mfc0_contextconfig); /* SmartMIPS ASE */
2747
            rn = "ContextConfig";
2748
//            break;
2749
        default:
2750
            goto die;
2751
        }
2752
        break;
2753
    case 5:
2754
        switch (sel) {
2755
        case 0:
2756
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_PageMask));
2757
            rn = "PageMask";
2758
            break;
2759
        case 1:
2760
            check_insn(env, ctx, ISA_MIPS32R2);
2761
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_PageGrain));
2762
            rn = "PageGrain";
2763
            break;
2764
        default:
2765
            goto die;
2766
        }
2767
        break;
2768
    case 6:
2769
        switch (sel) {
2770
        case 0:
2771
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Wired));
2772
            rn = "Wired";
2773
            break;
2774
        case 1:
2775
            check_insn(env, ctx, ISA_MIPS32R2);
2776
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSConf0));
2777
            rn = "SRSConf0";
2778
            break;
2779
        case 2:
2780
            check_insn(env, ctx, ISA_MIPS32R2);
2781
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSConf1));
2782
            rn = "SRSConf1";
2783
            break;
2784
        case 3:
2785
            check_insn(env, ctx, ISA_MIPS32R2);
2786
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSConf2));
2787
            rn = "SRSConf2";
2788
            break;
2789
        case 4:
2790
            check_insn(env, ctx, ISA_MIPS32R2);
2791
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSConf3));
2792
            rn = "SRSConf3";
2793
            break;
2794
        case 5:
2795
            check_insn(env, ctx, ISA_MIPS32R2);
2796
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSConf4));
2797
            rn = "SRSConf4";
2798
            break;
2799
        default:
2800
            goto die;
2801
        }
2802
        break;
2803
    case 7:
2804
        switch (sel) {
2805
        case 0:
2806
            check_insn(env, ctx, ISA_MIPS32R2);
2807
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_HWREna));
2808
            rn = "HWREna";
2809
            break;
2810
        default:
2811
            goto die;
2812
        }
2813
        break;
2814
    case 8:
2815
        switch (sel) {
2816
        case 0:
2817
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_BadVAddr));
2818
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
2819
            rn = "BadVAddr";
2820
            break;
2821
        default:
2822
            goto die;
2823
       }
2824
        break;
2825
    case 9:
2826
        switch (sel) {
2827
        case 0:
2828
            tcg_gen_helper_0_0(do_mfc0_count);
2829
            rn = "Count";
2830
            break;
2831
        /* 6,7 are implementation dependent */
2832
        default:
2833
            goto die;
2834
        }
2835
        break;
2836
    case 10:
2837
        switch (sel) {
2838
        case 0:
2839
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_EntryHi));
2840
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
2841
            rn = "EntryHi";
2842
            break;
2843
        default:
2844
            goto die;
2845
        }
2846
        break;
2847
    case 11:
2848
        switch (sel) {
2849
        case 0:
2850
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Compare));
2851
            rn = "Compare";
2852
            break;
2853
        /* 6,7 are implementation dependent */
2854
        default:
2855
            goto die;
2856
        }
2857
        break;
2858
    case 12:
2859
        switch (sel) {
2860
        case 0:
2861
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Status));
2862
            rn = "Status";
2863
            break;
2864
        case 1:
2865
            check_insn(env, ctx, ISA_MIPS32R2);
2866
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_IntCtl));
2867
            rn = "IntCtl";
2868
            break;
2869
        case 2:
2870
            check_insn(env, ctx, ISA_MIPS32R2);
2871
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSCtl));
2872
            rn = "SRSCtl";
2873
            break;
2874
        case 3:
2875
            check_insn(env, ctx, ISA_MIPS32R2);
2876
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSMap));
2877
            rn = "SRSMap";
2878
            break;
2879
        default:
2880
            goto die;
2881
       }
2882
        break;
2883
    case 13:
2884
        switch (sel) {
2885
        case 0:
2886
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Cause));
2887
            rn = "Cause";
2888
            break;
2889
        default:
2890
            goto die;
2891
       }
2892
        break;
2893
    case 14:
2894
        switch (sel) {
2895
        case 0:
2896
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_EPC));
2897
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
2898
            rn = "EPC";
2899
            break;
2900
        default:
2901
            goto die;
2902
        }
2903
        break;
2904
    case 15:
2905
        switch (sel) {
2906
        case 0:
2907
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_PRid));
2908
            rn = "PRid";
2909
            break;
2910
        case 1:
2911
            check_insn(env, ctx, ISA_MIPS32R2);
2912
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_EBase));
2913
            rn = "EBase";
2914
            break;
2915
        default:
2916
            goto die;
2917
       }
2918
        break;
2919
    case 16:
2920
        switch (sel) {
2921
        case 0:
2922
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config0));
2923
            rn = "Config";
2924
            break;
2925
        case 1:
2926
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config1));
2927
            rn = "Config1";
2928
            break;
2929
        case 2:
2930
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config2));
2931
            rn = "Config2";
2932
            break;
2933
        case 3:
2934
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config3));
2935
            rn = "Config3";
2936
            break;
2937
        /* 4,5 are reserved */
2938
        /* 6,7 are implementation dependent */
2939
        case 6:
2940
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config6));
2941
            rn = "Config6";
2942
            break;
2943
        case 7:
2944
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config7));
2945
            rn = "Config7";
2946
            break;
2947
        default:
2948
            goto die;
2949
        }
2950
        break;
2951
    case 17:
2952
        switch (sel) {
2953
        case 0:
2954
            tcg_gen_helper_0_0(do_mfc0_lladdr);
2955
            rn = "LLAddr";
2956
            break;
2957
        default:
2958
            goto die;
2959
        }
2960
        break;
2961
    case 18:
2962
        switch (sel) {
2963
        case 0 ... 7:
2964
            tcg_gen_helper_0_1i(do_mfc0_watchlo, sel);
2965
            rn = "WatchLo";
2966
            break;
2967
        default:
2968
            goto die;
2969
        }
2970
        break;
2971
    case 19:
2972
        switch (sel) {
2973
        case 0 ...7:
2974
            tcg_gen_helper_0_1i(do_mfc0_watchhi, sel);
2975
            rn = "WatchHi";
2976
            break;
2977
        default:
2978
            goto die;
2979
        }
2980
        break;
2981
    case 20:
2982
        switch (sel) {
2983
        case 0:
2984
#if defined(TARGET_MIPS64)
2985
            check_insn(env, ctx, ISA_MIPS3);
2986
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_XContext));
2987
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
2988
            rn = "XContext";
2989
            break;
2990
#endif
2991
        default:
2992
            goto die;
2993
        }
2994
        break;
2995
    case 21:
2996
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
2997
        switch (sel) {
2998
        case 0:
2999
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Framemask));
3000
            rn = "Framemask";
3001
            break;
3002
        default:
3003
            goto die;
3004
        }
3005
        break;
3006
    case 22:
3007
        /* ignored */
3008
        rn = "'Diagnostic"; /* implementation dependent */
3009
        break;
3010
    case 23:
3011
        switch (sel) {
3012
        case 0:
3013
            tcg_gen_helper_0_0(do_mfc0_debug); /* EJTAG support */
3014
            rn = "Debug";
3015
            break;
3016
        case 1:
3017
//            tcg_gen_helper_0_0(do_mfc0_tracecontrol); /* PDtrace support */
3018
            rn = "TraceControl";
3019
//            break;
3020
        case 2:
3021
//            tcg_gen_helper_0_0(do_mfc0_tracecontrol2); /* PDtrace support */
3022
            rn = "TraceControl2";
3023
//            break;
3024
        case 3:
3025
//            tcg_gen_helper_0_0(do_mfc0_usertracedata); /* PDtrace support */
3026
            rn = "UserTraceData";
3027
//            break;
3028
        case 4:
3029
//            tcg_gen_helper_0_0(do_mfc0_debug); /* PDtrace support */
3030
            rn = "TraceBPC";
3031
//            break;
3032
        default:
3033
            goto die;
3034
        }
3035
        break;
3036
    case 24:
3037
        switch (sel) {
3038
        case 0:
3039
            /* EJTAG support */
3040
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_DEPC));
3041
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
3042
            rn = "DEPC";
3043
            break;
3044
        default:
3045
            goto die;
3046
        }
3047
        break;
3048
    case 25:
3049
        switch (sel) {
3050
        case 0:
3051
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Performance0));
3052
            rn = "Performance0";
3053
            break;
3054
        case 1:
3055
//            tcg_gen_helper_0_0(do_mfc0_performance1);
3056
            rn = "Performance1";
3057
//            break;
3058
        case 2:
3059
//            tcg_gen_helper_0_0(do_mfc0_performance2);
3060
            rn = "Performance2";
3061
//            break;
3062
        case 3:
3063
//            tcg_gen_helper_0_0(do_mfc0_performance3);
3064
            rn = "Performance3";
3065
//            break;
3066
        case 4:
3067
//            tcg_gen_helper_0_0(do_mfc0_performance4);
3068
            rn = "Performance4";
3069
//            break;
3070
        case 5:
3071
//            tcg_gen_helper_0_0(do_mfc0_performance5);
3072
            rn = "Performance5";
3073
//            break;
3074
        case 6:
3075
//            tcg_gen_helper_0_0(do_mfc0_performance6);
3076
            rn = "Performance6";
3077
//            break;
3078
        case 7:
3079
//            tcg_gen_helper_0_0(do_mfc0_performance7);
3080
            rn = "Performance7";
3081
//            break;
3082
        default:
3083
            goto die;
3084
        }
3085
        break;
3086
    case 26:
3087
       rn = "ECC";
3088
       break;
3089
    case 27:
3090
        switch (sel) {
3091
        /* ignored */
3092
        case 0 ... 3:
3093
            rn = "CacheErr";
3094
            break;
3095
        default:
3096
            goto die;
3097
        }
3098
        break;
3099
    case 28:
3100
        switch (sel) {
3101
        case 0:
3102
        case 2:
3103
        case 4:
3104
        case 6:
3105
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_TagLo));
3106
            rn = "TagLo";
3107
            break;
3108
        case 1:
3109
        case 3:
3110
        case 5:
3111
        case 7:
3112
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_DataLo));
3113
            rn = "DataLo";
3114
            break;
3115
        default:
3116
            goto die;
3117
        }
3118
        break;
3119
    case 29:
3120
        switch (sel) {
3121
        case 0:
3122
        case 2:
3123
        case 4:
3124
        case 6:
3125
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_TagHi));
3126
            rn = "TagHi";
3127
            break;
3128
        case 1:
3129
        case 3:
3130
        case 5:
3131
        case 7:
3132
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_DataHi));
3133
            rn = "DataHi";
3134
            break;
3135
        default:
3136
            goto die;
3137
        }
3138
        break;
3139
    case 30:
3140
        switch (sel) {
3141
        case 0:
3142
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_ErrorEPC));
3143
            tcg_gen_ext32s_tl(cpu_T[0], cpu_T[0]);
3144
            rn = "ErrorEPC";
3145
            break;
3146
        default:
3147
            goto die;
3148
        }
3149
        break;
3150
    case 31:
3151
        switch (sel) {
3152
        case 0:
3153
            /* EJTAG support */
3154
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_DESAVE));
3155
            rn = "DESAVE";
3156
            break;
3157
        default:
3158
            goto die;
3159
        }
3160
        break;
3161
    default:
3162
       goto die;
3163
    }
3164
#if defined MIPS_DEBUG_DISAS
3165
    if (loglevel & CPU_LOG_TB_IN_ASM) {
3166
        fprintf(logfile, "mfc0 %s (reg %d sel %d)\n",
3167
                rn, reg, sel);
3168
    }
3169
#endif
3170
    return;
3171

    
3172
die:
3173
#if defined MIPS_DEBUG_DISAS
3174
    if (loglevel & CPU_LOG_TB_IN_ASM) {
3175
        fprintf(logfile, "mfc0 %s (reg %d sel %d)\n",
3176
                rn, reg, sel);
3177
    }
3178
#endif
3179
    generate_exception(ctx, EXCP_RI);
3180
}
3181

    
3182
static void gen_mtc0 (CPUState *env, DisasContext *ctx, int reg, int sel)
3183
{
3184
    const char *rn = "invalid";
3185

    
3186
    if (sel != 0)
3187
        check_insn(env, ctx, ISA_MIPS32);
3188

    
3189
    switch (reg) {
3190
    case 0:
3191
        switch (sel) {
3192
        case 0:
3193
            tcg_gen_helper_0_0(do_mtc0_index);
3194
            rn = "Index";
3195
            break;
3196
        case 1:
3197
            check_insn(env, ctx, ASE_MT);
3198
            tcg_gen_helper_0_0(do_mtc0_mvpcontrol);
3199
            rn = "MVPControl";
3200
            break;
3201
        case 2:
3202
            check_insn(env, ctx, ASE_MT);
3203
            /* ignored */
3204
            rn = "MVPConf0";
3205
            break;
3206
        case 3:
3207
            check_insn(env, ctx, ASE_MT);
3208
            /* ignored */
3209
            rn = "MVPConf1";
3210
            break;
3211
        default:
3212
            goto die;
3213
        }
3214
        break;
3215
    case 1:
3216
        switch (sel) {
3217
        case 0:
3218
            /* ignored */
3219
            rn = "Random";
3220
            break;
3221
        case 1:
3222
            check_insn(env, ctx, ASE_MT);
3223
            tcg_gen_helper_0_0(do_mtc0_vpecontrol);
3224
            rn = "VPEControl";
3225
            break;
3226
        case 2:
3227
            check_insn(env, ctx, ASE_MT);
3228
            tcg_gen_helper_0_0(do_mtc0_vpeconf0);
3229
            rn = "VPEConf0";
3230
            break;
3231
        case 3:
3232
            check_insn(env, ctx, ASE_MT);
3233
            tcg_gen_helper_0_0(do_mtc0_vpeconf1);
3234
            rn = "VPEConf1";
3235
            break;
3236
        case 4:
3237
            check_insn(env, ctx, ASE_MT);
3238
            tcg_gen_helper_0_0(do_mtc0_yqmask);
3239
            rn = "YQMask";
3240
            break;
3241
        case 5:
3242
            check_insn(env, ctx, ASE_MT);
3243
            gen_mtc0_store64(cpu_T[0], offsetof(CPUState, CP0_VPESchedule));
3244
            rn = "VPESchedule";
3245
            break;
3246
        case 6:
3247
            check_insn(env, ctx, ASE_MT);
3248
            gen_mtc0_store64(cpu_T[0], offsetof(CPUState, CP0_VPEScheFBack));
3249
            rn = "VPEScheFBack";
3250
            break;
3251
        case 7:
3252
            check_insn(env, ctx, ASE_MT);
3253
            tcg_gen_helper_0_0(do_mtc0_vpeopt);
3254
            rn = "VPEOpt";
3255
            break;
3256
        default:
3257
            goto die;
3258
        }
3259
        break;
3260
    case 2:
3261
        switch (sel) {
3262
        case 0:
3263
            tcg_gen_helper_0_0(do_mtc0_entrylo0);
3264
            rn = "EntryLo0";
3265
            break;
3266
        case 1:
3267
            check_insn(env, ctx, ASE_MT);
3268
            tcg_gen_helper_0_0(do_mtc0_tcstatus);
3269
            rn = "TCStatus";
3270
            break;
3271
        case 2:
3272
            check_insn(env, ctx, ASE_MT);
3273
            tcg_gen_helper_0_0(do_mtc0_tcbind);
3274
            rn = "TCBind";
3275
            break;
3276
        case 3:
3277
            check_insn(env, ctx, ASE_MT);
3278
            tcg_gen_helper_0_0(do_mtc0_tcrestart);
3279
            rn = "TCRestart";
3280
            break;
3281
        case 4:
3282
            check_insn(env, ctx, ASE_MT);
3283
            tcg_gen_helper_0_0(do_mtc0_tchalt);
3284
            rn = "TCHalt";
3285
            break;
3286
        case 5:
3287
            check_insn(env, ctx, ASE_MT);
3288
            tcg_gen_helper_0_0(do_mtc0_tccontext);
3289
            rn = "TCContext";
3290
            break;
3291
        case 6:
3292
            check_insn(env, ctx, ASE_MT);
3293
            tcg_gen_helper_0_0(do_mtc0_tcschedule);
3294
            rn = "TCSchedule";
3295
            break;
3296
        case 7:
3297
            check_insn(env, ctx, ASE_MT);
3298
            tcg_gen_helper_0_0(do_mtc0_tcschefback);
3299
            rn = "TCScheFBack";
3300
            break;
3301
        default:
3302
            goto die;
3303
        }
3304
        break;
3305
    case 3:
3306
        switch (sel) {
3307
        case 0:
3308
            tcg_gen_helper_0_0(do_mtc0_entrylo1);
3309
            rn = "EntryLo1";
3310
            break;
3311
        default:
3312
            goto die;
3313
        }
3314
        break;
3315
    case 4:
3316
        switch (sel) {
3317
        case 0:
3318
            tcg_gen_helper_0_0(do_mtc0_context);
3319
            rn = "Context";
3320
            break;
3321
        case 1:
3322
//            tcg_gen_helper_0_0(do_mtc0_contextconfig); /* SmartMIPS ASE */
3323
            rn = "ContextConfig";
3324
//            break;
3325
        default:
3326
            goto die;
3327
        }
3328
        break;
3329
    case 5:
3330
        switch (sel) {
3331
        case 0:
3332
            tcg_gen_helper_0_0(do_mtc0_pagemask);
3333
            rn = "PageMask";
3334
            break;
3335
        case 1:
3336
            check_insn(env, ctx, ISA_MIPS32R2);
3337
            tcg_gen_helper_0_0(do_mtc0_pagegrain);
3338
            rn = "PageGrain";
3339
            break;
3340
        default:
3341
            goto die;
3342
        }
3343
        break;
3344
    case 6:
3345
        switch (sel) {
3346
        case 0:
3347
            tcg_gen_helper_0_0(do_mtc0_wired);
3348
            rn = "Wired";
3349
            break;
3350
        case 1:
3351
            check_insn(env, ctx, ISA_MIPS32R2);
3352
            tcg_gen_helper_0_0(do_mtc0_srsconf0);
3353
            rn = "SRSConf0";
3354
            break;
3355
        case 2:
3356
            check_insn(env, ctx, ISA_MIPS32R2);
3357
            tcg_gen_helper_0_0(do_mtc0_srsconf1);
3358
            rn = "SRSConf1";
3359
            break;
3360
        case 3:
3361
            check_insn(env, ctx, ISA_MIPS32R2);
3362
            tcg_gen_helper_0_0(do_mtc0_srsconf2);
3363
            rn = "SRSConf2";
3364
            break;
3365
        case 4:
3366
            check_insn(env, ctx, ISA_MIPS32R2);
3367
            tcg_gen_helper_0_0(do_mtc0_srsconf3);
3368
            rn = "SRSConf3";
3369
            break;
3370
        case 5:
3371
            check_insn(env, ctx, ISA_MIPS32R2);
3372
            tcg_gen_helper_0_0(do_mtc0_srsconf4);
3373
            rn = "SRSConf4";
3374
            break;
3375
        default:
3376
            goto die;
3377
        }
3378
        break;
3379
    case 7:
3380
        switch (sel) {
3381
        case 0:
3382
            check_insn(env, ctx, ISA_MIPS32R2);
3383
            tcg_gen_helper_0_0(do_mtc0_hwrena);
3384
            rn = "HWREna";
3385
            break;
3386
        default:
3387
            goto die;
3388
        }
3389
        break;
3390
    case 8:
3391
        /* ignored */
3392
        rn = "BadVAddr";
3393
        break;
3394
    case 9:
3395
        switch (sel) {
3396
        case 0:
3397
            tcg_gen_helper_0_0(do_mtc0_count);
3398
            rn = "Count";
3399
            break;
3400
        /* 6,7 are implementation dependent */
3401
        default:
3402
            goto die;
3403
        }
3404
        /* Stop translation as we may have switched the execution mode */
3405
        ctx->bstate = BS_STOP;
3406
        break;
3407
    case 10:
3408
        switch (sel) {
3409
        case 0:
3410
            tcg_gen_helper_0_0(do_mtc0_entryhi);
3411
            rn = "EntryHi";
3412
            break;
3413
        default:
3414
            goto die;
3415
        }
3416
        break;
3417
    case 11:
3418
        switch (sel) {
3419
        case 0:
3420
            tcg_gen_helper_0_0(do_mtc0_compare);
3421
            rn = "Compare";
3422
            break;
3423
        /* 6,7 are implementation dependent */
3424
        default:
3425
            goto die;
3426
        }
3427
        /* Stop translation as we may have switched the execution mode */
3428
        ctx->bstate = BS_STOP;
3429
        break;
3430
    case 12:
3431
        switch (sel) {
3432
        case 0:
3433
            tcg_gen_helper_0_0(do_mtc0_status);
3434
            /* BS_STOP isn't good enough here, hflags may have changed. */
3435
            gen_save_pc(ctx->pc + 4);
3436
            ctx->bstate = BS_EXCP;
3437
            rn = "Status";
3438
            break;
3439
        case 1:
3440
            check_insn(env, ctx, ISA_MIPS32R2);
3441
            tcg_gen_helper_0_0(do_mtc0_intctl);
3442
            /* Stop translation as we may have switched the execution mode */
3443
            ctx->bstate = BS_STOP;
3444
            rn = "IntCtl";
3445
            break;
3446
        case 2:
3447
            check_insn(env, ctx, ISA_MIPS32R2);
3448
            tcg_gen_helper_0_0(do_mtc0_srsctl);
3449
            /* Stop translation as we may have switched the execution mode */
3450
            ctx->bstate = BS_STOP;
3451
            rn = "SRSCtl";
3452
            break;
3453
        case 3:
3454
            check_insn(env, ctx, ISA_MIPS32R2);
3455
            gen_mtc0_store32(cpu_T[0], offsetof(CPUState, CP0_SRSMap));
3456
            /* Stop translation as we may have switched the execution mode */
3457
            ctx->bstate = BS_STOP;
3458
            rn = "SRSMap";
3459
            break;
3460
        default:
3461
            goto die;
3462
        }
3463
        break;
3464
    case 13:
3465
        switch (sel) {
3466
        case 0:
3467
            tcg_gen_helper_0_0(do_mtc0_cause);
3468
            rn = "Cause";
3469
            break;
3470
        default:
3471
            goto die;
3472
        }
3473
        /* Stop translation as we may have switched the execution mode */
3474
        ctx->bstate = BS_STOP;
3475
        break;
3476
    case 14:
3477
        switch (sel) {
3478
        case 0:
3479
            gen_mtc0_store64(cpu_T[0], offsetof(CPUState, CP0_EPC));
3480
            rn = "EPC";
3481
            break;
3482
        default:
3483
            goto die;
3484
        }
3485
        break;
3486
    case 15:
3487
        switch (sel) {
3488
        case 0:
3489
            /* ignored */
3490
            rn = "PRid";
3491
            break;
3492
        case 1:
3493
            check_insn(env, ctx, ISA_MIPS32R2);
3494
            tcg_gen_helper_0_0(do_mtc0_ebase);
3495
            rn = "EBase";
3496
            break;
3497
        default:
3498
            goto die;
3499
        }
3500
        break;
3501
    case 16:
3502
        switch (sel) {
3503
        case 0:
3504
            tcg_gen_helper_0_0(do_mtc0_config0);
3505
            rn = "Config";
3506
            /* Stop translation as we may have switched the execution mode */
3507
            ctx->bstate = BS_STOP;
3508
            break;
3509
        case 1:
3510
            /* ignored, read only */
3511
            rn = "Config1";
3512
            break;
3513
        case 2:
3514
            tcg_gen_helper_0_0(do_mtc0_config2);
3515
            rn = "Config2";
3516
            /* Stop translation as we may have switched the execution mode */
3517
            ctx->bstate = BS_STOP;
3518
            break;
3519
        case 3:
3520
            /* ignored, read only */
3521
            rn = "Config3";
3522
            break;
3523
        /* 4,5 are reserved */
3524
        /* 6,7 are implementation dependent */
3525
        case 6:
3526
            /* ignored */
3527
            rn = "Config6";
3528
            break;
3529
        case 7:
3530
            /* ignored */
3531
            rn = "Config7";
3532
            break;
3533
        default:
3534
            rn = "Invalid config selector";
3535
            goto die;
3536
        }
3537
        break;
3538
    case 17:
3539
        switch (sel) {
3540
        case 0:
3541
            /* ignored */
3542
            rn = "LLAddr";
3543
            break;
3544
        default:
3545
            goto die;
3546
        }
3547
        break;
3548
    case 18:
3549
        switch (sel) {
3550
        case 0 ... 7:
3551
            tcg_gen_helper_0_1i(do_mtc0_watchlo, sel);
3552
            rn = "WatchLo";
3553
            break;
3554
        default:
3555
            goto die;
3556
        }
3557
        break;
3558
    case 19:
3559
        switch (sel) {
3560
        case 0 ... 7:
3561
            tcg_gen_helper_0_1i(do_mtc0_watchhi, sel);
3562
            rn = "WatchHi";
3563
            break;
3564
        default:
3565
            goto die;
3566
        }
3567
        break;
3568
    case 20:
3569
        switch (sel) {
3570
        case 0:
3571
#if defined(TARGET_MIPS64)
3572
            check_insn(env, ctx, ISA_MIPS3);
3573
            tcg_gen_helper_0_0(do_mtc0_xcontext);
3574
            rn = "XContext";
3575
            break;
3576
#endif
3577
        default:
3578
            goto die;
3579
        }
3580
        break;
3581
    case 21:
3582
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
3583
        switch (sel) {
3584
        case 0:
3585
            tcg_gen_helper_0_0(do_mtc0_framemask);
3586
            rn = "Framemask";
3587
            break;
3588
        default:
3589
            goto die;
3590
        }
3591
        break;
3592
    case 22:
3593
        /* ignored */
3594
        rn = "Diagnostic"; /* implementation dependent */
3595
        break;
3596
    case 23:
3597
        switch (sel) {
3598
        case 0:
3599
            tcg_gen_helper_0_0(do_mtc0_debug); /* EJTAG support */
3600
            /* BS_STOP isn't good enough here, hflags may have changed. */
3601
            gen_save_pc(ctx->pc + 4);
3602
            ctx->bstate = BS_EXCP;
3603
            rn = "Debug";
3604
            break;
3605
        case 1:
3606
//            tcg_gen_helper_0_0(do_mtc0_tracecontrol); /* PDtrace support */
3607
            rn = "TraceControl";
3608
            /* Stop translation as we may have switched the execution mode */
3609
            ctx->bstate = BS_STOP;
3610
//            break;
3611
        case 2:
3612
//            tcg_gen_helper_0_0(do_mtc0_tracecontrol2); /* PDtrace support */
3613
            rn = "TraceControl2";
3614
            /* Stop translation as we may have switched the execution mode */
3615
            ctx->bstate = BS_STOP;
3616
//            break;
3617
        case 3:
3618
            /* Stop translation as we may have switched the execution mode */
3619
            ctx->bstate = BS_STOP;
3620
//            tcg_gen_helper_0_0(do_mtc0_usertracedata); /* PDtrace support */
3621
            rn = "UserTraceData";
3622
            /* Stop translation as we may have switched the execution mode */
3623
            ctx->bstate = BS_STOP;
3624
//            break;
3625
        case 4:
3626
//            tcg_gen_helper_0_0(do_mtc0_debug); /* PDtrace support */
3627
            /* Stop translation as we may have switched the execution mode */
3628
            ctx->bstate = BS_STOP;
3629
            rn = "TraceBPC";
3630
//            break;
3631
        default:
3632
            goto die;
3633
        }
3634
        break;
3635
    case 24:
3636
        switch (sel) {
3637
        case 0:
3638
            /* EJTAG support */
3639
            gen_mtc0_store64(cpu_T[0], offsetof(CPUState, CP0_DEPC));
3640
            rn = "DEPC";
3641
            break;
3642
        default:
3643
            goto die;
3644
        }
3645
        break;
3646
    case 25:
3647
        switch (sel) {
3648
        case 0:
3649
            tcg_gen_helper_0_0(do_mtc0_performance0);
3650
            rn = "Performance0";
3651
            break;
3652
        case 1:
3653
//            tcg_gen_helper_0_0(do_mtc0_performance1);
3654
            rn = "Performance1";
3655
//            break;
3656
        case 2:
3657
//            tcg_gen_helper_0_0(do_mtc0_performance2);
3658
            rn = "Performance2";
3659
//            break;
3660
        case 3:
3661
//            tcg_gen_helper_0_0(do_mtc0_performance3);
3662
            rn = "Performance3";
3663
//            break;
3664
        case 4:
3665
//            tcg_gen_helper_0_0(do_mtc0_performance4);
3666
            rn = "Performance4";
3667
//            break;
3668
        case 5:
3669
//            tcg_gen_helper_0_0(do_mtc0_performance5);
3670
            rn = "Performance5";
3671
//            break;
3672
        case 6:
3673
//            tcg_gen_helper_0_0(do_mtc0_performance6);
3674
            rn = "Performance6";
3675
//            break;
3676
        case 7:
3677
//            tcg_gen_helper_0_0(do_mtc0_performance7);
3678
            rn = "Performance7";
3679
//            break;
3680
        default:
3681
            goto die;
3682
        }
3683
       break;
3684
    case 26:
3685
        /* ignored */
3686
        rn = "ECC";
3687
        break;
3688
    case 27:
3689
        switch (sel) {
3690
        case 0 ... 3:
3691
            /* ignored */
3692
            rn = "CacheErr";
3693
            break;
3694
        default:
3695
            goto die;
3696
        }
3697
       break;
3698
    case 28:
3699
        switch (sel) {
3700
        case 0:
3701
        case 2:
3702
        case 4:
3703
        case 6:
3704
            tcg_gen_helper_0_0(do_mtc0_taglo);
3705
            rn = "TagLo";
3706
            break;
3707
        case 1:
3708
        case 3:
3709
        case 5:
3710
        case 7:
3711
            tcg_gen_helper_0_0(do_mtc0_datalo);
3712
            rn = "DataLo";
3713
            break;
3714
        default:
3715
            goto die;
3716
        }
3717
        break;
3718
    case 29:
3719
        switch (sel) {
3720
        case 0:
3721
        case 2:
3722
        case 4:
3723
        case 6:
3724
            tcg_gen_helper_0_0(do_mtc0_taghi);
3725
            rn = "TagHi";
3726
            break;
3727
        case 1:
3728
        case 3:
3729
        case 5:
3730
        case 7:
3731
            tcg_gen_helper_0_0(do_mtc0_datahi);
3732
            rn = "DataHi";
3733
            break;
3734
        default:
3735
            rn = "invalid sel";
3736
            goto die;
3737
        }
3738
       break;
3739
    case 30:
3740
        switch (sel) {
3741
        case 0:
3742
            gen_mtc0_store64(cpu_T[0], offsetof(CPUState, CP0_ErrorEPC));
3743
            rn = "ErrorEPC";
3744
            break;
3745
        default:
3746
            goto die;
3747
        }
3748
        break;
3749
    case 31:
3750
        switch (sel) {
3751
        case 0:
3752
            /* EJTAG support */
3753
            gen_mtc0_store32(cpu_T[0], offsetof(CPUState, CP0_DESAVE));
3754
            rn = "DESAVE";
3755
            break;
3756
        default:
3757
            goto die;
3758
        }
3759
        /* Stop translation as we may have switched the execution mode */
3760
        ctx->bstate = BS_STOP;
3761
        break;
3762
    default:
3763
       goto die;
3764
    }
3765
#if defined MIPS_DEBUG_DISAS
3766
    if (loglevel & CPU_LOG_TB_IN_ASM) {
3767
        fprintf(logfile, "mtc0 %s (reg %d sel %d)\n",
3768
                rn, reg, sel);
3769
    }
3770
#endif
3771
    return;
3772

    
3773
die:
3774
#if defined MIPS_DEBUG_DISAS
3775
    if (loglevel & CPU_LOG_TB_IN_ASM) {
3776
        fprintf(logfile, "mtc0 %s (reg %d sel %d)\n",
3777
                rn, reg, sel);
3778
    }
3779
#endif
3780
    generate_exception(ctx, EXCP_RI);
3781
}
3782

    
3783
#if defined(TARGET_MIPS64)
3784
static void gen_dmfc0 (CPUState *env, DisasContext *ctx, int reg, int sel)
3785
{
3786
    const char *rn = "invalid";
3787

    
3788
    if (sel != 0)
3789
        check_insn(env, ctx, ISA_MIPS64);
3790

    
3791
    switch (reg) {
3792
    case 0:
3793
        switch (sel) {
3794
        case 0:
3795
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Index));
3796
            rn = "Index";
3797
            break;
3798
        case 1:
3799
            check_insn(env, ctx, ASE_MT);
3800
            tcg_gen_helper_0_0(do_mfc0_mvpcontrol);
3801
            rn = "MVPControl";
3802
            break;
3803
        case 2:
3804
            check_insn(env, ctx, ASE_MT);
3805
            tcg_gen_helper_0_0(do_mfc0_mvpconf0);
3806
            rn = "MVPConf0";
3807
            break;
3808
        case 3:
3809
            check_insn(env, ctx, ASE_MT);
3810
            tcg_gen_helper_0_0(do_mfc0_mvpconf1);
3811
            rn = "MVPConf1";
3812
            break;
3813
        default:
3814
            goto die;
3815
        }
3816
        break;
3817
    case 1:
3818
        switch (sel) {
3819
        case 0:
3820
            tcg_gen_helper_0_0(do_mfc0_random);
3821
            rn = "Random";
3822
            break;
3823
        case 1:
3824
            check_insn(env, ctx, ASE_MT);
3825
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_VPEControl));
3826
            rn = "VPEControl";
3827
            break;
3828
        case 2:
3829
            check_insn(env, ctx, ASE_MT);
3830
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_VPEConf0));
3831
            rn = "VPEConf0";
3832
            break;
3833
        case 3:
3834
            check_insn(env, ctx, ASE_MT);
3835
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_VPEConf1));
3836
            rn = "VPEConf1";
3837
            break;
3838
        case 4:
3839
            check_insn(env, ctx, ASE_MT);
3840
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_YQMask));
3841
            rn = "YQMask";
3842
            break;
3843
        case 5:
3844
            check_insn(env, ctx, ASE_MT);
3845
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_VPESchedule));
3846
            rn = "VPESchedule";
3847
            break;
3848
        case 6:
3849
            check_insn(env, ctx, ASE_MT);
3850
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_VPEScheFBack));
3851
            rn = "VPEScheFBack";
3852
            break;
3853
        case 7:
3854
            check_insn(env, ctx, ASE_MT);
3855
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_VPEOpt));
3856
            rn = "VPEOpt";
3857
            break;
3858
        default:
3859
            goto die;
3860
        }
3861
        break;
3862
    case 2:
3863
        switch (sel) {
3864
        case 0:
3865
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_EntryLo0));
3866
            rn = "EntryLo0";
3867
            break;
3868
        case 1:
3869
            check_insn(env, ctx, ASE_MT);
3870
            tcg_gen_helper_0_0(do_mfc0_tcstatus);
3871
            rn = "TCStatus";
3872
            break;
3873
        case 2:
3874
            check_insn(env, ctx, ASE_MT);
3875
            tcg_gen_helper_0_0(do_mfc0_tcbind);
3876
            rn = "TCBind";
3877
            break;
3878
        case 3:
3879
            check_insn(env, ctx, ASE_MT);
3880
            tcg_gen_helper_0_0(do_dmfc0_tcrestart);
3881
            rn = "TCRestart";
3882
            break;
3883
        case 4:
3884
            check_insn(env, ctx, ASE_MT);
3885
            tcg_gen_helper_0_0(do_dmfc0_tchalt);
3886
            rn = "TCHalt";
3887
            break;
3888
        case 5:
3889
            check_insn(env, ctx, ASE_MT);
3890
            tcg_gen_helper_0_0(do_dmfc0_tccontext);
3891
            rn = "TCContext";
3892
            break;
3893
        case 6:
3894
            check_insn(env, ctx, ASE_MT);
3895
            tcg_gen_helper_0_0(do_dmfc0_tcschedule);
3896
            rn = "TCSchedule";
3897
            break;
3898
        case 7:
3899
            check_insn(env, ctx, ASE_MT);
3900
            tcg_gen_helper_0_0(do_dmfc0_tcschefback);
3901
            rn = "TCScheFBack";
3902
            break;
3903
        default:
3904
            goto die;
3905
        }
3906
        break;
3907
    case 3:
3908
        switch (sel) {
3909
        case 0:
3910
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_EntryLo1));
3911
            rn = "EntryLo1";
3912
            break;
3913
        default:
3914
            goto die;
3915
        }
3916
        break;
3917
    case 4:
3918
        switch (sel) {
3919
        case 0:
3920
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_Context));
3921
            rn = "Context";
3922
            break;
3923
        case 1:
3924
//            tcg_gen_helper_0_0(do_dmfc0_contextconfig); /* SmartMIPS ASE */
3925
            rn = "ContextConfig";
3926
//            break;
3927
        default:
3928
            goto die;
3929
        }
3930
        break;
3931
    case 5:
3932
        switch (sel) {
3933
        case 0:
3934
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_PageMask));
3935
            rn = "PageMask";
3936
            break;
3937
        case 1:
3938
            check_insn(env, ctx, ISA_MIPS32R2);
3939
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_PageGrain));
3940
            rn = "PageGrain";
3941
            break;
3942
        default:
3943
            goto die;
3944
        }
3945
        break;
3946
    case 6:
3947
        switch (sel) {
3948
        case 0:
3949
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Wired));
3950
            rn = "Wired";
3951
            break;
3952
        case 1:
3953
            check_insn(env, ctx, ISA_MIPS32R2);
3954
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSConf0));
3955
            rn = "SRSConf0";
3956
            break;
3957
        case 2:
3958
            check_insn(env, ctx, ISA_MIPS32R2);
3959
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSConf1));
3960
            rn = "SRSConf1";
3961
            break;
3962
        case 3:
3963
            check_insn(env, ctx, ISA_MIPS32R2);
3964
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSConf2));
3965
            rn = "SRSConf2";
3966
            break;
3967
        case 4:
3968
            check_insn(env, ctx, ISA_MIPS32R2);
3969
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSConf3));
3970
            rn = "SRSConf3";
3971
            break;
3972
        case 5:
3973
            check_insn(env, ctx, ISA_MIPS32R2);
3974
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSConf4));
3975
            rn = "SRSConf4";
3976
            break;
3977
        default:
3978
            goto die;
3979
        }
3980
        break;
3981
    case 7:
3982
        switch (sel) {
3983
        case 0:
3984
            check_insn(env, ctx, ISA_MIPS32R2);
3985
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_HWREna));
3986
            rn = "HWREna";
3987
            break;
3988
        default:
3989
            goto die;
3990
        }
3991
        break;
3992
    case 8:
3993
        switch (sel) {
3994
        case 0:
3995
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_BadVAddr));
3996
            rn = "BadVAddr";
3997
            break;
3998
        default:
3999
            goto die;
4000
        }
4001
        break;
4002
    case 9:
4003
        switch (sel) {
4004
        case 0:
4005
            tcg_gen_helper_0_0(do_mfc0_count);
4006
            rn = "Count";
4007
            break;
4008
        /* 6,7 are implementation dependent */
4009
        default:
4010
            goto die;
4011
        }
4012
        break;
4013
    case 10:
4014
        switch (sel) {
4015
        case 0:
4016
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_EntryHi));
4017
            rn = "EntryHi";
4018
            break;
4019
        default:
4020
            goto die;
4021
        }
4022
        break;
4023
    case 11:
4024
        switch (sel) {
4025
        case 0:
4026
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Compare));
4027
            rn = "Compare";
4028
            break;
4029
        /* 6,7 are implementation dependent */
4030
        default:
4031
            goto die;
4032
        }
4033
        break;
4034
    case 12:
4035
        switch (sel) {
4036
        case 0:
4037
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Status));
4038
            rn = "Status";
4039
            break;
4040
        case 1:
4041
            check_insn(env, ctx, ISA_MIPS32R2);
4042
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_IntCtl));
4043
            rn = "IntCtl";
4044
            break;
4045
        case 2:
4046
            check_insn(env, ctx, ISA_MIPS32R2);
4047
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSCtl));
4048
            rn = "SRSCtl";
4049
            break;
4050
        case 3:
4051
            check_insn(env, ctx, ISA_MIPS32R2);
4052
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_SRSMap));
4053
            rn = "SRSMap";
4054
            break;
4055
        default:
4056
            goto die;
4057
        }
4058
        break;
4059
    case 13:
4060
        switch (sel) {
4061
        case 0:
4062
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Cause));
4063
            rn = "Cause";
4064
            break;
4065
        default:
4066
            goto die;
4067
        }
4068
        break;
4069
    case 14:
4070
        switch (sel) {
4071
        case 0:
4072
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_EPC));
4073
            rn = "EPC";
4074
            break;
4075
        default:
4076
            goto die;
4077
        }
4078
        break;
4079
    case 15:
4080
        switch (sel) {
4081
        case 0:
4082
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_PRid));
4083
            rn = "PRid";
4084
            break;
4085
        case 1:
4086
            check_insn(env, ctx, ISA_MIPS32R2);
4087
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_EBase));
4088
            rn = "EBase";
4089
            break;
4090
        default:
4091
            goto die;
4092
        }
4093
        break;
4094
    case 16:
4095
        switch (sel) {
4096
        case 0:
4097
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config0));
4098
            rn = "Config";
4099
            break;
4100
        case 1:
4101
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config1));
4102
            rn = "Config1";
4103
            break;
4104
        case 2:
4105
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config2));
4106
            rn = "Config2";
4107
            break;
4108
        case 3:
4109
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config3));
4110
            rn = "Config3";
4111
            break;
4112
       /* 6,7 are implementation dependent */
4113
        case 6:
4114
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config6));
4115
            rn = "Config6";
4116
            break;
4117
        case 7:
4118
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Config7));
4119
            rn = "Config7";
4120
            break;
4121
        default:
4122
            goto die;
4123
        }
4124
        break;
4125
    case 17:
4126
        switch (sel) {
4127
        case 0:
4128
            tcg_gen_helper_0_0(do_dmfc0_lladdr);
4129
            rn = "LLAddr";
4130
            break;
4131
        default:
4132
            goto die;
4133
        }
4134
        break;
4135
    case 18:
4136
        switch (sel) {
4137
        case 0 ... 7:
4138
            tcg_gen_helper_0_1i(do_dmfc0_watchlo, sel);
4139
            rn = "WatchLo";
4140
            break;
4141
        default:
4142
            goto die;
4143
        }
4144
        break;
4145
    case 19:
4146
        switch (sel) {
4147
        case 0 ... 7:
4148
            tcg_gen_helper_0_1i(do_mfc0_watchhi, sel);
4149
            rn = "WatchHi";
4150
            break;
4151
        default:
4152
            goto die;
4153
        }
4154
        break;
4155
    case 20:
4156
        switch (sel) {
4157
        case 0:
4158
            check_insn(env, ctx, ISA_MIPS3);
4159
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_XContext));
4160
            rn = "XContext";
4161
            break;
4162
        default:
4163
            goto die;
4164
        }
4165
        break;
4166
    case 21:
4167
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
4168
        switch (sel) {
4169
        case 0:
4170
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Framemask));
4171
            rn = "Framemask";
4172
            break;
4173
        default:
4174
            goto die;
4175
        }
4176
        break;
4177
    case 22:
4178
        /* ignored */
4179
        rn = "'Diagnostic"; /* implementation dependent */
4180
        break;
4181
    case 23:
4182
        switch (sel) {
4183
        case 0:
4184
            tcg_gen_helper_0_0(do_mfc0_debug); /* EJTAG support */
4185
            rn = "Debug";
4186
            break;
4187
        case 1:
4188
//            tcg_gen_helper_0_0(do_dmfc0_tracecontrol); /* PDtrace support */
4189
            rn = "TraceControl";
4190
//            break;
4191
        case 2:
4192
//            tcg_gen_helper_0_0(do_dmfc0_tracecontrol2); /* PDtrace support */
4193
            rn = "TraceControl2";
4194
//            break;
4195
        case 3:
4196
//            tcg_gen_helper_0_0(do_dmfc0_usertracedata); /* PDtrace support */
4197
            rn = "UserTraceData";
4198
//            break;
4199
        case 4:
4200
//            tcg_gen_helper_0_0(do_dmfc0_debug); /* PDtrace support */
4201
            rn = "TraceBPC";
4202
//            break;
4203
        default:
4204
            goto die;
4205
        }
4206
        break;
4207
    case 24:
4208
        switch (sel) {
4209
        case 0:
4210
            /* EJTAG support */
4211
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_DEPC));
4212
            rn = "DEPC";
4213
            break;
4214
        default:
4215
            goto die;
4216
        }
4217
        break;
4218
    case 25:
4219
        switch (sel) {
4220
        case 0:
4221
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_Performance0));
4222
            rn = "Performance0";
4223
            break;
4224
        case 1:
4225
//            tcg_gen_helper_0_0(do_dmfc0_performance1);
4226
            rn = "Performance1";
4227
//            break;
4228
        case 2:
4229
//            tcg_gen_helper_0_0(do_dmfc0_performance2);
4230
            rn = "Performance2";
4231
//            break;
4232
        case 3:
4233
//            tcg_gen_helper_0_0(do_dmfc0_performance3);
4234
            rn = "Performance3";
4235
//            break;
4236
        case 4:
4237
//            tcg_gen_helper_0_0(do_dmfc0_performance4);
4238
            rn = "Performance4";
4239
//            break;
4240
        case 5:
4241
//            tcg_gen_helper_0_0(do_dmfc0_performance5);
4242
            rn = "Performance5";
4243
//            break;
4244
        case 6:
4245
//            tcg_gen_helper_0_0(do_dmfc0_performance6);
4246
            rn = "Performance6";
4247
//            break;
4248
        case 7:
4249
//            tcg_gen_helper_0_0(do_dmfc0_performance7);
4250
            rn = "Performance7";
4251
//            break;
4252
        default:
4253
            goto die;
4254
        }
4255
        break;
4256
    case 26:
4257
       rn = "ECC";
4258
       break;
4259
    case 27:
4260
        switch (sel) {
4261
        /* ignored */
4262
        case 0 ... 3:
4263
            rn = "CacheErr";
4264
            break;
4265
        default:
4266
            goto die;
4267
        }
4268
        break;
4269
    case 28:
4270
        switch (sel) {
4271
        case 0:
4272
        case 2:
4273
        case 4:
4274
        case 6:
4275
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_TagLo));
4276
            rn = "TagLo";
4277
            break;
4278
        case 1:
4279
        case 3:
4280
        case 5:
4281
        case 7:
4282
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_DataLo));
4283
            rn = "DataLo";
4284
            break;
4285
        default:
4286
            goto die;
4287
        }
4288
        break;
4289
    case 29:
4290
        switch (sel) {
4291
        case 0:
4292
        case 2:
4293
        case 4:
4294
        case 6:
4295
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_TagHi));
4296
            rn = "TagHi";
4297
            break;
4298
        case 1:
4299
        case 3:
4300
        case 5:
4301
        case 7:
4302
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_DataHi));
4303
            rn = "DataHi";
4304
            break;
4305
        default:
4306
            goto die;
4307
        }
4308
        break;
4309
    case 30:
4310
        switch (sel) {
4311
        case 0:
4312
            tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_ErrorEPC));
4313
            rn = "ErrorEPC";
4314
            break;
4315
        default:
4316
            goto die;
4317
        }
4318
        break;
4319
    case 31:
4320
        switch (sel) {
4321
        case 0:
4322
            /* EJTAG support */
4323
            gen_mfc0_load32(cpu_T[0], offsetof(CPUState, CP0_DESAVE));
4324
            rn = "DESAVE";
4325
            break;
4326
        default:
4327
            goto die;
4328
        }
4329
        break;
4330
    default:
4331
        goto die;
4332
    }
4333
#if defined MIPS_DEBUG_DISAS
4334
    if (loglevel & CPU_LOG_TB_IN_ASM) {
4335
        fprintf(logfile, "dmfc0 %s (reg %d sel %d)\n",
4336
                rn, reg, sel);
4337
    }
4338
#endif
4339
    return;
4340

    
4341
die:
4342
#if defined MIPS_DEBUG_DISAS
4343
    if (loglevel & CPU_LOG_TB_IN_ASM) {
4344
        fprintf(logfile, "dmfc0 %s (reg %d sel %d)\n",
4345
                rn, reg, sel);
4346
    }
4347
#endif
4348
    generate_exception(ctx, EXCP_RI);
4349
}
4350

    
4351
static void gen_dmtc0 (CPUState *env, DisasContext *ctx, int reg, int sel)
4352
{
4353
    const char *rn = "invalid";
4354

    
4355
    if (sel != 0)
4356
        check_insn(env, ctx, ISA_MIPS64);
4357

    
4358
    switch (reg) {
4359
    case 0:
4360
        switch (sel) {
4361
        case 0:
4362
            tcg_gen_helper_0_0(do_mtc0_index);
4363
            rn = "Index";
4364
            break;
4365
        case 1:
4366
            check_insn(env, ctx, ASE_MT);
4367
            tcg_gen_helper_0_0(do_mtc0_mvpcontrol);
4368
            rn = "MVPControl";
4369
            break;
4370
        case 2:
4371
            check_insn(env, ctx, ASE_MT);
4372
            /* ignored */
4373
            rn = "MVPConf0";
4374
            break;
4375
        case 3:
4376
            check_insn(env, ctx, ASE_MT);
4377
            /* ignored */
4378
            rn = "MVPConf1";
4379
            break;
4380
        default:
4381
            goto die;
4382
        }
4383
        break;
4384
    case 1:
4385
        switch (sel) {
4386
        case 0:
4387
            /* ignored */
4388
            rn = "Random";
4389
            break;
4390
        case 1:
4391
            check_insn(env, ctx, ASE_MT);
4392
            tcg_gen_helper_0_0(do_mtc0_vpecontrol);
4393
            rn = "VPEControl";
4394
            break;
4395
        case 2:
4396
            check_insn(env, ctx, ASE_MT);
4397
            tcg_gen_helper_0_0(do_mtc0_vpeconf0);
4398
            rn = "VPEConf0";
4399
            break;
4400
        case 3:
4401
            check_insn(env, ctx, ASE_MT);
4402
            tcg_gen_helper_0_0(do_mtc0_vpeconf1);
4403
            rn = "VPEConf1";
4404
            break;
4405
        case 4:
4406
            check_insn(env, ctx, ASE_MT);
4407
            tcg_gen_helper_0_0(do_mtc0_yqmask);
4408
            rn = "YQMask";
4409
            break;
4410
        case 5:
4411
            check_insn(env, ctx, ASE_MT);
4412
            tcg_gen_st_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_VPESchedule));
4413
            rn = "VPESchedule";
4414
            break;
4415
        case 6:
4416
            check_insn(env, ctx, ASE_MT);
4417
            tcg_gen_st_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_VPEScheFBack));
4418
            rn = "VPEScheFBack";
4419
            break;
4420
        case 7:
4421
            check_insn(env, ctx, ASE_MT);
4422
            tcg_gen_helper_0_0(do_mtc0_vpeopt);
4423
            rn = "VPEOpt";
4424
            break;
4425
        default:
4426
            goto die;
4427
        }
4428
        break;
4429
    case 2:
4430
        switch (sel) {
4431
        case 0:
4432
            tcg_gen_helper_0_0(do_mtc0_entrylo0);
4433
            rn = "EntryLo0";
4434
            break;
4435
        case 1:
4436
            check_insn(env, ctx, ASE_MT);
4437
            tcg_gen_helper_0_0(do_mtc0_tcstatus);
4438
            rn = "TCStatus";
4439
            break;
4440
        case 2:
4441
            check_insn(env, ctx, ASE_MT);
4442
            tcg_gen_helper_0_0(do_mtc0_tcbind);
4443
            rn = "TCBind";
4444
            break;
4445
        case 3:
4446
            check_insn(env, ctx, ASE_MT);
4447
            tcg_gen_helper_0_0(do_mtc0_tcrestart);
4448
            rn = "TCRestart";
4449
            break;
4450
        case 4:
4451
            check_insn(env, ctx, ASE_MT);
4452
            tcg_gen_helper_0_0(do_mtc0_tchalt);
4453
            rn = "TCHalt";
4454
            break;
4455
        case 5:
4456
            check_insn(env, ctx, ASE_MT);
4457
            tcg_gen_helper_0_0(do_mtc0_tccontext);
4458
            rn = "TCContext";
4459
            break;
4460
        case 6:
4461
            check_insn(env, ctx, ASE_MT);
4462
            tcg_gen_helper_0_0(do_mtc0_tcschedule);
4463
            rn = "TCSchedule";
4464
            break;
4465
        case 7:
4466
            check_insn(env, ctx, ASE_MT);
4467
            tcg_gen_helper_0_0(do_mtc0_tcschefback);
4468
            rn = "TCScheFBack";
4469
            break;
4470
        default:
4471
            goto die;
4472
        }
4473
        break;
4474
    case 3:
4475
        switch (sel) {
4476
        case 0:
4477
            tcg_gen_helper_0_0(do_mtc0_entrylo1);
4478
            rn = "EntryLo1";
4479
            break;
4480
        default:
4481
            goto die;
4482
        }
4483
        break;
4484
    case 4:
4485
        switch (sel) {
4486
        case 0:
4487
            tcg_gen_helper_0_0(do_mtc0_context);
4488
            rn = "Context";
4489
            break;
4490
        case 1:
4491
//           tcg_gen_helper_0_0(do_mtc0_contextconfig); /* SmartMIPS ASE */
4492
            rn = "ContextConfig";
4493
//           break;
4494
        default:
4495
            goto die;
4496
        }
4497
        break;
4498
    case 5:
4499
        switch (sel) {
4500
        case 0:
4501
            tcg_gen_helper_0_0(do_mtc0_pagemask);
4502
            rn = "PageMask";
4503
            break;
4504
        case 1:
4505
            check_insn(env, ctx, ISA_MIPS32R2);
4506
            tcg_gen_helper_0_0(do_mtc0_pagegrain);
4507
            rn = "PageGrain";
4508
            break;
4509
        default:
4510
            goto die;
4511
        }
4512
        break;
4513
    case 6:
4514
        switch (sel) {
4515
        case 0:
4516
            tcg_gen_helper_0_0(do_mtc0_wired);
4517
            rn = "Wired";
4518
            break;
4519
        case 1:
4520
            check_insn(env, ctx, ISA_MIPS32R2);
4521
            tcg_gen_helper_0_0(do_mtc0_srsconf0);
4522
            rn = "SRSConf0";
4523
            break;
4524
        case 2:
4525
            check_insn(env, ctx, ISA_MIPS32R2);
4526
            tcg_gen_helper_0_0(do_mtc0_srsconf1);
4527
            rn = "SRSConf1";
4528
            break;
4529
        case 3:
4530
            check_insn(env, ctx, ISA_MIPS32R2);
4531
            tcg_gen_helper_0_0(do_mtc0_srsconf2);
4532
            rn = "SRSConf2";
4533
            break;
4534
        case 4:
4535
            check_insn(env, ctx, ISA_MIPS32R2);
4536
            tcg_gen_helper_0_0(do_mtc0_srsconf3);
4537
            rn = "SRSConf3";
4538
            break;
4539
        case 5:
4540
            check_insn(env, ctx, ISA_MIPS32R2);
4541
            tcg_gen_helper_0_0(do_mtc0_srsconf4);
4542
            rn = "SRSConf4";
4543
            break;
4544
        default:
4545
            goto die;
4546
        }
4547
        break;
4548
    case 7:
4549
        switch (sel) {
4550
        case 0:
4551
            check_insn(env, ctx, ISA_MIPS32R2);
4552
            tcg_gen_helper_0_0(do_mtc0_hwrena);
4553
            rn = "HWREna";
4554
            break;
4555
        default:
4556
            goto die;
4557
        }
4558
        break;
4559
    case 8:
4560
        /* ignored */
4561
        rn = "BadVAddr";
4562
        break;
4563
    case 9:
4564
        switch (sel) {
4565
        case 0:
4566
            tcg_gen_helper_0_0(do_mtc0_count);
4567
            rn = "Count";
4568
            break;
4569
        /* 6,7 are implementation dependent */
4570
        default:
4571
            goto die;
4572
        }
4573
        /* Stop translation as we may have switched the execution mode */
4574
        ctx->bstate = BS_STOP;
4575
        break;
4576
    case 10:
4577
        switch (sel) {
4578
        case 0:
4579
            tcg_gen_helper_0_0(do_mtc0_entryhi);
4580
            rn = "EntryHi";
4581
            break;
4582
        default:
4583
            goto die;
4584
        }
4585
        break;
4586
    case 11:
4587
        switch (sel) {
4588
        case 0:
4589
            tcg_gen_helper_0_0(do_mtc0_compare);
4590
            rn = "Compare";
4591
            break;
4592
        /* 6,7 are implementation dependent */
4593
        default:
4594
            goto die;
4595
        }
4596
        /* Stop translation as we may have switched the execution mode */
4597
        ctx->bstate = BS_STOP;
4598
        break;
4599
    case 12:
4600
        switch (sel) {
4601
        case 0:
4602
            tcg_gen_helper_0_0(do_mtc0_status);
4603
            /* BS_STOP isn't good enough here, hflags may have changed. */
4604
            gen_save_pc(ctx->pc + 4);
4605
            ctx->bstate = BS_EXCP;
4606
            rn = "Status";
4607
            break;
4608
        case 1:
4609
            check_insn(env, ctx, ISA_MIPS32R2);
4610
            tcg_gen_helper_0_0(do_mtc0_intctl);
4611
            /* Stop translation as we may have switched the execution mode */
4612
            ctx->bstate = BS_STOP;
4613
            rn = "IntCtl";
4614
            break;
4615
        case 2:
4616
            check_insn(env, ctx, ISA_MIPS32R2);
4617
            tcg_gen_helper_0_0(do_mtc0_srsctl);
4618
            /* Stop translation as we may have switched the execution mode */
4619
            ctx->bstate = BS_STOP;
4620
            rn = "SRSCtl";
4621
            break;
4622
        case 3:
4623
            check_insn(env, ctx, ISA_MIPS32R2);
4624
            gen_mtc0_store32(cpu_T[0], offsetof(CPUState, CP0_SRSMap));
4625
            /* Stop translation as we may have switched the execution mode */
4626
            ctx->bstate = BS_STOP;
4627
            rn = "SRSMap";
4628
            break;
4629
        default:
4630
            goto die;
4631
        }
4632
        break;
4633
    case 13:
4634
        switch (sel) {
4635
        case 0:
4636
            tcg_gen_helper_0_0(do_mtc0_cause);
4637
            rn = "Cause";
4638
            break;
4639
        default:
4640
            goto die;
4641
        }
4642
        /* Stop translation as we may have switched the execution mode */
4643
        ctx->bstate = BS_STOP;
4644
        break;
4645
    case 14:
4646
        switch (sel) {
4647
        case 0:
4648
            tcg_gen_st_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_EPC));
4649
            rn = "EPC";
4650
            break;
4651
        default:
4652
            goto die;
4653
        }
4654
        break;
4655
    case 15:
4656
        switch (sel) {
4657
        case 0:
4658
            /* ignored */
4659
            rn = "PRid";
4660
            break;
4661
        case 1:
4662
            check_insn(env, ctx, ISA_MIPS32R2);
4663
            tcg_gen_helper_0_0(do_mtc0_ebase);
4664
            rn = "EBase";
4665
            break;
4666
        default:
4667
            goto die;
4668
        }
4669
        break;
4670
    case 16:
4671
        switch (sel) {
4672
        case 0:
4673
            tcg_gen_helper_0_0(do_mtc0_config0);
4674
            rn = "Config";
4675
            /* Stop translation as we may have switched the execution mode */
4676
            ctx->bstate = BS_STOP;
4677
            break;
4678
        case 1:
4679
            /* ignored */
4680
            rn = "Config1";
4681
            break;
4682
        case 2:
4683
            tcg_gen_helper_0_0(do_mtc0_config2);
4684
            rn = "Config2";
4685
            /* Stop translation as we may have switched the execution mode */
4686
            ctx->bstate = BS_STOP;
4687
            break;
4688
        case 3:
4689
            /* ignored */
4690
            rn = "Config3";
4691
            break;
4692
        /* 6,7 are implementation dependent */
4693
        default:
4694
            rn = "Invalid config selector";
4695
            goto die;
4696
        }
4697
        break;
4698
    case 17:
4699
        switch (sel) {
4700
        case 0:
4701
            /* ignored */
4702
            rn = "LLAddr";
4703
            break;
4704
        default:
4705
            goto die;
4706
        }
4707
        break;
4708
    case 18:
4709
        switch (sel) {
4710
        case 0 ... 7:
4711
            tcg_gen_helper_0_1i(do_mtc0_watchlo, sel);
4712
            rn = "WatchLo";
4713
            break;
4714
        default:
4715
            goto die;
4716
        }
4717
        break;
4718
    case 19:
4719
        switch (sel) {
4720
        case 0 ... 7:
4721
            tcg_gen_helper_0_1i(do_mtc0_watchhi, sel);
4722
            rn = "WatchHi";
4723
            break;
4724
        default:
4725
            goto die;
4726
        }
4727
        break;
4728
    case 20:
4729
        switch (sel) {
4730
        case 0:
4731
            check_insn(env, ctx, ISA_MIPS3);
4732
            tcg_gen_helper_0_0(do_mtc0_xcontext);
4733
            rn = "XContext";
4734
            break;
4735
        default:
4736
            goto die;
4737
        }
4738
        break;
4739
    case 21:
4740
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
4741
        switch (sel) {
4742
        case 0:
4743
            tcg_gen_helper_0_0(do_mtc0_framemask);
4744
            rn = "Framemask";
4745
            break;
4746
        default:
4747
            goto die;
4748
        }
4749
        break;
4750
    case 22:
4751
        /* ignored */
4752
        rn = "Diagnostic"; /* implementation dependent */
4753
        break;
4754
    case 23:
4755
        switch (sel) {
4756
        case 0:
4757
            tcg_gen_helper_0_0(do_mtc0_debug); /* EJTAG support */
4758
            /* BS_STOP isn't good enough here, hflags may have changed. */
4759
            gen_save_pc(ctx->pc + 4);
4760
            ctx->bstate = BS_EXCP;
4761
            rn = "Debug";
4762
            break;
4763
        case 1:
4764
//            tcg_gen_helper_0_0(do_mtc0_tracecontrol); /* PDtrace support */
4765
            /* Stop translation as we may have switched the execution mode */
4766
            ctx->bstate = BS_STOP;
4767
            rn = "TraceControl";
4768
//            break;
4769
        case 2:
4770
//            tcg_gen_helper_0_0(do_mtc0_tracecontrol2); /* PDtrace support */
4771
            /* Stop translation as we may have switched the execution mode */
4772
            ctx->bstate = BS_STOP;
4773
            rn = "TraceControl2";
4774
//            break;
4775
        case 3:
4776
//            tcg_gen_helper_0_0(do_mtc0_usertracedata); /* PDtrace support */
4777
            /* Stop translation as we may have switched the execution mode */
4778
            ctx->bstate = BS_STOP;
4779
            rn = "UserTraceData";
4780
//            break;
4781
        case 4:
4782
//            tcg_gen_helper_0_0(do_mtc0_debug); /* PDtrace support */
4783
            /* Stop translation as we may have switched the execution mode */
4784
            ctx->bstate = BS_STOP;
4785
            rn = "TraceBPC";
4786
//            break;
4787
        default:
4788
            goto die;
4789
        }
4790
        break;
4791
    case 24:
4792
        switch (sel) {
4793
        case 0:
4794
            /* EJTAG support */
4795
            tcg_gen_st_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_DEPC));
4796
            rn = "DEPC";
4797
            break;
4798
        default:
4799
            goto die;
4800
        }
4801
        break;
4802
    case 25:
4803
        switch (sel) {
4804
        case 0:
4805
            tcg_gen_helper_0_0(do_mtc0_performance0);
4806
            rn = "Performance0";
4807
            break;
4808
        case 1:
4809
//            tcg_gen_helper_0_0(do_mtc0_performance1);
4810
            rn = "Performance1";
4811
//            break;
4812
        case 2:
4813
//            tcg_gen_helper_0_0(do_mtc0_performance2);
4814
            rn = "Performance2";
4815
//            break;
4816
        case 3:
4817
//            tcg_gen_helper_0_0(do_mtc0_performance3);
4818
            rn = "Performance3";
4819
//            break;
4820
        case 4:
4821
//            tcg_gen_helper_0_0(do_mtc0_performance4);
4822
            rn = "Performance4";
4823
//            break;
4824
        case 5:
4825
//            tcg_gen_helper_0_0(do_mtc0_performance5);
4826
            rn = "Performance5";
4827
//            break;
4828
        case 6:
4829
//            tcg_gen_helper_0_0(do_mtc0_performance6);
4830
            rn = "Performance6";
4831
//            break;
4832
        case 7:
4833
//            tcg_gen_helper_0_0(do_mtc0_performance7);
4834
            rn = "Performance7";
4835
//            break;
4836
        default:
4837
            goto die;
4838
        }
4839
        break;
4840
    case 26:
4841
        /* ignored */
4842
        rn = "ECC";
4843
        break;
4844
    case 27:
4845
        switch (sel) {
4846
        case 0 ... 3:
4847
            /* ignored */
4848
            rn = "CacheErr";
4849
            break;
4850
        default:
4851
            goto die;
4852
        }
4853
        break;
4854
    case 28:
4855
        switch (sel) {
4856
        case 0:
4857
        case 2:
4858
        case 4:
4859
        case 6:
4860
            tcg_gen_helper_0_0(do_mtc0_taglo);
4861
            rn = "TagLo";
4862
            break;
4863
        case 1:
4864
        case 3:
4865
        case 5:
4866
        case 7:
4867
            tcg_gen_helper_0_0(do_mtc0_datalo);
4868
            rn = "DataLo";
4869
            break;
4870
        default:
4871
            goto die;
4872
        }
4873
        break;
4874
    case 29:
4875
        switch (sel) {
4876
        case 0:
4877
        case 2:
4878
        case 4:
4879
        case 6:
4880
            tcg_gen_helper_0_0(do_mtc0_taghi);
4881
            rn = "TagHi";
4882
            break;
4883
        case 1:
4884
        case 3:
4885
        case 5:
4886
        case 7:
4887
            tcg_gen_helper_0_0(do_mtc0_datahi);
4888
            rn = "DataHi";
4889
            break;
4890
        default:
4891
            rn = "invalid sel";
4892
            goto die;
4893
        }
4894
        break;
4895
    case 30:
4896
        switch (sel) {
4897
        case 0:
4898
            tcg_gen_st_tl(cpu_T[0], cpu_env, offsetof(CPUState, CP0_ErrorEPC));
4899
            rn = "ErrorEPC";
4900
            break;
4901
        default:
4902
            goto die;
4903
        }
4904
        break;
4905
    case 31:
4906
        switch (sel) {
4907
        case 0:
4908
            /* EJTAG support */
4909
            gen_mtc0_store32(cpu_T[0], offsetof(CPUState, CP0_DESAVE));
4910
            rn = "DESAVE";
4911
            break;
4912
        default:
4913
            goto die;
4914
        }
4915
        /* Stop translation as we may have switched the execution mode */
4916
        ctx->bstate = BS_STOP;
4917
        break;
4918
    default:
4919
        goto die;
4920
    }
4921
#if defined MIPS_DEBUG_DISAS
4922
    if (loglevel & CPU_LOG_TB_IN_ASM) {
4923
        fprintf(logfile, "dmtc0 %s (reg %d sel %d)\n",
4924
                rn, reg, sel);
4925
    }
4926
#endif
4927
    return;
4928

    
4929
die:
4930
#if defined MIPS_DEBUG_DISAS
4931
    if (loglevel & CPU_LOG_TB_IN_ASM) {
4932
        fprintf(logfile, "dmtc0 %s (reg %d sel %d)\n",
4933
                rn, reg, sel);
4934
    }
4935
#endif
4936
    generate_exception(ctx, EXCP_RI);
4937
}
4938
#endif /* TARGET_MIPS64 */
4939

    
4940
static void gen_mftr(CPUState *env, DisasContext *ctx, int rt,
4941
                     int u, int sel, int h)
4942
{
4943
    int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
4944

    
4945
    if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
4946
        ((env->CP0_TCBind[other_tc] & (0xf << CP0TCBd_CurVPE)) !=
4947
         (env->CP0_TCBind[env->current_tc] & (0xf << CP0TCBd_CurVPE))))
4948
        tcg_gen_movi_tl(cpu_T[0], -1);
4949
    else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
4950
             (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC)))
4951
        tcg_gen_movi_tl(cpu_T[0], -1);
4952
    else if (u == 0) {
4953
        switch (rt) {
4954
        case 2:
4955
            switch (sel) {
4956
            case 1:
4957
                tcg_gen_helper_0_0(do_mftc0_tcstatus);
4958
                break;
4959
            case 2:
4960
                tcg_gen_helper_0_0(do_mftc0_tcbind);
4961
                break;
4962
            case 3:
4963
                tcg_gen_helper_0_0(do_mftc0_tcrestart);
4964
                break;
4965
            case 4:
4966
                tcg_gen_helper_0_0(do_mftc0_tchalt);
4967
                break;
4968
            case 5:
4969
                tcg_gen_helper_0_0(do_mftc0_tccontext);
4970
                break;
4971
            case 6:
4972
                tcg_gen_helper_0_0(do_mftc0_tcschedule);
4973
                break;
4974
            case 7:
4975
                tcg_gen_helper_0_0(do_mftc0_tcschefback);
4976
                break;
4977
            default:
4978
                gen_mfc0(env, ctx, rt, sel);
4979
                break;
4980
            }
4981
            break;
4982
        case 10:
4983
            switch (sel) {
4984
            case 0:
4985
                tcg_gen_helper_0_0(do_mftc0_entryhi);
4986
                break;
4987
            default:
4988
                gen_mfc0(env, ctx, rt, sel);
4989
                break;
4990
            }
4991
        case 12:
4992
            switch (sel) {
4993
            case 0:
4994
                tcg_gen_helper_0_0(do_mftc0_status);
4995
                break;
4996
            default:
4997
                gen_mfc0(env, ctx, rt, sel);
4998
                break;
4999
            }
5000
        case 23:
5001
            switch (sel) {
5002
            case 0:
5003
                tcg_gen_helper_0_0(do_mftc0_debug);
5004
                break;
5005
            default:
5006
                gen_mfc0(env, ctx, rt, sel);
5007
                break;
5008
            }
5009
            break;
5010
        default:
5011
            gen_mfc0(env, ctx, rt, sel);
5012
        }
5013
    } else switch (sel) {
5014
    /* GPR registers. */
5015
    case 0:
5016
        tcg_gen_helper_0_1i(do_mftgpr, rt);
5017
        break;
5018
    /* Auxiliary CPU registers */
5019
    case 1:
5020
        switch (rt) {
5021
        case 0:
5022
            tcg_gen_helper_0_1i(do_mftlo, 0);
5023
            break;
5024
        case 1:
5025
            tcg_gen_helper_0_1i(do_mfthi, 0);
5026
            break;
5027
        case 2:
5028
            tcg_gen_helper_0_1i(do_mftacx, 0);
5029
            break;
5030
        case 4:
5031
            tcg_gen_helper_0_1i(do_mftlo, 1);
5032
            break;
5033
        case 5:
5034
            tcg_gen_helper_0_1i(do_mfthi, 1);
5035
            break;
5036
        case 6:
5037
            tcg_gen_helper_0_1i(do_mftacx, 1);
5038
            break;
5039
        case 8:
5040
            tcg_gen_helper_0_1i(do_mftlo, 2);
5041
            break;
5042
        case 9:
5043
            tcg_gen_helper_0_1i(do_mfthi, 2);
5044
            break;
5045
        case 10:
5046
            tcg_gen_helper_0_1i(do_mftacx, 2);
5047
            break;
5048
        case 12:
5049
            tcg_gen_helper_0_1i(do_mftlo, 3);
5050
            break;
5051
        case 13:
5052
            tcg_gen_helper_0_1i(do_mfthi, 3);
5053
            break;
5054
        case 14:
5055
            tcg_gen_helper_0_1i(do_mftacx, 3);
5056
            break;
5057
        case 16:
5058
            tcg_gen_helper_0_0(do_mftdsp);
5059
            break;
5060
        default:
5061
            goto die;
5062
        }
5063
        break;
5064
    /* Floating point (COP1). */
5065
    case 2:
5066
        /* XXX: For now we support only a single FPU context. */
5067
        if (h == 0) {
5068
            gen_load_fpr32(fpu32_T[0], rt);
5069
            tcg_gen_ext_i32_tl(cpu_T[0], fpu32_T[0]);
5070
        } else {
5071
            gen_load_fpr32h(fpu32h_T[0], rt);
5072
            tcg_gen_ext_i32_tl(cpu_T[0], fpu32h_T[0]);
5073
        }
5074
        break;
5075
    case 3:
5076
        /* XXX: For now we support only a single FPU context. */
5077
        tcg_gen_helper_0_1i(do_cfc1, rt);
5078
        break;
5079
    /* COP2: Not implemented. */
5080
    case 4:
5081
    case 5:
5082
        /* fall through */
5083
    default:
5084
        goto die;
5085
    }
5086
#if defined MIPS_DEBUG_DISAS
5087
    if (loglevel & CPU_LOG_TB_IN_ASM) {
5088
        fprintf(logfile, "mftr (reg %d u %d sel %d h %d)\n",
5089
                rt, u, sel, h);
5090
    }
5091
#endif
5092
    return;
5093

    
5094
die:
5095
#if defined MIPS_DEBUG_DISAS
5096
    if (loglevel & CPU_LOG_TB_IN_ASM) {
5097
        fprintf(logfile, "mftr (reg %d u %d sel %d h %d)\n",
5098
                rt, u, sel, h);
5099
    }
5100
#endif
5101
    generate_exception(ctx, EXCP_RI);
5102
}
5103

    
5104
static void gen_mttr(CPUState *env, DisasContext *ctx, int rd,
5105
                     int u, int sel, int h)
5106
{
5107
    int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
5108

    
5109
    if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
5110
        ((env->CP0_TCBind[other_tc] & (0xf << CP0TCBd_CurVPE)) !=
5111
         (env->CP0_TCBind[env->current_tc] & (0xf << CP0TCBd_CurVPE))))
5112
        /* NOP */ ;
5113
    else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
5114
             (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC)))
5115
        /* NOP */ ;
5116
    else if (u == 0) {
5117
        switch (rd) {
5118
        case 2:
5119
            switch (sel) {
5120
            case 1:
5121
                tcg_gen_helper_0_0(do_mttc0_tcstatus);
5122
                break;
5123
            case 2:
5124
                tcg_gen_helper_0_0(do_mttc0_tcbind);
5125
                break;
5126
            case 3:
5127
                tcg_gen_helper_0_0(do_mttc0_tcrestart);
5128
                break;
5129
            case 4:
5130
                tcg_gen_helper_0_0(do_mttc0_tchalt);
5131
                break;
5132
            case 5:
5133
                tcg_gen_helper_0_0(do_mttc0_tccontext);
5134
                break;
5135
            case 6:
5136
                tcg_gen_helper_0_0(do_mttc0_tcschedule);
5137
                break;
5138
            case 7:
5139
                tcg_gen_helper_0_0(do_mttc0_tcschefback);
5140
                break;
5141
            default:
5142
                gen_mtc0(env, ctx, rd, sel);
5143
                break;
5144
            }
5145
            break;
5146
        case 10:
5147
            switch (sel) {
5148
            case 0:
5149
                tcg_gen_helper_0_0(do_mttc0_entryhi);
5150
                break;
5151
            default:
5152
                gen_mtc0(env, ctx, rd, sel);
5153
                break;
5154
            }
5155
        case 12:
5156
            switch (sel) {
5157
            case 0:
5158
                tcg_gen_helper_0_0(do_mttc0_status);
5159
                break;
5160
            default:
5161
                gen_mtc0(env, ctx, rd, sel);
5162
                break;
5163
            }
5164
        case 23:
5165
            switch (sel) {
5166
            case 0:
5167
                tcg_gen_helper_0_0(do_mttc0_debug);
5168
                break;
5169
            default:
5170
                gen_mtc0(env, ctx, rd, sel);
5171
                break;
5172
            }
5173
            break;
5174
        default:
5175
            gen_mtc0(env, ctx, rd, sel);
5176
        }
5177
    } else switch (sel) {
5178
    /* GPR registers. */
5179
    case 0:
5180
        tcg_gen_helper_0_1i(do_mttgpr, rd);
5181
        break;
5182
    /* Auxiliary CPU registers */
5183
    case 1:
5184
        switch (rd) {
5185
        case 0:
5186
            tcg_gen_helper_0_1i(do_mttlo, 0);
5187
            break;
5188
        case 1:
5189
            tcg_gen_helper_0_1i(do_mtthi, 0);
5190
            break;
5191
        case 2:
5192
            tcg_gen_helper_0_1i(do_mttacx, 0);
5193
            break;
5194
        case 4:
5195
            tcg_gen_helper_0_1i(do_mttlo, 1);
5196
            break;
5197
        case 5:
5198
            tcg_gen_helper_0_1i(do_mtthi, 1);
5199
            break;
5200
        case 6:
5201
            tcg_gen_helper_0_1i(do_mttacx, 1);
5202
            break;
5203
        case 8:
5204
            tcg_gen_helper_0_1i(do_mttlo, 2);
5205
            break;
5206
        case 9:
5207
            tcg_gen_helper_0_1i(do_mtthi, 2);
5208
            break;
5209
        case 10:
5210
            tcg_gen_helper_0_1i(do_mttacx, 2);
5211
            break;
5212
        case 12:
5213
            tcg_gen_helper_0_1i(do_mttlo, 3);
5214
            break;
5215
        case 13:
5216
            tcg_gen_helper_0_1i(do_mtthi, 3);
5217
            break;
5218
        case 14:
5219
            tcg_gen_helper_0_1i(do_mttacx, 3);
5220
            break;
5221
        case 16:
5222
            tcg_gen_helper_0_0(do_mttdsp);
5223
            break;
5224
        default:
5225
            goto die;
5226
        }
5227
        break;
5228
    /* Floating point (COP1). */
5229
    case 2:
5230
        /* XXX: For now we support only a single FPU context. */
5231
        if (h == 0) {
5232
            tcg_gen_trunc_tl_i32(fpu32_T[0], cpu_T[0]);
5233
            gen_store_fpr32(fpu32_T[0], rd);
5234
        } else {
5235
            tcg_gen_trunc_tl_i32(fpu32h_T[0], cpu_T[0]);
5236
            gen_store_fpr32h(fpu32h_T[0], rd);
5237
        }
5238
        break;
5239
    case 3:
5240
        /* XXX: For now we support only a single FPU context. */
5241
        tcg_gen_helper_0_1i(do_ctc1, rd);
5242
        break;
5243
    /* COP2: Not implemented. */
5244
    case 4:
5245
    case 5:
5246
        /* fall through */
5247
    default:
5248
        goto die;
5249
    }
5250
#if defined MIPS_DEBUG_DISAS
5251
    if (loglevel & CPU_LOG_TB_IN_ASM) {
5252
        fprintf(logfile, "mttr (reg %d u %d sel %d h %d)\n",
5253
                rd, u, sel, h);
5254
    }
5255
#endif
5256
    return;
5257

    
5258
die:
5259
#if defined MIPS_DEBUG_DISAS
5260
    if (loglevel & CPU_LOG_TB_IN_ASM) {
5261
        fprintf(logfile, "mttr (reg %d u %d sel %d h %d)\n",
5262
                rd, u, sel, h);
5263
    }
5264
#endif
5265
    generate_exception(ctx, EXCP_RI);
5266
}
5267

    
5268
static void gen_cp0 (CPUState *env, DisasContext *ctx, uint32_t opc, int rt, int rd)
5269
{
5270
    const char *opn = "ldst";
5271

    
5272
    switch (opc) {
5273
    case OPC_MFC0:
5274
        if (rt == 0) {
5275
            /* Treat as NOP. */
5276
            return;
5277
        }
5278
        gen_mfc0(env, ctx, rd, ctx->opcode & 0x7);
5279
        gen_store_gpr(cpu_T[0], rt);
5280
        opn = "mfc0";
5281
        break;
5282
    case OPC_MTC0:
5283
        gen_load_gpr(cpu_T[0], rt);
5284
        save_cpu_state(ctx, 1);
5285
        gen_mtc0(env, ctx, rd, ctx->opcode & 0x7);
5286
        opn = "mtc0";
5287
        break;
5288
#if defined(TARGET_MIPS64)
5289
    case OPC_DMFC0:
5290
        check_insn(env, ctx, ISA_MIPS3);
5291
        if (rt == 0) {
5292
            /* Treat as NOP. */
5293
            return;
5294
        }
5295
        gen_dmfc0(env, ctx, rd, ctx->opcode & 0x7);
5296
        gen_store_gpr(cpu_T[0], rt);
5297
        opn = "dmfc0";
5298
        break;
5299
    case OPC_DMTC0:
5300
        check_insn(env, ctx, ISA_MIPS3);
5301
        gen_load_gpr(cpu_T[0], rt);
5302
        save_cpu_state(ctx, 1);
5303
        gen_dmtc0(env, ctx, rd, ctx->opcode & 0x7);
5304
        opn = "dmtc0";
5305
        break;
5306
#endif
5307
    case OPC_MFTR:
5308
        check_insn(env, ctx, ASE_MT);
5309
        if (rd == 0) {
5310
            /* Treat as NOP. */
5311
            return;
5312
        }
5313
        gen_mftr(env, ctx, rt, (ctx->opcode >> 5) & 1,
5314
                 ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
5315
        gen_store_gpr(cpu_T[0], rd);
5316
        opn = "mftr";
5317
        break;
5318
    case OPC_MTTR:
5319
        check_insn(env, ctx, ASE_MT);
5320
        gen_load_gpr(cpu_T[0], rt);
5321
        gen_mttr(env, ctx, rd, (ctx->opcode >> 5) & 1,
5322
                 ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
5323
        opn = "mttr";
5324
        break;
5325
    case OPC_TLBWI:
5326
        opn = "tlbwi";
5327
        if (!env->tlb->do_tlbwi)
5328
            goto die;
5329
        tcg_gen_helper_0_0(env->tlb->do_tlbwi);
5330
        break;
5331
    case OPC_TLBWR:
5332
        opn = "tlbwr";
5333
        if (!env->tlb->do_tlbwr)
5334
            goto die;
5335
        tcg_gen_helper_0_0(env->tlb->do_tlbwr);
5336
        break;
5337
    case OPC_TLBP:
5338
        opn = "tlbp";
5339
        if (!env->tlb->do_tlbp)
5340
            goto die;
5341
        tcg_gen_helper_0_0(env->tlb->do_tlbp);
5342
        break;
5343
    case OPC_TLBR:
5344
        opn = "tlbr";
5345
        if (!env->tlb->do_tlbr)
5346
            goto die;
5347
        tcg_gen_helper_0_0(env->tlb->do_tlbr);
5348
        break;
5349
    case OPC_ERET:
5350
        opn = "eret";
5351
        check_insn(env, ctx, ISA_MIPS2);
5352
        save_cpu_state(ctx, 1);
5353
        gen_op_eret();
5354
        ctx->bstate = BS_EXCP;
5355
        break;
5356
    case OPC_DERET:
5357
        opn = "deret";
5358
        check_insn(env, ctx, ISA_MIPS32);
5359
        if (!(ctx->hflags & MIPS_HFLAG_DM)) {
5360
            MIPS_INVAL(opn);
5361
            generate_exception(ctx, EXCP_RI);
5362
        } else {
5363
            save_cpu_state(ctx, 1);
5364
            gen_op_deret();
5365
            ctx->bstate = BS_EXCP;
5366
        }
5367
        break;
5368
    case OPC_WAIT:
5369
        opn = "wait";
5370
        check_insn(env, ctx, ISA_MIPS3 | ISA_MIPS32);
5371
        /* If we get an exception, we want to restart at next instruction */
5372
        ctx->pc += 4;
5373
        save_cpu_state(ctx, 1);
5374
        ctx->pc -= 4;
5375
        tcg_gen_helper_0_0(do_wait);
5376
        ctx->bstate = BS_EXCP;
5377
        break;
5378
    default:
5379
 die:
5380
        MIPS_INVAL(opn);
5381
        generate_exception(ctx, EXCP_RI);
5382
        return;
5383
    }
5384
    MIPS_DEBUG("%s %s %d", opn, regnames[rt], rd);
5385
}
5386
#endif /* !CONFIG_USER_ONLY */
5387

    
5388
/* CP1 Branches (before delay slot) */
5389
static void gen_compute_branch1 (CPUState *env, DisasContext *ctx, uint32_t op,
5390
                                 int32_t cc, int32_t offset)
5391
{
5392
    target_ulong btarget;
5393
    const char *opn = "cp1 cond branch";
5394

    
5395
    if (cc != 0)
5396
        check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
5397

    
5398
    btarget = ctx->pc + 4 + offset;
5399

    
5400
    switch (op) {
5401
    case OPC_BC1F:
5402
        gen_op_bc1f(cc);
5403
        opn = "bc1f";
5404
        goto not_likely;
5405
    case OPC_BC1FL:
5406
        gen_op_bc1f(cc);
5407
        opn = "bc1fl";
5408
        goto likely;
5409
    case OPC_BC1T:
5410
        gen_op_bc1t(cc);
5411
        opn = "bc1t";
5412
        goto not_likely;
5413
    case OPC_BC1TL:
5414
        gen_op_bc1t(cc);
5415
        opn = "bc1tl";
5416
    likely:
5417
        ctx->hflags |= MIPS_HFLAG_BL;
5418
        tcg_gen_st_tl(cpu_T[0], cpu_env, offsetof(CPUState, bcond));
5419
        break;
5420
    case OPC_BC1FANY2:
5421
        gen_op_bc1any2f(cc);
5422
        opn = "bc1any2f";
5423
        goto not_likely;
5424
    case OPC_BC1TANY2:
5425
        gen_op_bc1any2t(cc);
5426
        opn = "bc1any2t";
5427
        goto not_likely;
5428
    case OPC_BC1FANY4:
5429
        gen_op_bc1any4f(cc);
5430
        opn = "bc1any4f";
5431
        goto not_likely;
5432
    case OPC_BC1TANY4:
5433
        gen_op_bc1any4t(cc);
5434
        opn = "bc1any4t";
5435
    not_likely:
5436
        ctx->hflags |= MIPS_HFLAG_BC;
5437
        tcg_gen_st_tl(cpu_T[0], cpu_env, offsetof(CPUState, bcond));
5438
        break;
5439
    default:
5440
        MIPS_INVAL(opn);
5441
        generate_exception (ctx, EXCP_RI);
5442
        return;
5443
    }
5444
    MIPS_DEBUG("%s: cond %02x target " TARGET_FMT_lx, opn,
5445
               ctx->hflags, btarget);
5446
    ctx->btarget = btarget;
5447
}
5448

    
5449
/* Coprocessor 1 (FPU) */
5450

    
5451
#define FOP(func, fmt) (((fmt) << 21) | (func))
5452

    
5453
static void gen_cp1 (DisasContext *ctx, uint32_t opc, int rt, int fs)
5454
{
5455
    const char *opn = "cp1 move";
5456

    
5457
    switch (opc) {
5458
    case OPC_MFC1:
5459
        gen_load_fpr32(fpu32_T[0], fs);
5460
        tcg_gen_ext_i32_tl(cpu_T[0], fpu32_T[0]);
5461
        gen_store_gpr(cpu_T[0], rt);
5462
        opn = "mfc1";
5463
        break;
5464
    case OPC_MTC1:
5465
        gen_load_gpr(cpu_T[0], rt);
5466
        tcg_gen_trunc_tl_i32(fpu32_T[0], cpu_T[0]);
5467
        gen_store_fpr32(fpu32_T[0], fs);
5468
        opn = "mtc1";
5469
        break;
5470
    case OPC_CFC1:
5471
        tcg_gen_helper_0_1i(do_cfc1, fs);
5472
        gen_store_gpr(cpu_T[0], rt);
5473
        opn = "cfc1";
5474
        break;
5475
    case OPC_CTC1:
5476
        gen_load_gpr(cpu_T[0], rt);
5477
        tcg_gen_helper_0_1i(do_ctc1, fs);
5478
        opn = "ctc1";
5479
        break;
5480
    case OPC_DMFC1:
5481
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5482
        tcg_gen_mov_tl(cpu_T[0], fpu64_T[0]);
5483
        gen_store_gpr(cpu_T[0], rt);
5484
        opn = "dmfc1";
5485
        break;
5486
    case OPC_DMTC1:
5487
        gen_load_gpr(cpu_T[0], rt);
5488
        tcg_gen_mov_tl(fpu64_T[0], cpu_T[0]);
5489
        gen_store_fpr64(ctx, fpu64_T[0], fs);
5490
        opn = "dmtc1";
5491
        break;
5492
    case OPC_MFHC1:
5493
        gen_load_fpr32h(fpu32h_T[0], fs);
5494
        tcg_gen_ext_i32_tl(cpu_T[0], fpu32h_T[0]);
5495
        gen_store_gpr(cpu_T[0], rt);
5496
        opn = "mfhc1";
5497
        break;
5498
    case OPC_MTHC1:
5499
        gen_load_gpr(cpu_T[0], rt);
5500
        tcg_gen_trunc_tl_i32(fpu32h_T[0], cpu_T[0]);
5501
        gen_store_fpr32h(fpu32h_T[0], fs);
5502
        opn = "mthc1";
5503
        break;
5504
    default:
5505
        MIPS_INVAL(opn);
5506
        generate_exception (ctx, EXCP_RI);
5507
        return;
5508
    }
5509
    MIPS_DEBUG("%s %s %s", opn, regnames[rt], fregnames[fs]);
5510
}
5511

    
5512
static void gen_movci (DisasContext *ctx, int rd, int rs, int cc, int tf)
5513
{
5514
    int l1 = gen_new_label();
5515
    uint32_t ccbit;
5516
    TCGCond cond;
5517

    
5518
    if (cc)
5519
        ccbit = 1 << (24 + cc);
5520
    else
5521
        ccbit = 1 << 23;
5522
    if (tf)
5523
        cond = TCG_COND_EQ;
5524
    else
5525
        cond = TCG_COND_NE;
5526

    
5527
    gen_load_gpr(cpu_T[0], rd);
5528
    gen_load_gpr(cpu_T[1], rs);
5529
    {
5530
        TCGv r_ptr = tcg_temp_new(TCG_TYPE_PTR);
5531
        TCGv r_tmp = tcg_temp_local_new(TCG_TYPE_I32);
5532

    
5533
        tcg_gen_ld_ptr(r_ptr, cpu_env, offsetof(CPUState, fpu));
5534
        tcg_gen_ld_i32(r_tmp, r_ptr, offsetof(CPUMIPSFPUContext, fcr31));
5535
        tcg_temp_free(r_ptr);
5536
        tcg_gen_andi_i32(r_tmp, r_tmp, ccbit);
5537
        tcg_gen_brcondi_i32(cond, r_tmp, 0, l1);
5538
        tcg_temp_free(r_tmp);
5539
    }
5540
    tcg_gen_mov_tl(cpu_T[0], cpu_T[1]);
5541

    
5542
    gen_set_label(l1);
5543
    gen_store_gpr(cpu_T[0], rd);
5544
}
5545

    
5546
#define GEN_MOVCF(fmt)                                                \
5547
static void glue(gen_movcf_, fmt) (DisasContext *ctx, int cc, int tf) \
5548
{                                                                     \
5549
    uint32_t ccbit;                                                   \
5550
                                                                      \
5551
    if (cc) {                                                         \
5552
        ccbit = 1 << (24 + cc);                                       \
5553
    } else                                                            \
5554
        ccbit = 1 << 23;                                              \
5555
    if (!tf)                                                          \
5556
        glue(gen_op_float_movf_, fmt)(ccbit);                         \
5557
    else                                                              \
5558
        glue(gen_op_float_movt_, fmt)(ccbit);                         \
5559
}
5560
GEN_MOVCF(d);
5561
GEN_MOVCF(s);
5562
#undef GEN_MOVCF
5563

    
5564
static void gen_farith (DisasContext *ctx, uint32_t op1,
5565
                        int ft, int fs, int fd, int cc)
5566
{
5567
    const char *opn = "farith";
5568
    const char *condnames[] = {
5569
            "c.f",
5570
            "c.un",
5571
            "c.eq",
5572
            "c.ueq",
5573
            "c.olt",
5574
            "c.ult",
5575
            "c.ole",
5576
            "c.ule",
5577
            "c.sf",
5578
            "c.ngle",
5579
            "c.seq",
5580
            "c.ngl",
5581
            "c.lt",
5582
            "c.nge",
5583
            "c.le",
5584
            "c.ngt",
5585
    };
5586
    const char *condnames_abs[] = {
5587
            "cabs.f",
5588
            "cabs.un",
5589
            "cabs.eq",
5590
            "cabs.ueq",
5591
            "cabs.olt",
5592
            "cabs.ult",
5593
            "cabs.ole",
5594
            "cabs.ule",
5595
            "cabs.sf",
5596
            "cabs.ngle",
5597
            "cabs.seq",
5598
            "cabs.ngl",
5599
            "cabs.lt",
5600
            "cabs.nge",
5601
            "cabs.le",
5602
            "cabs.ngt",
5603
    };
5604
    enum { BINOP, CMPOP, OTHEROP } optype = OTHEROP;
5605
    uint32_t func = ctx->opcode & 0x3f;
5606

    
5607
    switch (ctx->opcode & FOP(0x3f, 0x1f)) {
5608
    case FOP(0, 16):
5609
        gen_load_fpr32(fpu32_T[0], fs);
5610
        gen_load_fpr32(fpu32_T[1], ft);
5611
        tcg_gen_helper_0_0(do_float_add_s);
5612
        gen_store_fpr32(fpu32_T[2], fd);
5613
        opn = "add.s";
5614
        optype = BINOP;
5615
        break;
5616
    case FOP(1, 16):
5617
        gen_load_fpr32(fpu32_T[0], fs);
5618
        gen_load_fpr32(fpu32_T[1], ft);
5619
        tcg_gen_helper_0_0(do_float_sub_s);
5620
        gen_store_fpr32(fpu32_T[2], fd);
5621
        opn = "sub.s";
5622
        optype = BINOP;
5623
        break;
5624
    case FOP(2, 16):
5625
        gen_load_fpr32(fpu32_T[0], fs);
5626
        gen_load_fpr32(fpu32_T[1], ft);
5627
        tcg_gen_helper_0_0(do_float_mul_s);
5628
        gen_store_fpr32(fpu32_T[2], fd);
5629
        opn = "mul.s";
5630
        optype = BINOP;
5631
        break;
5632
    case FOP(3, 16):
5633
        gen_load_fpr32(fpu32_T[0], fs);
5634
        gen_load_fpr32(fpu32_T[1], ft);
5635
        tcg_gen_helper_0_0(do_float_div_s);
5636
        gen_store_fpr32(fpu32_T[2], fd);
5637
        opn = "div.s";
5638
        optype = BINOP;
5639
        break;
5640
    case FOP(4, 16):
5641
        gen_load_fpr32(fpu32_T[0], fs);
5642
        gen_op_float_sqrt_s();
5643
        gen_store_fpr32(fpu32_T[2], fd);
5644
        opn = "sqrt.s";
5645
        break;
5646
    case FOP(5, 16):
5647
        gen_load_fpr32(fpu32_T[0], fs);
5648
        gen_op_float_abs_s();
5649
        gen_store_fpr32(fpu32_T[2], fd);
5650
        opn = "abs.s";
5651
        break;
5652
    case FOP(6, 16):
5653
        gen_load_fpr32(fpu32_T[0], fs);
5654
        gen_op_float_mov_s();
5655
        gen_store_fpr32(fpu32_T[2], fd);
5656
        opn = "mov.s";
5657
        break;
5658
    case FOP(7, 16):
5659
        gen_load_fpr32(fpu32_T[0], fs);
5660
        gen_op_float_chs_s();
5661
        gen_store_fpr32(fpu32_T[2], fd);
5662
        opn = "neg.s";
5663
        break;
5664
    case FOP(8, 16):
5665
        check_cp1_64bitmode(ctx);
5666
        gen_load_fpr32(fpu32_T[0], fs);
5667
        tcg_gen_helper_0_0(do_float_roundl_s);
5668
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5669
        opn = "round.l.s";
5670
        break;
5671
    case FOP(9, 16):
5672
        check_cp1_64bitmode(ctx);
5673
        gen_load_fpr32(fpu32_T[0], fs);
5674
        tcg_gen_helper_0_0(do_float_truncl_s);
5675
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5676
        opn = "trunc.l.s";
5677
        break;
5678
    case FOP(10, 16):
5679
        check_cp1_64bitmode(ctx);
5680
        gen_load_fpr32(fpu32_T[0], fs);
5681
        tcg_gen_helper_0_0(do_float_ceill_s);
5682
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5683
        opn = "ceil.l.s";
5684
        break;
5685
    case FOP(11, 16):
5686
        check_cp1_64bitmode(ctx);
5687
        gen_load_fpr32(fpu32_T[0], fs);
5688
        tcg_gen_helper_0_0(do_float_floorl_s);
5689
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5690
        opn = "floor.l.s";
5691
        break;
5692
    case FOP(12, 16):
5693
        gen_load_fpr32(fpu32_T[0], fs);
5694
        tcg_gen_helper_0_0(do_float_roundw_s);
5695
        gen_store_fpr32(fpu32_T[2], fd);
5696
        opn = "round.w.s";
5697
        break;
5698
    case FOP(13, 16):
5699
        gen_load_fpr32(fpu32_T[0], fs);
5700
        tcg_gen_helper_0_0(do_float_truncw_s);
5701
        gen_store_fpr32(fpu32_T[2], fd);
5702
        opn = "trunc.w.s";
5703
        break;
5704
    case FOP(14, 16):
5705
        gen_load_fpr32(fpu32_T[0], fs);
5706
        tcg_gen_helper_0_0(do_float_ceilw_s);
5707
        gen_store_fpr32(fpu32_T[2], fd);
5708
        opn = "ceil.w.s";
5709
        break;
5710
    case FOP(15, 16):
5711
        gen_load_fpr32(fpu32_T[0], fs);
5712
        tcg_gen_helper_0_0(do_float_floorw_s);
5713
        gen_store_fpr32(fpu32_T[2], fd);
5714
        opn = "floor.w.s";
5715
        break;
5716
    case FOP(17, 16):
5717
        gen_load_gpr(cpu_T[0], ft);
5718
        gen_load_fpr32(fpu32_T[0], fs);
5719
        gen_load_fpr32(fpu32_T[2], fd);
5720
        gen_movcf_s(ctx, (ft >> 2) & 0x7, ft & 0x1);
5721
        gen_store_fpr32(fpu32_T[2], fd);
5722
        opn = "movcf.s";
5723
        break;
5724
    case FOP(18, 16):
5725
        gen_load_gpr(cpu_T[0], ft);
5726
        gen_load_fpr32(fpu32_T[0], fs);
5727
        gen_load_fpr32(fpu32_T[2], fd);
5728
        gen_op_float_movz_s();
5729
        gen_store_fpr32(fpu32_T[2], fd);
5730
        opn = "movz.s";
5731
        break;
5732
    case FOP(19, 16):
5733
        gen_load_gpr(cpu_T[0], ft);
5734
        gen_load_fpr32(fpu32_T[0], fs);
5735
        gen_load_fpr32(fpu32_T[2], fd);
5736
        gen_op_float_movn_s();
5737
        gen_store_fpr32(fpu32_T[2], fd);
5738
        opn = "movn.s";
5739
        break;
5740
    case FOP(21, 16):
5741
        check_cop1x(ctx);
5742
        gen_load_fpr32(fpu32_T[0], fs);
5743
        tcg_gen_helper_0_0(do_float_recip_s);
5744
        gen_store_fpr32(fpu32_T[2], fd);
5745
        opn = "recip.s";
5746
        break;
5747
    case FOP(22, 16):
5748
        check_cop1x(ctx);
5749
        gen_load_fpr32(fpu32_T[0], fs);
5750
        tcg_gen_helper_0_0(do_float_rsqrt_s);
5751
        gen_store_fpr32(fpu32_T[2], fd);
5752
        opn = "rsqrt.s";
5753
        break;
5754
    case FOP(28, 16):
5755
        check_cp1_64bitmode(ctx);
5756
        gen_load_fpr32(fpu32_T[0], fs);
5757
        gen_load_fpr32(fpu32_T[2], fd);
5758
        tcg_gen_helper_0_0(do_float_recip2_s);
5759
        gen_store_fpr32(fpu32_T[2], fd);
5760
        opn = "recip2.s";
5761
        break;
5762
    case FOP(29, 16):
5763
        check_cp1_64bitmode(ctx);
5764
        gen_load_fpr32(fpu32_T[0], fs);
5765
        tcg_gen_helper_0_0(do_float_recip1_s);
5766
        gen_store_fpr32(fpu32_T[2], fd);
5767
        opn = "recip1.s";
5768
        break;
5769
    case FOP(30, 16):
5770
        check_cp1_64bitmode(ctx);
5771
        gen_load_fpr32(fpu32_T[0], fs);
5772
        tcg_gen_helper_0_0(do_float_rsqrt1_s);
5773
        gen_store_fpr32(fpu32_T[2], fd);
5774
        opn = "rsqrt1.s";
5775
        break;
5776
    case FOP(31, 16):
5777
        check_cp1_64bitmode(ctx);
5778
        gen_load_fpr32(fpu32_T[0], fs);
5779
        gen_load_fpr32(fpu32_T[2], ft);
5780
        tcg_gen_helper_0_0(do_float_rsqrt2_s);
5781
        gen_store_fpr32(fpu32_T[2], fd);
5782
        opn = "rsqrt2.s";
5783
        break;
5784
    case FOP(33, 16):
5785
        check_cp1_registers(ctx, fd);
5786
        gen_load_fpr32(fpu32_T[0], fs);
5787
        tcg_gen_helper_0_0(do_float_cvtd_s);
5788
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5789
        opn = "cvt.d.s";
5790
        break;
5791
    case FOP(36, 16):
5792
        gen_load_fpr32(fpu32_T[0], fs);
5793
        tcg_gen_helper_0_0(do_float_cvtw_s);
5794
        gen_store_fpr32(fpu32_T[2], fd);
5795
        opn = "cvt.w.s";
5796
        break;
5797
    case FOP(37, 16):
5798
        check_cp1_64bitmode(ctx);
5799
        gen_load_fpr32(fpu32_T[0], fs);
5800
        tcg_gen_helper_0_0(do_float_cvtl_s);
5801
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5802
        opn = "cvt.l.s";
5803
        break;
5804
    case FOP(38, 16):
5805
        check_cp1_64bitmode(ctx);
5806
        gen_load_fpr32(fpu32_T[1], fs);
5807
        gen_load_fpr32(fpu32_T[0], ft);
5808
        gen_op_float_cvtps_s();
5809
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5810
        opn = "cvt.ps.s";
5811
        break;
5812
    case FOP(48, 16):
5813
    case FOP(49, 16):
5814
    case FOP(50, 16):
5815
    case FOP(51, 16):
5816
    case FOP(52, 16):
5817
    case FOP(53, 16):
5818
    case FOP(54, 16):
5819
    case FOP(55, 16):
5820
    case FOP(56, 16):
5821
    case FOP(57, 16):
5822
    case FOP(58, 16):
5823
    case FOP(59, 16):
5824
    case FOP(60, 16):
5825
    case FOP(61, 16):
5826
    case FOP(62, 16):
5827
    case FOP(63, 16):
5828
        gen_load_fpr32(fpu32_T[0], fs);
5829
        gen_load_fpr32(fpu32_T[1], ft);
5830
        if (ctx->opcode & (1 << 6)) {
5831
            check_cop1x(ctx);
5832
            gen_cmpabs_s(func-48, cc);
5833
            opn = condnames_abs[func-48];
5834
        } else {
5835
            gen_cmp_s(func-48, cc);
5836
            opn = condnames[func-48];
5837
        }
5838
        break;
5839
    case FOP(0, 17):
5840
        check_cp1_registers(ctx, fs | ft | fd);
5841
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5842
        gen_load_fpr64(ctx, fpu64_T[1], ft);
5843
        tcg_gen_helper_0_0(do_float_add_d);
5844
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5845
        opn = "add.d";
5846
        optype = BINOP;
5847
        break;
5848
    case FOP(1, 17):
5849
        check_cp1_registers(ctx, fs | ft | fd);
5850
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5851
        gen_load_fpr64(ctx, fpu64_T[1], ft);
5852
        tcg_gen_helper_0_0(do_float_sub_d);
5853
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5854
        opn = "sub.d";
5855
        optype = BINOP;
5856
        break;
5857
    case FOP(2, 17):
5858
        check_cp1_registers(ctx, fs | ft | fd);
5859
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5860
        gen_load_fpr64(ctx, fpu64_T[1], ft);
5861
        tcg_gen_helper_0_0(do_float_mul_d);
5862
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5863
        opn = "mul.d";
5864
        optype = BINOP;
5865
        break;
5866
    case FOP(3, 17):
5867
        check_cp1_registers(ctx, fs | ft | fd);
5868
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5869
        gen_load_fpr64(ctx, fpu64_T[1], ft);
5870
        tcg_gen_helper_0_0(do_float_div_d);
5871
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5872
        opn = "div.d";
5873
        optype = BINOP;
5874
        break;
5875
    case FOP(4, 17):
5876
        check_cp1_registers(ctx, fs | fd);
5877
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5878
        gen_op_float_sqrt_d();
5879
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5880
        opn = "sqrt.d";
5881
        break;
5882
    case FOP(5, 17):
5883
        check_cp1_registers(ctx, fs | fd);
5884
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5885
        gen_op_float_abs_d();
5886
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5887
        opn = "abs.d";
5888
        break;
5889
    case FOP(6, 17):
5890
        check_cp1_registers(ctx, fs | fd);
5891
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5892
        gen_op_float_mov_d();
5893
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5894
        opn = "mov.d";
5895
        break;
5896
    case FOP(7, 17):
5897
        check_cp1_registers(ctx, fs | fd);
5898
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5899
        gen_op_float_chs_d();
5900
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5901
        opn = "neg.d";
5902
        break;
5903
    case FOP(8, 17):
5904
        check_cp1_64bitmode(ctx);
5905
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5906
        tcg_gen_helper_0_0(do_float_roundl_d);
5907
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5908
        opn = "round.l.d";
5909
        break;
5910
    case FOP(9, 17):
5911
        check_cp1_64bitmode(ctx);
5912
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5913
        tcg_gen_helper_0_0(do_float_truncl_d);
5914
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5915
        opn = "trunc.l.d";
5916
        break;
5917
    case FOP(10, 17):
5918
        check_cp1_64bitmode(ctx);
5919
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5920
        tcg_gen_helper_0_0(do_float_ceill_d);
5921
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5922
        opn = "ceil.l.d";
5923
        break;
5924
    case FOP(11, 17):
5925
        check_cp1_64bitmode(ctx);
5926
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5927
        tcg_gen_helper_0_0(do_float_floorl_d);
5928
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5929
        opn = "floor.l.d";
5930
        break;
5931
    case FOP(12, 17):
5932
        check_cp1_registers(ctx, fs);
5933
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5934
        tcg_gen_helper_0_0(do_float_roundw_d);
5935
        gen_store_fpr32(fpu32_T[2], fd);
5936
        opn = "round.w.d";
5937
        break;
5938
    case FOP(13, 17):
5939
        check_cp1_registers(ctx, fs);
5940
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5941
        tcg_gen_helper_0_0(do_float_truncw_d);
5942
        gen_store_fpr32(fpu32_T[2], fd);
5943
        opn = "trunc.w.d";
5944
        break;
5945
    case FOP(14, 17):
5946
        check_cp1_registers(ctx, fs);
5947
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5948
        tcg_gen_helper_0_0(do_float_ceilw_d);
5949
        gen_store_fpr32(fpu32_T[2], fd);
5950
        opn = "ceil.w.d";
5951
        break;
5952
    case FOP(15, 17):
5953
        check_cp1_registers(ctx, fs);
5954
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5955
        tcg_gen_helper_0_0(do_float_floorw_d);
5956
        gen_store_fpr32(fpu32_T[2], fd);
5957
        opn = "floor.w.d";
5958
        break;
5959
    case FOP(17, 17):
5960
        gen_load_gpr(cpu_T[0], ft);
5961
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5962
        gen_load_fpr64(ctx, fpu64_T[2], fd);
5963
        gen_movcf_d(ctx, (ft >> 2) & 0x7, ft & 0x1);
5964
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5965
        opn = "movcf.d";
5966
        break;
5967
    case FOP(18, 17):
5968
        gen_load_gpr(cpu_T[0], ft);
5969
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5970
        gen_load_fpr64(ctx, fpu64_T[2], fd);
5971
        gen_op_float_movz_d();
5972
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5973
        opn = "movz.d";
5974
        break;
5975
    case FOP(19, 17):
5976
        gen_load_gpr(cpu_T[0], ft);
5977
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5978
        gen_load_fpr64(ctx, fpu64_T[2], fd);
5979
        gen_op_float_movn_d();
5980
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5981
        opn = "movn.d";
5982
        break;
5983
    case FOP(21, 17):
5984
        check_cp1_64bitmode(ctx);
5985
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5986
        tcg_gen_helper_0_0(do_float_recip_d);
5987
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5988
        opn = "recip.d";
5989
        break;
5990
    case FOP(22, 17):
5991
        check_cp1_64bitmode(ctx);
5992
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5993
        tcg_gen_helper_0_0(do_float_rsqrt_d);
5994
        gen_store_fpr64(ctx, fpu64_T[2], fd);
5995
        opn = "rsqrt.d";
5996
        break;
5997
    case FOP(28, 17):
5998
        check_cp1_64bitmode(ctx);
5999
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6000
        gen_load_fpr64(ctx, fpu64_T[2], ft);
6001
        tcg_gen_helper_0_0(do_float_recip2_d);
6002
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6003
        opn = "recip2.d";
6004
        break;
6005
    case FOP(29, 17):
6006
        check_cp1_64bitmode(ctx);
6007
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6008
        tcg_gen_helper_0_0(do_float_recip1_d);
6009
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6010
        opn = "recip1.d";
6011
        break;
6012
    case FOP(30, 17):
6013
        check_cp1_64bitmode(ctx);
6014
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6015
        tcg_gen_helper_0_0(do_float_rsqrt1_d);
6016
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6017
        opn = "rsqrt1.d";
6018
        break;
6019
    case FOP(31, 17):
6020
        check_cp1_64bitmode(ctx);
6021
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6022
        gen_load_fpr64(ctx, fpu64_T[2], ft);
6023
        tcg_gen_helper_0_0(do_float_rsqrt2_d);
6024
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6025
        opn = "rsqrt2.d";
6026
        break;
6027
    case FOP(48, 17):
6028
    case FOP(49, 17):
6029
    case FOP(50, 17):
6030
    case FOP(51, 17):
6031
    case FOP(52, 17):
6032
    case FOP(53, 17):
6033
    case FOP(54, 17):
6034
    case FOP(55, 17):
6035
    case FOP(56, 17):
6036
    case FOP(57, 17):
6037
    case FOP(58, 17):
6038
    case FOP(59, 17):
6039
    case FOP(60, 17):
6040
    case FOP(61, 17):
6041
    case FOP(62, 17):
6042
    case FOP(63, 17):
6043
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6044
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6045
        if (ctx->opcode & (1 << 6)) {
6046
            check_cop1x(ctx);
6047
            check_cp1_registers(ctx, fs | ft);
6048
            gen_cmpabs_d(func-48, cc);
6049
            opn = condnames_abs[func-48];
6050
        } else {
6051
            check_cp1_registers(ctx, fs | ft);
6052
            gen_cmp_d(func-48, cc);
6053
            opn = condnames[func-48];
6054
        }
6055
        break;
6056
    case FOP(32, 17):
6057
        check_cp1_registers(ctx, fs);
6058
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6059
        tcg_gen_helper_0_0(do_float_cvts_d);
6060
        gen_store_fpr32(fpu32_T[2], fd);
6061
        opn = "cvt.s.d";
6062
        break;
6063
    case FOP(36, 17):
6064
        check_cp1_registers(ctx, fs);
6065
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6066
        tcg_gen_helper_0_0(do_float_cvtw_d);
6067
        gen_store_fpr32(fpu32_T[2], fd);
6068
        opn = "cvt.w.d";
6069
        break;
6070
    case FOP(37, 17):
6071
        check_cp1_64bitmode(ctx);
6072
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6073
        tcg_gen_helper_0_0(do_float_cvtl_d);
6074
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6075
        opn = "cvt.l.d";
6076
        break;
6077
    case FOP(32, 20):
6078
        gen_load_fpr32(fpu32_T[0], fs);
6079
        tcg_gen_helper_0_0(do_float_cvts_w);
6080
        gen_store_fpr32(fpu32_T[2], fd);
6081
        opn = "cvt.s.w";
6082
        break;
6083
    case FOP(33, 20):
6084
        check_cp1_registers(ctx, fd);
6085
        gen_load_fpr32(fpu32_T[0], fs);
6086
        tcg_gen_helper_0_0(do_float_cvtd_w);
6087
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6088
        opn = "cvt.d.w";
6089
        break;
6090
    case FOP(32, 21):
6091
        check_cp1_64bitmode(ctx);
6092
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6093
        tcg_gen_helper_0_0(do_float_cvts_l);
6094
        gen_store_fpr32(fpu32_T[2], fd);
6095
        opn = "cvt.s.l";
6096
        break;
6097
    case FOP(33, 21):
6098
        check_cp1_64bitmode(ctx);
6099
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6100
        tcg_gen_helper_0_0(do_float_cvtd_l);
6101
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6102
        opn = "cvt.d.l";
6103
        break;
6104
    case FOP(38, 20):
6105
        check_cp1_64bitmode(ctx);
6106
        gen_load_fpr32(fpu32_T[0], fs);
6107
        gen_load_fpr32h(fpu32h_T[0], fs);
6108
        tcg_gen_helper_0_0(do_float_cvtps_pw);
6109
        gen_store_fpr32(fpu32_T[2], fd);
6110
        gen_store_fpr32h(fpu32h_T[2], fd);
6111
        opn = "cvt.ps.pw";
6112
        break;
6113
    case FOP(0, 22):
6114
        check_cp1_64bitmode(ctx);
6115
        gen_load_fpr32(fpu32_T[0], fs);
6116
        gen_load_fpr32h(fpu32h_T[0], fs);
6117
        gen_load_fpr32(fpu32_T[1], ft);
6118
        gen_load_fpr32h(fpu32h_T[1], ft);
6119
        tcg_gen_helper_0_0(do_float_add_ps);
6120
        gen_store_fpr32(fpu32_T[2], fd);
6121
        gen_store_fpr32h(fpu32h_T[2], fd);
6122
        opn = "add.ps";
6123
        break;
6124
    case FOP(1, 22):
6125
        check_cp1_64bitmode(ctx);
6126
        gen_load_fpr32(fpu32_T[0], fs);
6127
        gen_load_fpr32h(fpu32h_T[0], fs);
6128
        gen_load_fpr32(fpu32_T[1], ft);
6129
        gen_load_fpr32h(fpu32h_T[1], ft);
6130
        tcg_gen_helper_0_0(do_float_sub_ps);
6131
        gen_store_fpr32(fpu32_T[2], fd);
6132
        gen_store_fpr32h(fpu32h_T[2], fd);
6133
        opn = "sub.ps";
6134
        break;
6135
    case FOP(2, 22):
6136
        check_cp1_64bitmode(ctx);
6137
        gen_load_fpr32(fpu32_T[0], fs);
6138
        gen_load_fpr32h(fpu32h_T[0], fs);
6139
        gen_load_fpr32(fpu32_T[1], ft);
6140
        gen_load_fpr32h(fpu32h_T[1], ft);
6141
        tcg_gen_helper_0_0(do_float_mul_ps);
6142
        gen_store_fpr32(fpu32_T[2], fd);
6143
        gen_store_fpr32h(fpu32h_T[2], fd);
6144
        opn = "mul.ps";
6145
        break;
6146
    case FOP(5, 22):
6147
        check_cp1_64bitmode(ctx);
6148
        gen_load_fpr32(fpu32_T[0], fs);
6149
        gen_load_fpr32h(fpu32h_T[0], fs);
6150
        gen_op_float_abs_ps();
6151
        gen_store_fpr32(fpu32_T[2], fd);
6152
        gen_store_fpr32h(fpu32h_T[2], fd);
6153
        opn = "abs.ps";
6154
        break;
6155
    case FOP(6, 22):
6156
        check_cp1_64bitmode(ctx);
6157
        gen_load_fpr32(fpu32_T[0], fs);
6158
        gen_load_fpr32h(fpu32h_T[0], fs);
6159
        gen_op_float_mov_ps();
6160
        gen_store_fpr32(fpu32_T[2], fd);
6161
        gen_store_fpr32h(fpu32h_T[2], fd);
6162
        opn = "mov.ps";
6163
        break;
6164
    case FOP(7, 22):
6165
        check_cp1_64bitmode(ctx);
6166
        gen_load_fpr32(fpu32_T[0], fs);
6167
        gen_load_fpr32h(fpu32h_T[0], fs);
6168
        gen_op_float_chs_ps();
6169
        gen_store_fpr32(fpu32_T[2], fd);
6170
        gen_store_fpr32h(fpu32h_T[2], fd);
6171
        opn = "neg.ps";
6172
        break;
6173
    case FOP(17, 22):
6174
        check_cp1_64bitmode(ctx);
6175
        gen_load_gpr(cpu_T[0], ft);
6176
        gen_load_fpr32(fpu32_T[0], fs);
6177
        gen_load_fpr32h(fpu32h_T[0], fs);
6178
        gen_load_fpr32(fpu32_T[2], fd);
6179
        gen_load_fpr32h(fpu32h_T[2], fd);
6180
        if (ft & 0x1)
6181
            gen_op_float_movt_ps ((ft >> 2) & 0x7);
6182
        else
6183
            gen_op_float_movf_ps ((ft >> 2) & 0x7);
6184
        gen_store_fpr32(fpu32_T[2], fd);
6185
        gen_store_fpr32h(fpu32h_T[2], fd);
6186
        opn = "movcf.ps";
6187
        break;
6188
    case FOP(18, 22):
6189
        check_cp1_64bitmode(ctx);
6190
        gen_load_gpr(cpu_T[0], ft);
6191
        gen_load_fpr32(fpu32_T[0], fs);
6192
        gen_load_fpr32h(fpu32h_T[0], fs);
6193
        gen_load_fpr32(fpu32_T[2], fd);
6194
        gen_load_fpr32h(fpu32h_T[2], fd);
6195
        gen_op_float_movz_ps();
6196
        gen_store_fpr32(fpu32_T[2], fd);
6197
        gen_store_fpr32h(fpu32h_T[2], fd);
6198
        opn = "movz.ps";
6199
        break;
6200
    case FOP(19, 22):
6201
        check_cp1_64bitmode(ctx);
6202
        gen_load_gpr(cpu_T[0], ft);
6203
        gen_load_fpr32(fpu32_T[0], fs);
6204
        gen_load_fpr32h(fpu32h_T[0], fs);
6205
        gen_load_fpr32(fpu32_T[2], fd);
6206
        gen_load_fpr32h(fpu32h_T[2], fd);
6207
        gen_op_float_movn_ps();
6208
        gen_store_fpr32(fpu32_T[2], fd);
6209
        gen_store_fpr32h(fpu32h_T[2], fd);
6210
        opn = "movn.ps";
6211
        break;
6212
    case FOP(24, 22):
6213
        check_cp1_64bitmode(ctx);
6214
        gen_load_fpr32(fpu32_T[0], ft);
6215
        gen_load_fpr32h(fpu32h_T[0], ft);
6216
        gen_load_fpr32(fpu32_T[1], fs);
6217
        gen_load_fpr32h(fpu32h_T[1], fs);
6218
        tcg_gen_helper_0_0(do_float_addr_ps);
6219
        gen_store_fpr32(fpu32_T[2], fd);
6220
        gen_store_fpr32h(fpu32h_T[2], fd);
6221
        opn = "addr.ps";
6222
        break;
6223
    case FOP(26, 22):
6224
        check_cp1_64bitmode(ctx);
6225
        gen_load_fpr32(fpu32_T[0], ft);
6226
        gen_load_fpr32h(fpu32h_T[0], ft);
6227
        gen_load_fpr32(fpu32_T[1], fs);
6228
        gen_load_fpr32h(fpu32h_T[1], fs);
6229
        tcg_gen_helper_0_0(do_float_mulr_ps);
6230
        gen_store_fpr32(fpu32_T[2], fd);
6231
        gen_store_fpr32h(fpu32h_T[2], fd);
6232
        opn = "mulr.ps";
6233
        break;
6234
    case FOP(28, 22):
6235
        check_cp1_64bitmode(ctx);
6236
        gen_load_fpr32(fpu32_T[0], fs);
6237
        gen_load_fpr32h(fpu32h_T[0], fs);
6238
        gen_load_fpr32(fpu32_T[2], fd);
6239
        gen_load_fpr32h(fpu32h_T[2], fd);
6240
        tcg_gen_helper_0_0(do_float_recip2_ps);
6241
        gen_store_fpr32(fpu32_T[2], fd);
6242
        gen_store_fpr32h(fpu32h_T[2], fd);
6243
        opn = "recip2.ps";
6244
        break;
6245
    case FOP(29, 22):
6246
        check_cp1_64bitmode(ctx);
6247
        gen_load_fpr32(fpu32_T[0], fs);
6248
        gen_load_fpr32h(fpu32h_T[0], fs);
6249
        tcg_gen_helper_0_0(do_float_recip1_ps);
6250
        gen_store_fpr32(fpu32_T[2], fd);
6251
        gen_store_fpr32h(fpu32h_T[2], fd);
6252
        opn = "recip1.ps";
6253
        break;
6254
    case FOP(30, 22):
6255
        check_cp1_64bitmode(ctx);
6256
        gen_load_fpr32(fpu32_T[0], fs);
6257
        gen_load_fpr32h(fpu32h_T[0], fs);
6258
        tcg_gen_helper_0_0(do_float_rsqrt1_ps);
6259
        gen_store_fpr32(fpu32_T[2], fd);
6260
        gen_store_fpr32h(fpu32h_T[2], fd);
6261
        opn = "rsqrt1.ps";
6262
        break;
6263
    case FOP(31, 22):
6264
        check_cp1_64bitmode(ctx);
6265
        gen_load_fpr32(fpu32_T[0], fs);
6266
        gen_load_fpr32h(fpu32h_T[0], fs);
6267
        gen_load_fpr32(fpu32_T[2], ft);
6268
        gen_load_fpr32h(fpu32h_T[2], ft);
6269
        tcg_gen_helper_0_0(do_float_rsqrt2_ps);
6270
        gen_store_fpr32(fpu32_T[2], fd);
6271
        gen_store_fpr32h(fpu32h_T[2], fd);
6272
        opn = "rsqrt2.ps";
6273
        break;
6274
    case FOP(32, 22):
6275
        check_cp1_64bitmode(ctx);
6276
        gen_load_fpr32h(fpu32h_T[0], fs);
6277
        tcg_gen_helper_0_0(do_float_cvts_pu);
6278
        gen_store_fpr32(fpu32_T[2], fd);
6279
        opn = "cvt.s.pu";
6280
        break;
6281
    case FOP(36, 22):
6282
        check_cp1_64bitmode(ctx);
6283
        gen_load_fpr32(fpu32_T[0], fs);
6284
        gen_load_fpr32h(fpu32h_T[0], fs);
6285
        tcg_gen_helper_0_0(do_float_cvtpw_ps);
6286
        gen_store_fpr32(fpu32_T[2], fd);
6287
        gen_store_fpr32h(fpu32h_T[2], fd);
6288
        opn = "cvt.pw.ps";
6289
        break;
6290
    case FOP(40, 22):
6291
        check_cp1_64bitmode(ctx);
6292
        gen_load_fpr32(fpu32_T[0], fs);
6293
        tcg_gen_helper_0_0(do_float_cvts_pl);
6294
        gen_store_fpr32(fpu32_T[2], fd);
6295
        opn = "cvt.s.pl";
6296
        break;
6297
    case FOP(44, 22):
6298
        check_cp1_64bitmode(ctx);
6299
        gen_load_fpr32(fpu32_T[0], fs);
6300
        gen_load_fpr32(fpu32_T[1], ft);
6301
        gen_op_float_pll_ps();
6302
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6303
        opn = "pll.ps";
6304
        break;
6305
    case FOP(45, 22):
6306
        check_cp1_64bitmode(ctx);
6307
        gen_load_fpr32(fpu32_T[0], fs);
6308
        gen_load_fpr32h(fpu32h_T[1], ft);
6309
        gen_op_float_plu_ps();
6310
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6311
        opn = "plu.ps";
6312
        break;
6313
    case FOP(46, 22):
6314
        check_cp1_64bitmode(ctx);
6315
        gen_load_fpr32h(fpu32h_T[0], fs);
6316
        gen_load_fpr32(fpu32_T[1], ft);
6317
        gen_op_float_pul_ps();
6318
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6319
        opn = "pul.ps";
6320
        break;
6321
    case FOP(47, 22):
6322
        check_cp1_64bitmode(ctx);
6323
        gen_load_fpr32h(fpu32h_T[0], fs);
6324
        gen_load_fpr32h(fpu32h_T[1], ft);
6325
        gen_op_float_puu_ps();
6326
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6327
        opn = "puu.ps";
6328
        break;
6329
    case FOP(48, 22):
6330
    case FOP(49, 22):
6331
    case FOP(50, 22):
6332
    case FOP(51, 22):
6333
    case FOP(52, 22):
6334
    case FOP(53, 22):
6335
    case FOP(54, 22):
6336
    case FOP(55, 22):
6337
    case FOP(56, 22):
6338
    case FOP(57, 22):
6339
    case FOP(58, 22):
6340
    case FOP(59, 22):
6341
    case FOP(60, 22):
6342
    case FOP(61, 22):
6343
    case FOP(62, 22):
6344
    case FOP(63, 22):
6345
        check_cp1_64bitmode(ctx);
6346
        gen_load_fpr32(fpu32_T[0], fs);
6347
        gen_load_fpr32h(fpu32h_T[0], fs);
6348
        gen_load_fpr32(fpu32_T[1], ft);
6349
        gen_load_fpr32h(fpu32h_T[1], ft);
6350
        if (ctx->opcode & (1 << 6)) {
6351
            gen_cmpabs_ps(func-48, cc);
6352
            opn = condnames_abs[func-48];
6353
        } else {
6354
            gen_cmp_ps(func-48, cc);
6355
            opn = condnames[func-48];
6356
        }
6357
        break;
6358
    default:
6359
        MIPS_INVAL(opn);
6360
        generate_exception (ctx, EXCP_RI);
6361
        return;
6362
    }
6363
    switch (optype) {
6364
    case BINOP:
6365
        MIPS_DEBUG("%s %s, %s, %s", opn, fregnames[fd], fregnames[fs], fregnames[ft]);
6366
        break;
6367
    case CMPOP:
6368
        MIPS_DEBUG("%s %s,%s", opn, fregnames[fs], fregnames[ft]);
6369
        break;
6370
    default:
6371
        MIPS_DEBUG("%s %s,%s", opn, fregnames[fd], fregnames[fs]);
6372
        break;
6373
    }
6374
}
6375

    
6376
/* Coprocessor 3 (FPU) */
6377
static void gen_flt3_ldst (DisasContext *ctx, uint32_t opc,
6378
                           int fd, int fs, int base, int index)
6379
{
6380
    const char *opn = "extended float load/store";
6381
    int store = 0;
6382

    
6383
    if (base == 0) {
6384
        gen_load_gpr(cpu_T[0], index);
6385
    } else if (index == 0) {
6386
        gen_load_gpr(cpu_T[0], base);
6387
    } else {
6388
        gen_load_gpr(cpu_T[0], base);
6389
        gen_load_gpr(cpu_T[1], index);
6390
        gen_op_addr_add();
6391
    }
6392
    /* Don't do NOP if destination is zero: we must perform the actual
6393
       memory access. */
6394
    switch (opc) {
6395
    case OPC_LWXC1:
6396
        check_cop1x(ctx);
6397
        tcg_gen_qemu_ld32s(fpu32_T[0], cpu_T[0], ctx->mem_idx);
6398
        gen_store_fpr32(fpu32_T[0], fd);
6399
        opn = "lwxc1";
6400
        break;
6401
    case OPC_LDXC1:
6402
        check_cop1x(ctx);
6403
        check_cp1_registers(ctx, fd);
6404
        tcg_gen_qemu_ld64(fpu64_T[0], cpu_T[0], ctx->mem_idx);
6405
        gen_store_fpr64(ctx, fpu64_T[0], fd);
6406
        opn = "ldxc1";
6407
        break;
6408
    case OPC_LUXC1:
6409
        check_cp1_64bitmode(ctx);
6410
        op_ldst(luxc1);
6411
        gen_store_fpr64(ctx, fpu64_T[0], fd);
6412
        opn = "luxc1";
6413
        break;
6414
    case OPC_SWXC1:
6415
        check_cop1x(ctx);
6416
        gen_load_fpr32(fpu32_T[0], fs);
6417
        tcg_gen_qemu_st32(fpu32_T[0], cpu_T[0], ctx->mem_idx);
6418
        opn = "swxc1";
6419
        store = 1;
6420
        break;
6421
    case OPC_SDXC1:
6422
        check_cop1x(ctx);
6423
        check_cp1_registers(ctx, fs);
6424
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6425
        tcg_gen_qemu_st64(fpu64_T[0], cpu_T[0], ctx->mem_idx);
6426
        opn = "sdxc1";
6427
        store = 1;
6428
        break;
6429
    case OPC_SUXC1:
6430
        check_cp1_64bitmode(ctx);
6431
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6432
        op_ldst(suxc1);
6433
        opn = "suxc1";
6434
        store = 1;
6435
        break;
6436
    default:
6437
        MIPS_INVAL(opn);
6438
        generate_exception(ctx, EXCP_RI);
6439
        return;
6440
    }
6441
    MIPS_DEBUG("%s %s, %s(%s)", opn, fregnames[store ? fs : fd],
6442
               regnames[index], regnames[base]);
6443
}
6444

    
6445
static void gen_flt3_arith (DisasContext *ctx, uint32_t opc,
6446
                            int fd, int fr, int fs, int ft)
6447
{
6448
    const char *opn = "flt3_arith";
6449

    
6450
    switch (opc) {
6451
    case OPC_ALNV_PS:
6452
        check_cp1_64bitmode(ctx);
6453
        gen_load_gpr(cpu_T[0], fr);
6454
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6455
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6456
        gen_op_float_alnv_ps();
6457
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6458
        opn = "alnv.ps";
6459
        break;
6460
    case OPC_MADD_S:
6461
        check_cop1x(ctx);
6462
        gen_load_fpr32(fpu32_T[0], fs);
6463
        gen_load_fpr32(fpu32_T[1], ft);
6464
        gen_load_fpr32(fpu32_T[2], fr);
6465
        gen_op_float_muladd_s();
6466
        gen_store_fpr32(fpu32_T[2], fd);
6467
        opn = "madd.s";
6468
        break;
6469
    case OPC_MADD_D:
6470
        check_cop1x(ctx);
6471
        check_cp1_registers(ctx, fd | fs | ft | fr);
6472
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6473
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6474
        gen_load_fpr64(ctx, fpu64_T[2], fr);
6475
        gen_op_float_muladd_d();
6476
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6477
        opn = "madd.d";
6478
        break;
6479
    case OPC_MADD_PS:
6480
        check_cp1_64bitmode(ctx);
6481
        gen_load_fpr32(fpu32_T[0], fs);
6482
        gen_load_fpr32h(fpu32h_T[0], fs);
6483
        gen_load_fpr32(fpu32_T[1], ft);
6484
        gen_load_fpr32h(fpu32h_T[1], ft);
6485
        gen_load_fpr32(fpu32_T[2], fr);
6486
        gen_load_fpr32h(fpu32h_T[2], fr);
6487
        gen_op_float_muladd_ps();
6488
        gen_store_fpr32(fpu32_T[2], fd);
6489
        gen_store_fpr32h(fpu32h_T[2], fd);
6490
        opn = "madd.ps";
6491
        break;
6492
    case OPC_MSUB_S:
6493
        check_cop1x(ctx);
6494
        gen_load_fpr32(fpu32_T[0], fs);
6495
        gen_load_fpr32(fpu32_T[1], ft);
6496
        gen_load_fpr32(fpu32_T[2], fr);
6497
        gen_op_float_mulsub_s();
6498
        gen_store_fpr32(fpu32_T[2], fd);
6499
        opn = "msub.s";
6500
        break;
6501
    case OPC_MSUB_D:
6502
        check_cop1x(ctx);
6503
        check_cp1_registers(ctx, fd | fs | ft | fr);
6504
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6505
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6506
        gen_load_fpr64(ctx, fpu64_T[2], fr);
6507
        gen_op_float_mulsub_d();
6508
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6509
        opn = "msub.d";
6510
        break;
6511
    case OPC_MSUB_PS:
6512
        check_cp1_64bitmode(ctx);
6513
        gen_load_fpr32(fpu32_T[0], fs);
6514
        gen_load_fpr32h(fpu32h_T[0], fs);
6515
        gen_load_fpr32(fpu32_T[1], ft);
6516
        gen_load_fpr32h(fpu32h_T[1], ft);
6517
        gen_load_fpr32(fpu32_T[2], fr);
6518
        gen_load_fpr32h(fpu32h_T[2], fr);
6519
        gen_op_float_mulsub_ps();
6520
        gen_store_fpr32(fpu32_T[2], fd);
6521
        gen_store_fpr32h(fpu32h_T[2], fd);
6522
        opn = "msub.ps";
6523
        break;
6524
    case OPC_NMADD_S:
6525
        check_cop1x(ctx);
6526
        gen_load_fpr32(fpu32_T[0], fs);
6527
        gen_load_fpr32(fpu32_T[1], ft);
6528
        gen_load_fpr32(fpu32_T[2], fr);
6529
        gen_op_float_nmuladd_s();
6530
        gen_store_fpr32(fpu32_T[2], fd);
6531
        opn = "nmadd.s";
6532
        break;
6533
    case OPC_NMADD_D:
6534
        check_cop1x(ctx);
6535
        check_cp1_registers(ctx, fd | fs | ft | fr);
6536
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6537
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6538
        gen_load_fpr64(ctx, fpu64_T[2], fr);
6539
        gen_op_float_nmuladd_d();
6540
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6541
        opn = "nmadd.d";
6542
        break;
6543
    case OPC_NMADD_PS:
6544
        check_cp1_64bitmode(ctx);
6545
        gen_load_fpr32(fpu32_T[0], fs);
6546
        gen_load_fpr32h(fpu32h_T[0], fs);
6547
        gen_load_fpr32(fpu32_T[1], ft);
6548
        gen_load_fpr32h(fpu32h_T[1], ft);
6549
        gen_load_fpr32(fpu32_T[2], fr);
6550
        gen_load_fpr32h(fpu32h_T[2], fr);
6551
        gen_op_float_nmuladd_ps();
6552
        gen_store_fpr32(fpu32_T[2], fd);
6553
        gen_store_fpr32h(fpu32h_T[2], fd);
6554
        opn = "nmadd.ps";
6555
        break;
6556
    case OPC_NMSUB_S:
6557
        check_cop1x(ctx);
6558
        gen_load_fpr32(fpu32_T[0], fs);
6559
        gen_load_fpr32(fpu32_T[1], ft);
6560
        gen_load_fpr32(fpu32_T[2], fr);
6561
        gen_op_float_nmulsub_s();
6562
        gen_store_fpr32(fpu32_T[2], fd);
6563
        opn = "nmsub.s";
6564
        break;
6565
    case OPC_NMSUB_D:
6566
        check_cop1x(ctx);
6567
        check_cp1_registers(ctx, fd | fs | ft | fr);
6568
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6569
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6570
        gen_load_fpr64(ctx, fpu64_T[2], fr);
6571
        gen_op_float_nmulsub_d();
6572
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6573
        opn = "nmsub.d";
6574
        break;
6575
    case OPC_NMSUB_PS:
6576
        check_cp1_64bitmode(ctx);
6577
        gen_load_fpr32(fpu32_T[0], fs);
6578
        gen_load_fpr32h(fpu32h_T[0], fs);
6579
        gen_load_fpr32(fpu32_T[1], ft);
6580
        gen_load_fpr32h(fpu32h_T[1], ft);
6581
        gen_load_fpr32(fpu32_T[2], fr);
6582
        gen_load_fpr32h(fpu32h_T[2], fr);
6583
        gen_op_float_nmulsub_ps();
6584
        gen_store_fpr32(fpu32_T[2], fd);
6585
        gen_store_fpr32h(fpu32h_T[2], fd);
6586
        opn = "nmsub.ps";
6587
        break;
6588
    default:
6589
        MIPS_INVAL(opn);
6590
        generate_exception (ctx, EXCP_RI);
6591
        return;
6592
    }
6593
    MIPS_DEBUG("%s %s, %s, %s, %s", opn, fregnames[fd], fregnames[fr],
6594
               fregnames[fs], fregnames[ft]);
6595
}
6596

    
6597
/* ISA extensions (ASEs) */
6598
/* MIPS16 extension to MIPS32 */
6599
/* SmartMIPS extension to MIPS32 */
6600

    
6601
#if defined(TARGET_MIPS64)
6602

    
6603
/* MDMX extension to MIPS64 */
6604

    
6605
#endif
6606

    
6607
static void decode_opc (CPUState *env, DisasContext *ctx)
6608
{
6609
    int32_t offset;
6610
    int rs, rt, rd, sa;
6611
    uint32_t op, op1, op2;
6612
    int16_t imm;
6613

    
6614
    /* make sure instructions are on a word boundary */
6615
    if (ctx->pc & 0x3) {
6616
        env->CP0_BadVAddr = ctx->pc;
6617
        generate_exception(ctx, EXCP_AdEL);
6618
        return;
6619
    }
6620

    
6621
    /* Handle blikely not taken case */
6622
    if ((ctx->hflags & MIPS_HFLAG_BMASK) == MIPS_HFLAG_BL) {
6623
        TCGv r_tmp = tcg_temp_local_new(TCG_TYPE_TL);
6624
        int l1 = gen_new_label();
6625

    
6626
        MIPS_DEBUG("blikely condition (" TARGET_FMT_lx ")", ctx->pc + 4);
6627
        tcg_gen_ld_tl(r_tmp, cpu_env, offsetof(CPUState, bcond));
6628
        tcg_gen_brcondi_tl(TCG_COND_NE, r_tmp, 0, l1);
6629
        tcg_temp_free(r_tmp);
6630
        {
6631
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
6632

    
6633
            tcg_gen_movi_i32(r_tmp2, ctx->hflags & ~MIPS_HFLAG_BMASK);
6634
            tcg_gen_st_i32(r_tmp2, cpu_env, offsetof(CPUState, hflags));
6635
            tcg_temp_free(r_tmp2);
6636
        }
6637
        gen_goto_tb(ctx, 1, ctx->pc + 4);
6638
        gen_set_label(l1);
6639
    }
6640
    op = MASK_OP_MAJOR(ctx->opcode);
6641
    rs = (ctx->opcode >> 21) & 0x1f;
6642
    rt = (ctx->opcode >> 16) & 0x1f;
6643
    rd = (ctx->opcode >> 11) & 0x1f;
6644
    sa = (ctx->opcode >> 6) & 0x1f;
6645
    imm = (int16_t)ctx->opcode;
6646
    switch (op) {
6647
    case OPC_SPECIAL:
6648
        op1 = MASK_SPECIAL(ctx->opcode);
6649
        switch (op1) {
6650
        case OPC_SLL:          /* Arithmetic with immediate */
6651
        case OPC_SRL ... OPC_SRA:
6652
            gen_arith_imm(env, ctx, op1, rd, rt, sa);
6653
            break;
6654
        case OPC_MOVZ ... OPC_MOVN:
6655
            check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
6656
        case OPC_SLLV:         /* Arithmetic */
6657
        case OPC_SRLV ... OPC_SRAV:
6658
        case OPC_ADD ... OPC_NOR:
6659
        case OPC_SLT ... OPC_SLTU:
6660
            gen_arith(env, ctx, op1, rd, rs, rt);
6661
            break;
6662
        case OPC_MULT ... OPC_DIVU:
6663
            if (sa) {
6664
                check_insn(env, ctx, INSN_VR54XX);
6665
                op1 = MASK_MUL_VR54XX(ctx->opcode);
6666
                gen_mul_vr54xx(ctx, op1, rd, rs, rt);
6667
            } else
6668
                gen_muldiv(ctx, op1, rs, rt);
6669
            break;
6670
        case OPC_JR ... OPC_JALR:
6671
            gen_compute_branch(ctx, op1, rs, rd, sa);
6672
            return;
6673
        case OPC_TGE ... OPC_TEQ: /* Traps */
6674
        case OPC_TNE:
6675
            gen_trap(ctx, op1, rs, rt, -1);
6676
            break;
6677
        case OPC_MFHI:          /* Move from HI/LO */
6678
        case OPC_MFLO:
6679
            gen_HILO(ctx, op1, rd);
6680
            break;
6681
        case OPC_MTHI:
6682
        case OPC_MTLO:          /* Move to HI/LO */
6683
            gen_HILO(ctx, op1, rs);
6684
            break;
6685
        case OPC_PMON:          /* Pmon entry point, also R4010 selsl */
6686
#ifdef MIPS_STRICT_STANDARD
6687
            MIPS_INVAL("PMON / selsl");
6688
            generate_exception(ctx, EXCP_RI);
6689
#else
6690
            tcg_gen_helper_0_1i(do_pmon, sa);
6691
#endif
6692
            break;
6693
        case OPC_SYSCALL:
6694
            generate_exception(ctx, EXCP_SYSCALL);
6695
            break;
6696
        case OPC_BREAK:
6697
            generate_exception(ctx, EXCP_BREAK);
6698
            break;
6699
        case OPC_SPIM:
6700
#ifdef MIPS_STRICT_STANDARD
6701
            MIPS_INVAL("SPIM");
6702
            generate_exception(ctx, EXCP_RI);
6703
#else
6704
           /* Implemented as RI exception for now. */
6705
            MIPS_INVAL("spim (unofficial)");
6706
            generate_exception(ctx, EXCP_RI);
6707
#endif
6708
            break;
6709
        case OPC_SYNC:
6710
            /* Treat as NOP. */
6711
            break;
6712

    
6713
        case OPC_MOVCI:
6714
            check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
6715
            if (env->CP0_Config1 & (1 << CP0C1_FP)) {
6716
                save_cpu_state(ctx, 1);
6717
                check_cp1_enabled(ctx);
6718
                gen_movci(ctx, rd, rs, (ctx->opcode >> 18) & 0x7,
6719
                          (ctx->opcode >> 16) & 1);
6720
            } else {
6721
                generate_exception_err(ctx, EXCP_CpU, 1);
6722
            }
6723
            break;
6724

    
6725
#if defined(TARGET_MIPS64)
6726
       /* MIPS64 specific opcodes */
6727
        case OPC_DSLL:
6728
        case OPC_DSRL ... OPC_DSRA:
6729
        case OPC_DSLL32:
6730
        case OPC_DSRL32 ... OPC_DSRA32:
6731
            check_insn(env, ctx, ISA_MIPS3);
6732
            check_mips_64(ctx);
6733
            gen_arith_imm(env, ctx, op1, rd, rt, sa);
6734
            break;
6735
        case OPC_DSLLV:
6736
        case OPC_DSRLV ... OPC_DSRAV:
6737
        case OPC_DADD ... OPC_DSUBU:
6738
            check_insn(env, ctx, ISA_MIPS3);
6739
            check_mips_64(ctx);
6740
            gen_arith(env, ctx, op1, rd, rs, rt);
6741
            break;
6742
        case OPC_DMULT ... OPC_DDIVU:
6743
            check_insn(env, ctx, ISA_MIPS3);
6744
            check_mips_64(ctx);
6745
            gen_muldiv(ctx, op1, rs, rt);
6746
            break;
6747
#endif
6748
        default:            /* Invalid */
6749
            MIPS_INVAL("special");
6750
            generate_exception(ctx, EXCP_RI);
6751
            break;
6752
        }
6753
        break;
6754
    case OPC_SPECIAL2:
6755
        op1 = MASK_SPECIAL2(ctx->opcode);
6756
        switch (op1) {
6757
        case OPC_MADD ... OPC_MADDU: /* Multiply and add/sub */
6758
        case OPC_MSUB ... OPC_MSUBU:
6759
            check_insn(env, ctx, ISA_MIPS32);
6760
            gen_muldiv(ctx, op1, rs, rt);
6761
            break;
6762
        case OPC_MUL:
6763
            gen_arith(env, ctx, op1, rd, rs, rt);
6764
            break;
6765
        case OPC_CLZ ... OPC_CLO:
6766
            check_insn(env, ctx, ISA_MIPS32);
6767
            gen_cl(ctx, op1, rd, rs);
6768
            break;
6769
        case OPC_SDBBP:
6770
            /* XXX: not clear which exception should be raised
6771
             *      when in debug mode...
6772
             */
6773
            check_insn(env, ctx, ISA_MIPS32);
6774
            if (!(ctx->hflags & MIPS_HFLAG_DM)) {
6775
                generate_exception(ctx, EXCP_DBp);
6776
            } else {
6777
                generate_exception(ctx, EXCP_DBp);
6778
            }
6779
            /* Treat as NOP. */
6780
            break;
6781
#if defined(TARGET_MIPS64)
6782
        case OPC_DCLZ ... OPC_DCLO:
6783
            check_insn(env, ctx, ISA_MIPS64);
6784
            check_mips_64(ctx);
6785
            gen_cl(ctx, op1, rd, rs);
6786
            break;
6787
#endif
6788
        default:            /* Invalid */
6789
            MIPS_INVAL("special2");
6790
            generate_exception(ctx, EXCP_RI);
6791
            break;
6792
        }
6793
        break;
6794
    case OPC_SPECIAL3:
6795
         op1 = MASK_SPECIAL3(ctx->opcode);
6796
         switch (op1) {
6797
         case OPC_EXT:
6798
         case OPC_INS:
6799
             check_insn(env, ctx, ISA_MIPS32R2);
6800
             gen_bitops(ctx, op1, rt, rs, sa, rd);
6801
             break;
6802
         case OPC_BSHFL:
6803
             check_insn(env, ctx, ISA_MIPS32R2);
6804
             op2 = MASK_BSHFL(ctx->opcode);
6805
             switch (op2) {
6806
             case OPC_WSBH:
6807
                 gen_load_gpr(cpu_T[1], rt);
6808
                 gen_op_wsbh();
6809
                 break;
6810
             case OPC_SEB:
6811
                 gen_load_gpr(cpu_T[1], rt);
6812
                 tcg_gen_ext8s_tl(cpu_T[0], cpu_T[1]);
6813
                 break;
6814
             case OPC_SEH:
6815
                 gen_load_gpr(cpu_T[1], rt);
6816
                 tcg_gen_ext16s_tl(cpu_T[0], cpu_T[1]);
6817
                 break;
6818
             default:            /* Invalid */
6819
                 MIPS_INVAL("bshfl");
6820
                 generate_exception(ctx, EXCP_RI);
6821
                 break;
6822
            }
6823
            gen_store_gpr(cpu_T[0], rd);
6824
            break;
6825
        case OPC_RDHWR:
6826
            check_insn(env, ctx, ISA_MIPS32R2);
6827
            switch (rd) {
6828
            case 0:
6829
                save_cpu_state(ctx, 1);
6830
                gen_op_rdhwr_cpunum();
6831
                break;
6832
            case 1:
6833
                save_cpu_state(ctx, 1);
6834
                gen_op_rdhwr_synci_step();
6835
                break;
6836
            case 2:
6837
                save_cpu_state(ctx, 1);
6838
                gen_op_rdhwr_cc();
6839
                break;
6840
            case 3:
6841
                save_cpu_state(ctx, 1);
6842
                gen_op_rdhwr_ccres();
6843
                break;
6844
            case 29:
6845
#if defined (CONFIG_USER_ONLY)
6846
                tcg_gen_ld_tl(cpu_T[0], cpu_env, offsetof(CPUState, tls_value));
6847
                break;
6848
#endif
6849
            default:            /* Invalid */
6850
                MIPS_INVAL("rdhwr");
6851
                generate_exception(ctx, EXCP_RI);
6852
                break;
6853
            }
6854
            gen_store_gpr(cpu_T[0], rt);
6855
            break;
6856
        case OPC_FORK:
6857
            check_insn(env, ctx, ASE_MT);
6858
            gen_load_gpr(cpu_T[0], rt);
6859
            gen_load_gpr(cpu_T[1], rs);
6860
            tcg_gen_helper_0_0(do_fork);
6861
            break;
6862
        case OPC_YIELD:
6863
            check_insn(env, ctx, ASE_MT);
6864
            gen_load_gpr(cpu_T[0], rs);
6865
            tcg_gen_helper_0_0(do_yield);
6866
            gen_store_gpr(cpu_T[0], rd);
6867
            break;
6868
#if defined(TARGET_MIPS64)
6869
        case OPC_DEXTM ... OPC_DEXT:
6870
        case OPC_DINSM ... OPC_DINS:
6871
            check_insn(env, ctx, ISA_MIPS64R2);
6872
            check_mips_64(ctx);
6873
            gen_bitops(ctx, op1, rt, rs, sa, rd);
6874
            break;
6875
        case OPC_DBSHFL:
6876
            check_insn(env, ctx, ISA_MIPS64R2);
6877
            check_mips_64(ctx);
6878
            op2 = MASK_DBSHFL(ctx->opcode);
6879
            switch (op2) {
6880
            case OPC_DSBH:
6881
                gen_load_gpr(cpu_T[1], rt);
6882
                gen_op_dsbh();
6883
                break;
6884
            case OPC_DSHD:
6885
                gen_load_gpr(cpu_T[1], rt);
6886
                gen_op_dshd();
6887
                break;
6888
            default:            /* Invalid */
6889
                MIPS_INVAL("dbshfl");
6890
                generate_exception(ctx, EXCP_RI);
6891
                break;
6892
            }
6893
            gen_store_gpr(cpu_T[0], rd);
6894
            break;
6895
#endif
6896
        default:            /* Invalid */
6897
            MIPS_INVAL("special3");
6898
            generate_exception(ctx, EXCP_RI);
6899
            break;
6900
        }
6901
        break;
6902
    case OPC_REGIMM:
6903
        op1 = MASK_REGIMM(ctx->opcode);
6904
        switch (op1) {
6905
        case OPC_BLTZ ... OPC_BGEZL: /* REGIMM branches */
6906
        case OPC_BLTZAL ... OPC_BGEZALL:
6907
            gen_compute_branch(ctx, op1, rs, -1, imm << 2);
6908
            return;
6909
        case OPC_TGEI ... OPC_TEQI: /* REGIMM traps */
6910
        case OPC_TNEI:
6911
            gen_trap(ctx, op1, rs, -1, imm);
6912
            break;
6913
        case OPC_SYNCI:
6914
            check_insn(env, ctx, ISA_MIPS32R2);
6915
            /* Treat as NOP. */
6916
            break;
6917
        default:            /* Invalid */
6918
            MIPS_INVAL("regimm");
6919
            generate_exception(ctx, EXCP_RI);
6920
            break;
6921
        }
6922
        break;
6923
    case OPC_CP0:
6924
        check_cp0_enabled(ctx);
6925
        op1 = MASK_CP0(ctx->opcode);
6926
        switch (op1) {
6927
        case OPC_MFC0:
6928
        case OPC_MTC0:
6929
        case OPC_MFTR:
6930
        case OPC_MTTR:
6931
#if defined(TARGET_MIPS64)
6932
        case OPC_DMFC0:
6933
        case OPC_DMTC0:
6934
#endif
6935
#ifndef CONFIG_USER_ONLY
6936
            gen_cp0(env, ctx, op1, rt, rd);
6937
#endif
6938
            break;
6939
        case OPC_C0_FIRST ... OPC_C0_LAST:
6940
#ifndef CONFIG_USER_ONLY
6941
            gen_cp0(env, ctx, MASK_C0(ctx->opcode), rt, rd);
6942
#endif
6943
            break;
6944
        case OPC_MFMC0:
6945
            op2 = MASK_MFMC0(ctx->opcode);
6946
            switch (op2) {
6947
            case OPC_DMT:
6948
                check_insn(env, ctx, ASE_MT);
6949
                tcg_gen_helper_0_0(do_dmt);
6950
                break;
6951
            case OPC_EMT:
6952
                check_insn(env, ctx, ASE_MT);
6953
                tcg_gen_helper_0_0(do_emt);
6954
                break;
6955
            case OPC_DVPE:
6956
                check_insn(env, ctx, ASE_MT);
6957
                tcg_gen_helper_0_0(do_dvpe);
6958
                break;
6959
            case OPC_EVPE:
6960
                check_insn(env, ctx, ASE_MT);
6961
                tcg_gen_helper_0_0(do_evpe);
6962
                break;
6963
            case OPC_DI:
6964
                check_insn(env, ctx, ISA_MIPS32R2);
6965
                save_cpu_state(ctx, 1);
6966
                gen_op_di();
6967
                /* Stop translation as we may have switched the execution mode */
6968
                ctx->bstate = BS_STOP;
6969
                break;
6970
            case OPC_EI:
6971
                check_insn(env, ctx, ISA_MIPS32R2);
6972
                save_cpu_state(ctx, 1);
6973
                gen_op_ei();
6974
                /* Stop translation as we may have switched the execution mode */
6975
                ctx->bstate = BS_STOP;
6976
                break;
6977
            default:            /* Invalid */
6978
                MIPS_INVAL("mfmc0");
6979
                generate_exception(ctx, EXCP_RI);
6980
                break;
6981
            }
6982
            gen_store_gpr(cpu_T[0], rt);
6983
            break;
6984
        case OPC_RDPGPR:
6985
            check_insn(env, ctx, ISA_MIPS32R2);
6986
            gen_load_srsgpr(cpu_T[0], rt);
6987
            gen_store_gpr(cpu_T[0], rd);
6988
            break;
6989
        case OPC_WRPGPR:
6990
            check_insn(env, ctx, ISA_MIPS32R2);
6991
            gen_load_gpr(cpu_T[0], rt);
6992
            gen_store_srsgpr(cpu_T[0], rd);
6993
            break;
6994
        default:
6995
            MIPS_INVAL("cp0");
6996
            generate_exception(ctx, EXCP_RI);
6997
            break;
6998
        }
6999
        break;
7000
    case OPC_ADDI ... OPC_LUI: /* Arithmetic with immediate opcode */
7001
         gen_arith_imm(env, ctx, op, rt, rs, imm);
7002
         break;
7003
    case OPC_J ... OPC_JAL: /* Jump */
7004
         offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
7005
         gen_compute_branch(ctx, op, rs, rt, offset);
7006
         return;
7007
    case OPC_BEQ ... OPC_BGTZ: /* Branch */
7008
    case OPC_BEQL ... OPC_BGTZL:
7009
         gen_compute_branch(ctx, op, rs, rt, imm << 2);
7010
         return;
7011
    case OPC_LB ... OPC_LWR: /* Load and stores */
7012
    case OPC_SB ... OPC_SW:
7013
    case OPC_SWR:
7014
    case OPC_LL:
7015
    case OPC_SC:
7016
         gen_ldst(ctx, op, rt, rs, imm);
7017
         break;
7018
    case OPC_CACHE:
7019
        check_insn(env, ctx, ISA_MIPS3 | ISA_MIPS32);
7020
        /* Treat as NOP. */
7021
        break;
7022
    case OPC_PREF:
7023
        check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
7024
        /* Treat as NOP. */
7025
        break;
7026

    
7027
    /* Floating point (COP1). */
7028
    case OPC_LWC1:
7029
    case OPC_LDC1:
7030
    case OPC_SWC1:
7031
    case OPC_SDC1:
7032
        if (env->CP0_Config1 & (1 << CP0C1_FP)) {
7033
            save_cpu_state(ctx, 1);
7034
            check_cp1_enabled(ctx);
7035
            gen_flt_ldst(ctx, op, rt, rs, imm);
7036
        } else {
7037
            generate_exception_err(ctx, EXCP_CpU, 1);
7038
        }
7039
        break;
7040

    
7041
    case OPC_CP1:
7042
        if (env->CP0_Config1 & (1 << CP0C1_FP)) {
7043
            save_cpu_state(ctx, 1);
7044
            check_cp1_enabled(ctx);
7045
            op1 = MASK_CP1(ctx->opcode);
7046
            switch (op1) {
7047
            case OPC_MFHC1:
7048
            case OPC_MTHC1:
7049
                check_insn(env, ctx, ISA_MIPS32R2);
7050
            case OPC_MFC1:
7051
            case OPC_CFC1:
7052
            case OPC_MTC1:
7053
            case OPC_CTC1:
7054
                gen_cp1(ctx, op1, rt, rd);
7055
                break;
7056
#if defined(TARGET_MIPS64)
7057
            case OPC_DMFC1:
7058
            case OPC_DMTC1:
7059
                check_insn(env, ctx, ISA_MIPS3);
7060
                gen_cp1(ctx, op1, rt, rd);
7061
                break;
7062
#endif
7063
            case OPC_BC1ANY2:
7064
            case OPC_BC1ANY4:
7065
                check_cop1x(ctx);
7066
                check_insn(env, ctx, ASE_MIPS3D);
7067
                /* fall through */
7068
            case OPC_BC1:
7069
                gen_compute_branch1(env, ctx, MASK_BC1(ctx->opcode),
7070
                                    (rt >> 2) & 0x7, imm << 2);
7071
                return;
7072
            case OPC_S_FMT:
7073
            case OPC_D_FMT:
7074
            case OPC_W_FMT:
7075
            case OPC_L_FMT:
7076
            case OPC_PS_FMT:
7077
                gen_farith(ctx, MASK_CP1_FUNC(ctx->opcode), rt, rd, sa,
7078
                           (imm >> 8) & 0x7);
7079
                break;
7080
            default:
7081
                MIPS_INVAL("cp1");
7082
                generate_exception (ctx, EXCP_RI);
7083
                break;
7084
            }
7085
        } else {
7086
            generate_exception_err(ctx, EXCP_CpU, 1);
7087
        }
7088
        break;
7089

    
7090
    /* COP2.  */
7091
    case OPC_LWC2:
7092
    case OPC_LDC2:
7093
    case OPC_SWC2:
7094
    case OPC_SDC2:
7095
    case OPC_CP2:
7096
        /* COP2: Not implemented. */
7097
        generate_exception_err(ctx, EXCP_CpU, 2);
7098
        break;
7099

    
7100
    case OPC_CP3:
7101
        if (env->CP0_Config1 & (1 << CP0C1_FP)) {
7102
            save_cpu_state(ctx, 1);
7103
            check_cp1_enabled(ctx);
7104
            op1 = MASK_CP3(ctx->opcode);
7105
            switch (op1) {
7106
            case OPC_LWXC1:
7107
            case OPC_LDXC1:
7108
            case OPC_LUXC1:
7109
            case OPC_SWXC1:
7110
            case OPC_SDXC1:
7111
            case OPC_SUXC1:
7112
                gen_flt3_ldst(ctx, op1, sa, rd, rs, rt);
7113
                break;
7114
            case OPC_PREFX:
7115
                /* Treat as NOP. */
7116
                break;
7117
            case OPC_ALNV_PS:
7118
            case OPC_MADD_S:
7119
            case OPC_MADD_D:
7120
            case OPC_MADD_PS:
7121
            case OPC_MSUB_S:
7122
            case OPC_MSUB_D:
7123
            case OPC_MSUB_PS:
7124
            case OPC_NMADD_S:
7125
            case OPC_NMADD_D:
7126
            case OPC_NMADD_PS:
7127
            case OPC_NMSUB_S:
7128
            case OPC_NMSUB_D:
7129
            case OPC_NMSUB_PS:
7130
                gen_flt3_arith(ctx, op1, sa, rs, rd, rt);
7131
                break;
7132
            default:
7133
                MIPS_INVAL("cp3");
7134
                generate_exception (ctx, EXCP_RI);
7135
                break;
7136
            }
7137
        } else {
7138
            generate_exception_err(ctx, EXCP_CpU, 1);
7139
        }
7140
        break;
7141

    
7142
#if defined(TARGET_MIPS64)
7143
    /* MIPS64 opcodes */
7144
    case OPC_LWU:
7145
    case OPC_LDL ... OPC_LDR:
7146
    case OPC_SDL ... OPC_SDR:
7147
    case OPC_LLD:
7148
    case OPC_LD:
7149
    case OPC_SCD:
7150
    case OPC_SD:
7151
        check_insn(env, ctx, ISA_MIPS3);
7152
        check_mips_64(ctx);
7153
        gen_ldst(ctx, op, rt, rs, imm);
7154
        break;
7155
    case OPC_DADDI ... OPC_DADDIU:
7156
        check_insn(env, ctx, ISA_MIPS3);
7157
        check_mips_64(ctx);
7158
        gen_arith_imm(env, ctx, op, rt, rs, imm);
7159
        break;
7160
#endif
7161
    case OPC_JALX:
7162
        check_insn(env, ctx, ASE_MIPS16);
7163
        /* MIPS16: Not implemented. */
7164
    case OPC_MDMX:
7165
        check_insn(env, ctx, ASE_MDMX);
7166
        /* MDMX: Not implemented. */
7167
    default:            /* Invalid */
7168
        MIPS_INVAL("major opcode");
7169
        generate_exception(ctx, EXCP_RI);
7170
        break;
7171
    }
7172
    if (ctx->hflags & MIPS_HFLAG_BMASK) {
7173
        int hflags = ctx->hflags & MIPS_HFLAG_BMASK;
7174
        /* Branches completion */
7175
        ctx->hflags &= ~MIPS_HFLAG_BMASK;
7176
        ctx->bstate = BS_BRANCH;
7177
        save_cpu_state(ctx, 0);
7178
        switch (hflags) {
7179
        case MIPS_HFLAG_B:
7180
            /* unconditional branch */
7181
            MIPS_DEBUG("unconditional branch");
7182
            gen_goto_tb(ctx, 0, ctx->btarget);
7183
            break;
7184
        case MIPS_HFLAG_BL:
7185
            /* blikely taken case */
7186
            MIPS_DEBUG("blikely branch taken");
7187
            gen_goto_tb(ctx, 0, ctx->btarget);
7188
            break;
7189
        case MIPS_HFLAG_BC:
7190
            /* Conditional branch */
7191
            MIPS_DEBUG("conditional branch");
7192
            {
7193
                TCGv r_tmp = tcg_temp_local_new(TCG_TYPE_TL);
7194
                int l1 = gen_new_label();
7195

    
7196
                tcg_gen_ld_tl(r_tmp, cpu_env, offsetof(CPUState, bcond));
7197
                tcg_gen_brcondi_tl(TCG_COND_NE, r_tmp, 0, l1);
7198
                tcg_temp_free(r_tmp);
7199
                gen_goto_tb(ctx, 1, ctx->pc + 4);
7200
                gen_set_label(l1);
7201
                gen_goto_tb(ctx, 0, ctx->btarget);
7202
            }
7203
            break;
7204
        case MIPS_HFLAG_BR:
7205
            /* unconditional branch to register */
7206
            MIPS_DEBUG("branch to register");
7207
            gen_breg_pc();
7208
            tcg_gen_exit_tb(0);
7209
            break;
7210
        default:
7211
            MIPS_DEBUG("unknown branch");
7212
            break;
7213
        }
7214
    }
7215
}
7216

    
7217
static always_inline int
7218
gen_intermediate_code_internal (CPUState *env, TranslationBlock *tb,
7219
                                int search_pc)
7220
{
7221
    DisasContext ctx;
7222
    target_ulong pc_start;
7223
    uint16_t *gen_opc_end;
7224
    int j, lj = -1;
7225

    
7226
    if (search_pc && loglevel)
7227
        fprintf (logfile, "search pc %d\n", search_pc);
7228

    
7229
    pc_start = tb->pc;
7230
    /* Leave some spare opc slots for branch handling. */
7231
    gen_opc_end = gen_opc_buf + OPC_MAX_SIZE - 16;
7232
    ctx.pc = pc_start;
7233
    ctx.saved_pc = -1;
7234
    ctx.tb = tb;
7235
    ctx.bstate = BS_NONE;
7236
    /* Restore delay slot state from the tb context.  */
7237
    ctx.hflags = (uint32_t)tb->flags; /* FIXME: maybe use 64 bits here? */
7238
    restore_cpu_state(env, &ctx);
7239
#if defined(CONFIG_USER_ONLY)
7240
    ctx.mem_idx = MIPS_HFLAG_UM;
7241
#else
7242
    ctx.mem_idx = ctx.hflags & MIPS_HFLAG_KSU;
7243
#endif
7244
#ifdef DEBUG_DISAS
7245
    if (loglevel & CPU_LOG_TB_CPU) {
7246
        fprintf(logfile, "------------------------------------------------\n");
7247
        /* FIXME: This may print out stale hflags from env... */
7248
        cpu_dump_state(env, logfile, fprintf, 0);
7249
    }
7250
#endif
7251
#ifdef MIPS_DEBUG_DISAS
7252
    if (loglevel & CPU_LOG_TB_IN_ASM)
7253
        fprintf(logfile, "\ntb %p idx %d hflags %04x\n",
7254
                tb, ctx.mem_idx, ctx.hflags);
7255
#endif
7256
    while (ctx.bstate == BS_NONE) {
7257
        if (env->nb_breakpoints > 0) {
7258
            for(j = 0; j < env->nb_breakpoints; j++) {
7259
                if (env->breakpoints[j] == ctx.pc) {
7260
                    save_cpu_state(&ctx, 1);
7261
                    ctx.bstate = BS_BRANCH;
7262
                    tcg_gen_helper_0_1i(do_raise_exception, EXCP_DEBUG);
7263
                    /* Include the breakpoint location or the tb won't
7264
                     * be flushed when it must be.  */
7265
                    ctx.pc += 4;
7266
                    goto done_generating;
7267
                }
7268
            }
7269
        }
7270

    
7271
        if (search_pc) {
7272
            j = gen_opc_ptr - gen_opc_buf;
7273
            if (lj < j) {
7274
                lj++;
7275
                while (lj < j)
7276
                    gen_opc_instr_start[lj++] = 0;
7277
            }
7278
            gen_opc_pc[lj] = ctx.pc;
7279
            gen_opc_hflags[lj] = ctx.hflags & MIPS_HFLAG_BMASK;
7280
            gen_opc_instr_start[lj] = 1;
7281
        }
7282
        ctx.opcode = ldl_code(ctx.pc);
7283
        decode_opc(env, &ctx);
7284
        ctx.pc += 4;
7285

    
7286
        if (env->singlestep_enabled)
7287
            break;
7288

    
7289
        if ((ctx.pc & (TARGET_PAGE_SIZE - 1)) == 0)
7290
            break;
7291

    
7292
        if (gen_opc_ptr >= gen_opc_end)
7293
            break;
7294

    
7295
        if (gen_opc_ptr >= gen_opc_end)
7296
            break;
7297

    
7298
#if defined (MIPS_SINGLE_STEP)
7299
        break;
7300
#endif
7301
    }
7302
    if (env->singlestep_enabled) {
7303
        save_cpu_state(&ctx, ctx.bstate == BS_NONE);
7304
        tcg_gen_helper_0_1i(do_raise_exception, EXCP_DEBUG);
7305
    } else {
7306
        switch (ctx.bstate) {
7307
        case BS_STOP:
7308
            tcg_gen_helper_0_0(do_interrupt_restart);
7309
            gen_goto_tb(&ctx, 0, ctx.pc);
7310
            break;
7311
        case BS_NONE:
7312
            save_cpu_state(&ctx, 0);
7313
            gen_goto_tb(&ctx, 0, ctx.pc);
7314
            break;
7315
        case BS_EXCP:
7316
            tcg_gen_helper_0_0(do_interrupt_restart);
7317
            tcg_gen_exit_tb(0);
7318
            break;
7319
        case BS_BRANCH:
7320
        default:
7321
            break;
7322
        }
7323
    }
7324
done_generating:
7325
    *gen_opc_ptr = INDEX_op_end;
7326
    if (search_pc) {
7327
        j = gen_opc_ptr - gen_opc_buf;
7328
        lj++;
7329
        while (lj <= j)
7330
            gen_opc_instr_start[lj++] = 0;
7331
    } else {
7332
        tb->size = ctx.pc - pc_start;
7333
    }
7334
#ifdef DEBUG_DISAS
7335
#if defined MIPS_DEBUG_DISAS
7336
    if (loglevel & CPU_LOG_TB_IN_ASM)
7337
        fprintf(logfile, "\n");
7338
#endif
7339
    if (loglevel & CPU_LOG_TB_IN_ASM) {
7340
        fprintf(logfile, "IN: %s\n", lookup_symbol(pc_start));
7341
        target_disas(logfile, pc_start, ctx.pc - pc_start, 0);
7342
        fprintf(logfile, "\n");
7343
    }
7344
    if (loglevel & CPU_LOG_TB_CPU) {
7345
        fprintf(logfile, "---------------- %d %08x\n", ctx.bstate, ctx.hflags);
7346
    }
7347
#endif
7348

    
7349
    return 0;
7350
}
7351

    
7352
int gen_intermediate_code (CPUState *env, struct TranslationBlock *tb)
7353
{
7354
    return gen_intermediate_code_internal(env, tb, 0);
7355
}
7356

    
7357
int gen_intermediate_code_pc (CPUState *env, struct TranslationBlock *tb)
7358
{
7359
    return gen_intermediate_code_internal(env, tb, 1);
7360
}
7361

    
7362
void fpu_dump_state(CPUState *env, FILE *f,
7363
                    int (*fpu_fprintf)(FILE *f, const char *fmt, ...),
7364
                    int flags)
7365
{
7366
    int i;
7367
    int is_fpu64 = !!(env->hflags & MIPS_HFLAG_F64);
7368

    
7369
#define printfpr(fp)                                                        \
7370
    do {                                                                    \
7371
        if (is_fpu64)                                                       \
7372
            fpu_fprintf(f, "w:%08x d:%016lx fd:%13g fs:%13g psu: %13g\n",   \
7373
                        (fp)->w[FP_ENDIAN_IDX], (fp)->d, (fp)->fd,          \
7374
                        (fp)->fs[FP_ENDIAN_IDX], (fp)->fs[!FP_ENDIAN_IDX]); \
7375
        else {                                                              \
7376
            fpr_t tmp;                                                      \
7377
            tmp.w[FP_ENDIAN_IDX] = (fp)->w[FP_ENDIAN_IDX];                  \
7378
            tmp.w[!FP_ENDIAN_IDX] = ((fp) + 1)->w[FP_ENDIAN_IDX];           \
7379
            fpu_fprintf(f, "w:%08x d:%016lx fd:%13g fs:%13g psu:%13g\n",    \
7380
                        tmp.w[FP_ENDIAN_IDX], tmp.d, tmp.fd,                \
7381
                        tmp.fs[FP_ENDIAN_IDX], tmp.fs[!FP_ENDIAN_IDX]);     \
7382
        }                                                                   \
7383
    } while(0)
7384

    
7385

    
7386
    fpu_fprintf(f, "CP1 FCR0 0x%08x  FCR31 0x%08x  SR.FR %d  fp_status 0x%08x(0x%02x)\n",
7387
                env->fpu->fcr0, env->fpu->fcr31, is_fpu64, env->fpu->fp_status,
7388
                get_float_exception_flags(&env->fpu->fp_status));
7389
    fpu_fprintf(f, "FT0: "); printfpr(&env->ft0);
7390
    fpu_fprintf(f, "FT1: "); printfpr(&env->ft1);
7391
    fpu_fprintf(f, "FT2: "); printfpr(&env->ft2);
7392
    for (i = 0; i < 32; (is_fpu64) ? i++ : (i += 2)) {
7393
        fpu_fprintf(f, "%3s: ", fregnames[i]);
7394
        printfpr(&env->fpu->fpr[i]);
7395
    }
7396

    
7397
#undef printfpr
7398
}
7399

    
7400
void dump_fpu (CPUState *env)
7401
{
7402
    if (loglevel) {
7403
        fprintf(logfile,
7404
                "pc=0x" TARGET_FMT_lx " HI=0x" TARGET_FMT_lx
7405
                " LO=0x" TARGET_FMT_lx " ds %04x " TARGET_FMT_lx
7406
                " %04x\n",
7407
                env->PC[env->current_tc], env->HI[env->current_tc][0],
7408
                env->LO[env->current_tc][0], env->hflags, env->btarget,
7409
                env->bcond);
7410
       fpu_dump_state(env, logfile, fprintf, 0);
7411
    }
7412
}
7413

    
7414
#if defined(TARGET_MIPS64) && defined(MIPS_DEBUG_SIGN_EXTENSIONS)
7415
/* Debug help: The architecture requires 32bit code to maintain proper
7416
   sign-extened values on 64bit machines.  */
7417

    
7418
#define SIGN_EXT_P(val) ((((val) & ~0x7fffffff) == 0) || (((val) & ~0x7fffffff) == ~0x7fffffff))
7419

    
7420
void cpu_mips_check_sign_extensions (CPUState *env, FILE *f,
7421
                     int (*cpu_fprintf)(FILE *f, const char *fmt, ...),
7422
                     int flags)
7423
{
7424
    int i;
7425

    
7426
    if (!SIGN_EXT_P(env->PC[env->current_tc]))
7427
        cpu_fprintf(f, "BROKEN: pc=0x" TARGET_FMT_lx "\n", env->PC[env->current_tc]);
7428
    if (!SIGN_EXT_P(env->HI[env->current_tc][0]))
7429
        cpu_fprintf(f, "BROKEN: HI=0x" TARGET_FMT_lx "\n", env->HI[env->current_tc][0]);
7430
    if (!SIGN_EXT_P(env->LO[env->current_tc][0]))
7431
        cpu_fprintf(f, "BROKEN: LO=0x" TARGET_FMT_lx "\n", env->LO[env->current_tc][0]);
7432
    if (!SIGN_EXT_P(env->btarget))
7433
        cpu_fprintf(f, "BROKEN: btarget=0x" TARGET_FMT_lx "\n", env->btarget);
7434

    
7435
    for (i = 0; i < 32; i++) {
7436
        if (!SIGN_EXT_P(env->gpr[env->current_tc][i]))
7437
            cpu_fprintf(f, "BROKEN: %s=0x" TARGET_FMT_lx "\n", regnames[i], env->gpr[env->current_tc][i]);
7438
    }
7439

    
7440
    if (!SIGN_EXT_P(env->CP0_EPC))
7441
        cpu_fprintf(f, "BROKEN: EPC=0x" TARGET_FMT_lx "\n", env->CP0_EPC);
7442
    if (!SIGN_EXT_P(env->CP0_LLAddr))
7443
        cpu_fprintf(f, "BROKEN: LLAddr=0x" TARGET_FMT_lx "\n", env->CP0_LLAddr);
7444
}
7445
#endif
7446

    
7447
void cpu_dump_state (CPUState *env, FILE *f,
7448
                     int (*cpu_fprintf)(FILE *f, const char *fmt, ...),
7449
                     int flags)
7450
{
7451
    int i;
7452

    
7453
    cpu_fprintf(f, "pc=0x" TARGET_FMT_lx " HI=0x" TARGET_FMT_lx " LO=0x" TARGET_FMT_lx " ds %04x " TARGET_FMT_lx " %d\n",
7454
                env->PC[env->current_tc], env->HI[env->current_tc], env->LO[env->current_tc], env->hflags, env->btarget, env->bcond);
7455
    for (i = 0; i < 32; i++) {
7456
        if ((i & 3) == 0)
7457
            cpu_fprintf(f, "GPR%02d:", i);
7458
        cpu_fprintf(f, " %s " TARGET_FMT_lx, regnames[i], env->gpr[env->current_tc][i]);
7459
        if ((i & 3) == 3)
7460
            cpu_fprintf(f, "\n");
7461
    }
7462

    
7463
    cpu_fprintf(f, "CP0 Status  0x%08x Cause   0x%08x EPC    0x" TARGET_FMT_lx "\n",
7464
                env->CP0_Status, env->CP0_Cause, env->CP0_EPC);
7465
    cpu_fprintf(f, "    Config0 0x%08x Config1 0x%08x LLAddr 0x" TARGET_FMT_lx "\n",
7466
                env->CP0_Config0, env->CP0_Config1, env->CP0_LLAddr);
7467
    if (env->hflags & MIPS_HFLAG_FPU)
7468
        fpu_dump_state(env, f, cpu_fprintf, flags);
7469
#if defined(TARGET_MIPS64) && defined(MIPS_DEBUG_SIGN_EXTENSIONS)
7470
    cpu_mips_check_sign_extensions(env, f, cpu_fprintf, flags);
7471
#endif
7472
}
7473

    
7474
static void mips_tcg_init(void)
7475
{
7476
    static int inited;
7477

    
7478
    /* Initialize various static tables. */
7479
    if (inited)
7480
        return;
7481

    
7482
    cpu_env = tcg_global_reg_new(TCG_TYPE_PTR, TCG_AREG0, "env");
7483
    current_tc_gprs = tcg_global_mem_new(TCG_TYPE_PTR,
7484
                                         TCG_AREG0,
7485
                                         offsetof(CPUState, current_tc_gprs),
7486
                                         "current_tc_gprs");
7487
    current_tc_hi = tcg_global_mem_new(TCG_TYPE_PTR,
7488
                                       TCG_AREG0,
7489
                                       offsetof(CPUState, current_tc_hi),
7490
                                       "current_tc_hi");
7491
    current_fpu = tcg_global_mem_new(TCG_TYPE_PTR,
7492
                                     TCG_AREG0,
7493
                                     offsetof(CPUState, fpu),
7494
                                     "current_fpu");
7495
#if TARGET_LONG_BITS > HOST_LONG_BITS
7496
    cpu_T[0] = tcg_global_mem_new(TCG_TYPE_TL,
7497
                                  TCG_AREG0, offsetof(CPUState, t0), "T0");
7498
    cpu_T[1] = tcg_global_mem_new(TCG_TYPE_TL,
7499
                                  TCG_AREG0, offsetof(CPUState, t1), "T1");
7500
#else
7501
    cpu_T[0] = tcg_global_reg_new(TCG_TYPE_TL, TCG_AREG1, "T0");
7502
    cpu_T[1] = tcg_global_reg_new(TCG_TYPE_TL, TCG_AREG2, "T1");
7503
#endif
7504

    
7505
    /* register helpers */
7506
#undef DEF_HELPER
7507
#define DEF_HELPER(ret, name, params) tcg_register_helper(name, #name);
7508
#include "helper.h"
7509

    
7510
    fpu32_T[0] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft0.w[FP_ENDIAN_IDX]), "WT0");
7511
    fpu32_T[1] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft1.w[FP_ENDIAN_IDX]), "WT1");
7512
    fpu32_T[2] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft2.w[FP_ENDIAN_IDX]), "WT2");
7513
    fpu64_T[0] = tcg_global_mem_new(TCG_TYPE_I64, TCG_AREG0, offsetof(CPUState, ft0.d), "DT0");
7514
    fpu64_T[1] = tcg_global_mem_new(TCG_TYPE_I64, TCG_AREG0, offsetof(CPUState, ft1.d), "DT1");
7515
    fpu64_T[2] = tcg_global_mem_new(TCG_TYPE_I64, TCG_AREG0, offsetof(CPUState, ft2.d), "DT2");
7516
    fpu32h_T[0] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft0.w[!FP_ENDIAN_IDX]), "WTH0");
7517
    fpu32h_T[1] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft1.w[!FP_ENDIAN_IDX]), "WTH1");
7518
    fpu32h_T[2] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft2.w[!FP_ENDIAN_IDX]), "WTH2");
7519

    
7520
    inited = 1;
7521
}
7522

    
7523
#include "translate_init.c"
7524

    
7525
CPUMIPSState *cpu_mips_init (const char *cpu_model)
7526
{
7527
    CPUMIPSState *env;
7528
    const mips_def_t *def;
7529

    
7530
    def = cpu_mips_find_by_name(cpu_model);
7531
    if (!def)
7532
        return NULL;
7533
    env = qemu_mallocz(sizeof(CPUMIPSState));
7534
    if (!env)
7535
        return NULL;
7536
    env->cpu_model = def;
7537

    
7538
    cpu_exec_init(env);
7539
    env->cpu_model_str = cpu_model;
7540
    mips_tcg_init();
7541
    cpu_reset(env);
7542
    return env;
7543
}
7544

    
7545
void cpu_reset (CPUMIPSState *env)
7546
{
7547
    memset(env, 0, offsetof(CPUMIPSState, breakpoints));
7548

    
7549
    tlb_flush(env, 1);
7550

    
7551
    /* Minimal init */
7552
#if !defined(CONFIG_USER_ONLY)
7553
    if (env->hflags & MIPS_HFLAG_BMASK) {
7554
        /* If the exception was raised from a delay slot,
7555
         * come back to the jump.  */
7556
        env->CP0_ErrorEPC = env->PC[env->current_tc] - 4;
7557
    } else {
7558
        env->CP0_ErrorEPC = env->PC[env->current_tc];
7559
    }
7560
    env->PC[env->current_tc] = (int32_t)0xBFC00000;
7561
    env->CP0_Wired = 0;
7562
    /* SMP not implemented */
7563
    env->CP0_EBase = 0x80000000;
7564
    env->CP0_Status = (1 << CP0St_BEV) | (1 << CP0St_ERL);
7565
    /* vectored interrupts not implemented, timer on int 7,
7566
       no performance counters. */
7567
    env->CP0_IntCtl = 0xe0000000;
7568
    {
7569
        int i;
7570

    
7571
        for (i = 0; i < 7; i++) {
7572
            env->CP0_WatchLo[i] = 0;
7573
            env->CP0_WatchHi[i] = 0x80000000;
7574
        }
7575
        env->CP0_WatchLo[7] = 0;
7576
        env->CP0_WatchHi[7] = 0;
7577
    }
7578
    /* Count register increments in debug mode, EJTAG version 1 */
7579
    env->CP0_Debug = (1 << CP0DB_CNT) | (0x1 << CP0DB_VER);
7580
#endif
7581
    env->exception_index = EXCP_NONE;
7582
#if defined(CONFIG_USER_ONLY)
7583
    env->hflags = MIPS_HFLAG_UM;
7584
    env->user_mode_only = 1;
7585
#else
7586
    env->hflags = MIPS_HFLAG_CP0;
7587
#endif
7588
    cpu_mips_register(env, env->cpu_model);
7589
}
7590

    
7591
void gen_pc_load(CPUState *env, TranslationBlock *tb,
7592
                unsigned long searched_pc, int pc_pos, void *puc)
7593
{
7594
    env->PC[env->current_tc] = gen_opc_pc[pc_pos];
7595
    env->hflags &= ~MIPS_HFLAG_BMASK;
7596
    env->hflags |= gen_opc_hflags[pc_pos];
7597
}