Statistics
| Branch: | Revision:

root / target-mips / translate.c @ d26968ec

History | View | Annotate | Download (244.4 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_fpu;
427

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

    
431
#include "gen-icount.h"
432

    
433
static inline void tcg_gen_helper_0_i(void *func, TCGv arg)
434
{
435
    TCGv tmp = tcg_const_i32(arg);
436

    
437
    tcg_gen_helper_0_1(func, tmp);
438
    tcg_temp_free(tmp);
439
}
440

    
441
static inline void tcg_gen_helper_0_ii(void *func, TCGv arg1, TCGv arg2)
442
{
443
    TCGv tmp1 = tcg_const_i32(arg1);
444
    TCGv tmp2 = tcg_const_i32(arg2);
445

    
446
    tcg_gen_helper_0_2(func, tmp1, tmp2);
447
    tcg_temp_free(tmp1);
448
    tcg_temp_free(tmp2);
449
}
450

    
451
static inline void tcg_gen_helper_0_1i(void *func, TCGv arg1, TCGv arg2)
452
{
453
    TCGv tmp = tcg_const_i32(arg2);
454

    
455
    tcg_gen_helper_0_2(func, arg1, tmp);
456
    tcg_temp_free(tmp);
457
}
458

    
459
static inline void tcg_gen_helper_0_2i(void *func, TCGv arg1, TCGv arg2, TCGv arg3)
460
{
461
    TCGv tmp = tcg_const_i32(arg3);
462

    
463
    tcg_gen_helper_0_3(func, arg1, arg2, tmp);
464
    tcg_temp_free(tmp);
465
}
466

    
467
static inline void tcg_gen_helper_0_1ii(void *func, TCGv arg1, TCGv arg2, TCGv arg3)
468
{
469
    TCGv tmp1 = tcg_const_i32(arg2);
470
    TCGv tmp2 = tcg_const_i32(arg3);
471

    
472
    tcg_gen_helper_0_3(func, arg1, tmp1, tmp2);
473
    tcg_temp_free(tmp1);
474
    tcg_temp_free(tmp2);
475
}
476

    
477
static inline void tcg_gen_helper_1_i(void *func, TCGv ret, TCGv arg)
478
{
479
    TCGv tmp = tcg_const_i32(arg);
480

    
481
    tcg_gen_helper_1_1(func, ret, tmp);
482
    tcg_temp_free(tmp);
483
}
484

    
485
static inline void tcg_gen_helper_1_1i(void *func, TCGv ret, TCGv arg1, TCGv arg2)
486
{
487
    TCGv tmp = tcg_const_i32(arg2);
488

    
489
    tcg_gen_helper_1_2(func, ret, arg1, tmp);
490
    tcg_temp_free(tmp);
491
}
492

    
493
static inline void tcg_gen_helper_1_1ii(void *func, TCGv ret, TCGv arg1, TCGv arg2, TCGv arg3)
494
{
495
    TCGv tmp1 = tcg_const_i32(arg2);
496
    TCGv tmp2 = tcg_const_i32(arg3);
497

    
498
    tcg_gen_helper_1_3(func, ret, arg1, tmp1, tmp2);
499
    tcg_temp_free(tmp1);
500
    tcg_temp_free(tmp2);
501
}
502

    
503
static inline void tcg_gen_helper_1_2i(void *func, TCGv ret, TCGv arg1, TCGv arg2, TCGv arg3)
504
{
505
    TCGv tmp = tcg_const_i32(arg3);
506

    
507
    tcg_gen_helper_1_3(func, ret, arg1, arg2, tmp);
508
    tcg_temp_free(tmp);
509
}
510

    
511
static inline void tcg_gen_helper_1_2ii(void *func, TCGv ret, TCGv arg1, TCGv arg2, TCGv arg3, TCGv arg4)
512
{
513
    TCGv tmp1 = tcg_const_i32(arg3);
514
    TCGv tmp2 = tcg_const_i32(arg4);
515

    
516
    tcg_gen_helper_1_4(func, ret, arg1, arg2, tmp1, tmp2);
517
    tcg_temp_free(tmp1);
518
    tcg_temp_free(tmp2);
519
}
520

    
521
typedef struct DisasContext {
522
    struct TranslationBlock *tb;
523
    target_ulong pc, saved_pc;
524
    uint32_t opcode;
525
    uint32_t fp_status;
526
    /* Routine used to access memory */
527
    int mem_idx;
528
    uint32_t hflags, saved_hflags;
529
    int bstate;
530
    target_ulong btarget;
531
} DisasContext;
532

    
533
enum {
534
    BS_NONE     = 0, /* We go out of the TB without reaching a branch or an
535
                      * exception condition
536
                      */
537
    BS_STOP     = 1, /* We want to stop translation for any reason */
538
    BS_BRANCH   = 2, /* We reached a branch condition     */
539
    BS_EXCP     = 3, /* We reached an exception condition */
540
};
541

    
542
static const char *regnames[] =
543
    { "r0", "at", "v0", "v1", "a0", "a1", "a2", "a3",
544
      "t0", "t1", "t2", "t3", "t4", "t5", "t6", "t7",
545
      "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7",
546
      "t8", "t9", "k0", "k1", "gp", "sp", "s8", "ra", };
547

    
548
static const char *fregnames[] =
549
    { "f0",  "f1",  "f2",  "f3",  "f4",  "f5",  "f6",  "f7",
550
      "f8",  "f9",  "f10", "f11", "f12", "f13", "f14", "f15",
551
      "f16", "f17", "f18", "f19", "f20", "f21", "f22", "f23",
552
      "f24", "f25", "f26", "f27", "f28", "f29", "f30", "f31", };
553

    
554
#ifdef MIPS_DEBUG_DISAS
555
#define MIPS_DEBUG(fmt, args...)                                              \
556
do {                                                                          \
557
    if (loglevel & CPU_LOG_TB_IN_ASM) {                                       \
558
        fprintf(logfile, TARGET_FMT_lx ": %08x " fmt "\n",                    \
559
                ctx->pc, ctx->opcode , ##args);                               \
560
    }                                                                         \
561
} while (0)
562
#else
563
#define MIPS_DEBUG(fmt, args...) do { } while(0)
564
#endif
565

    
566
#define MIPS_INVAL(op)                                                        \
567
do {                                                                          \
568
    MIPS_DEBUG("Invalid %s %03x %03x %03x", op, ctx->opcode >> 26,            \
569
               ctx->opcode & 0x3F, ((ctx->opcode >> 16) & 0x1F));             \
570
} while (0)
571

    
572
/* General purpose registers moves. */
573
static inline void gen_load_gpr (TCGv t, int reg)
574
{
575
    if (reg == 0)
576
        tcg_gen_movi_tl(t, 0);
577
    else
578
        tcg_gen_ld_tl(t, cpu_env, offsetof(CPUState, active_tc.gpr) +
579
                                  sizeof(target_ulong) * reg);
580
}
581

    
582
static inline void gen_store_gpr (TCGv t, int reg)
583
{
584
    if (reg != 0)
585
        tcg_gen_st_tl(t, cpu_env, offsetof(CPUState, active_tc.gpr) +
586
                                  sizeof(target_ulong) * reg);
587
}
588

    
589
/* Moves to/from HI and LO registers.  */
590
static inline void gen_load_LO (TCGv t, int reg)
591
{
592
    tcg_gen_ld_tl(t, cpu_env, offsetof(CPUState, active_tc.LO) +
593
                              sizeof(target_ulong) * reg);
594
}
595

    
596
static inline void gen_store_LO (TCGv t, int reg)
597
{
598
    tcg_gen_st_tl(t, cpu_env, offsetof(CPUState, active_tc.LO) +
599
                              sizeof(target_ulong) * reg);
600
}
601

    
602
static inline void gen_load_HI (TCGv t, int reg)
603
{
604
    tcg_gen_ld_tl(t, cpu_env, offsetof(CPUState, active_tc.HI) +
605
                              sizeof(target_ulong) * reg);
606
}
607

    
608
static inline void gen_store_HI (TCGv t, int reg)
609
{
610
    tcg_gen_st_tl(t, cpu_env, offsetof(CPUState, active_tc.HI) +
611
                              sizeof(target_ulong) * reg);
612
}
613

    
614
/* Moves to/from shadow registers. */
615
static inline void gen_load_srsgpr (int from, int to)
616
{
617
    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_TL);
618

    
619
    if (from == 0)
620
        tcg_gen_movi_tl(r_tmp1, 0);
621
    else {
622
        TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
623

    
624
        tcg_gen_ld_i32(r_tmp2, cpu_env, offsetof(CPUState, CP0_SRSCtl));
625
        tcg_gen_shri_i32(r_tmp2, r_tmp2, CP0SRSCtl_PSS);
626
        tcg_gen_andi_i32(r_tmp2, r_tmp2, 0xf);
627
        tcg_gen_muli_i32(r_tmp2, r_tmp2, sizeof(target_ulong) * 32);
628
        tcg_gen_add_i32(r_tmp2, cpu_env, r_tmp2);
629

    
630
        tcg_gen_ld_tl(r_tmp1, r_tmp2, sizeof(target_ulong) * from);
631
        tcg_temp_free(r_tmp2);
632
    }
633
    gen_store_gpr(r_tmp1, to);
634
    tcg_temp_free(r_tmp1);
635
}
636

    
637
static inline void gen_store_srsgpr (int from, int to)
638
{
639
    if (to != 0) {
640
        TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_TL);
641
        TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
642

    
643
        gen_load_gpr(r_tmp1, from);
644
        tcg_gen_ld_i32(r_tmp2, cpu_env, offsetof(CPUState, CP0_SRSCtl));
645
        tcg_gen_shri_i32(r_tmp2, r_tmp2, CP0SRSCtl_PSS);
646
        tcg_gen_andi_i32(r_tmp2, r_tmp2, 0xf);
647
        tcg_gen_muli_i32(r_tmp2, r_tmp2, sizeof(target_ulong) * 32);
648
        tcg_gen_add_i32(r_tmp2, cpu_env, r_tmp2);
649

    
650
        tcg_gen_st_tl(r_tmp1, r_tmp2, sizeof(target_ulong) * to);
651
        tcg_temp_free(r_tmp1);
652
        tcg_temp_free(r_tmp2);
653
    }
654
}
655

    
656
/* Floating point register moves. */
657
static inline void gen_load_fpr32 (TCGv t, int reg)
658
{
659
    tcg_gen_ld_i32(t, current_fpu, 8 * reg + 4 * FP_ENDIAN_IDX);
660
}
661

    
662
static inline void gen_store_fpr32 (TCGv t, int reg)
663
{
664
    tcg_gen_st_i32(t, current_fpu, 8 * reg + 4 * FP_ENDIAN_IDX);
665
}
666

    
667
static inline void gen_load_fpr64 (DisasContext *ctx, TCGv t, int reg)
668
{
669
    if (ctx->hflags & MIPS_HFLAG_F64) {
670
        tcg_gen_ld_i64(t, current_fpu, 8 * reg);
671
    } else {
672
        TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
673
        TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
674

    
675
        tcg_gen_ld_i32(r_tmp1, current_fpu, 8 * (reg | 1) + 4 * FP_ENDIAN_IDX);
676
        tcg_gen_extu_i32_i64(t, r_tmp1);
677
        tcg_gen_shli_i64(t, t, 32);
678
        tcg_gen_ld_i32(r_tmp1, current_fpu, 8 * (reg & ~1) + 4 * FP_ENDIAN_IDX);
679
        tcg_gen_extu_i32_i64(r_tmp2, r_tmp1);
680
        tcg_gen_or_i64(t, t, r_tmp2);
681
        tcg_temp_free(r_tmp1);
682
        tcg_temp_free(r_tmp2);
683
    }
684
}
685

    
686
static inline void gen_store_fpr64 (DisasContext *ctx, TCGv t, int reg)
687
{
688
    if (ctx->hflags & MIPS_HFLAG_F64) {
689
        tcg_gen_st_i64(t, current_fpu, 8 * reg);
690
    } else {
691
        TCGv r_tmp = tcg_temp_new(TCG_TYPE_I32);
692

    
693
        tcg_gen_trunc_i64_i32(r_tmp, t);
694
        tcg_gen_st_i32(r_tmp, current_fpu, 8 * (reg & ~1) + 4 * FP_ENDIAN_IDX);
695
        tcg_gen_shri_i64(t, t, 32);
696
        tcg_gen_trunc_i64_i32(r_tmp, t);
697
        tcg_gen_st_i32(r_tmp, current_fpu, 8 * (reg | 1) + 4 * FP_ENDIAN_IDX);
698
        tcg_temp_free(r_tmp);
699
    }
700
}
701

    
702
static inline void gen_load_fpr32h (TCGv t, int reg)
703
{
704
    tcg_gen_ld_i32(t, current_fpu, 8 * reg + 4 * !FP_ENDIAN_IDX);
705
}
706

    
707
static inline void gen_store_fpr32h (TCGv t, int reg)
708
{
709
    tcg_gen_st_i32(t, current_fpu, 8 * reg + 4 * !FP_ENDIAN_IDX);
710
}
711

    
712
static inline void get_fp_cond (TCGv t)
713
{
714
    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
715
    TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
716

    
717
    tcg_gen_ld_i32(r_tmp1, current_fpu, offsetof(CPUMIPSFPUContext, fcr31));
718
    tcg_gen_shri_i32(r_tmp2, r_tmp1, 24);
719
    tcg_gen_andi_i32(r_tmp2, r_tmp2, 0xfe);
720
    tcg_gen_shri_i32(r_tmp1, r_tmp1, 23);
721
    tcg_gen_andi_i32(r_tmp1, r_tmp1, 0x1);
722
    tcg_gen_or_i32(t, r_tmp1, r_tmp2);
723
    tcg_temp_free(r_tmp1);
724
    tcg_temp_free(r_tmp2);
725
}
726

    
727
#define FOP_CONDS(type, fmt)                                              \
728
static GenOpFunc1 * fcmp ## type ## _ ## fmt ## _table[16] = {            \
729
    do_cmp ## type ## _ ## fmt ## _f,                                     \
730
    do_cmp ## type ## _ ## fmt ## _un,                                    \
731
    do_cmp ## type ## _ ## fmt ## _eq,                                    \
732
    do_cmp ## type ## _ ## fmt ## _ueq,                                   \
733
    do_cmp ## type ## _ ## fmt ## _olt,                                   \
734
    do_cmp ## type ## _ ## fmt ## _ult,                                   \
735
    do_cmp ## type ## _ ## fmt ## _ole,                                   \
736
    do_cmp ## type ## _ ## fmt ## _ule,                                   \
737
    do_cmp ## type ## _ ## fmt ## _sf,                                    \
738
    do_cmp ## type ## _ ## fmt ## _ngle,                                  \
739
    do_cmp ## type ## _ ## fmt ## _seq,                                   \
740
    do_cmp ## type ## _ ## fmt ## _ngl,                                   \
741
    do_cmp ## type ## _ ## fmt ## _lt,                                    \
742
    do_cmp ## type ## _ ## fmt ## _nge,                                   \
743
    do_cmp ## type ## _ ## fmt ## _le,                                    \
744
    do_cmp ## type ## _ ## fmt ## _ngt,                                   \
745
};                                                                        \
746
static inline void gen_cmp ## type ## _ ## fmt(int n, long cc)            \
747
{                                                                         \
748
    tcg_gen_helper_0_i(fcmp ## type ## _ ## fmt ## _table[n], cc);        \
749
}
750

    
751
FOP_CONDS(, d)
752
FOP_CONDS(abs, d)
753
FOP_CONDS(, s)
754
FOP_CONDS(abs, s)
755
FOP_CONDS(, ps)
756
FOP_CONDS(abs, ps)
757
#undef FOP_CONDS
758

    
759
/* Tests */
760
#define OP_COND(name, cond)                                   \
761
void glue(gen_op_, name) (TCGv t0, TCGv t1)                   \
762
{                                                             \
763
    int l1 = gen_new_label();                                 \
764
    int l2 = gen_new_label();                                 \
765
                                                              \
766
    tcg_gen_brcond_tl(cond, t0, t1, l1);                      \
767
    tcg_gen_movi_tl(t0, 0);                                   \
768
    tcg_gen_br(l2);                                           \
769
    gen_set_label(l1);                                        \
770
    tcg_gen_movi_tl(t0, 1);                                   \
771
    gen_set_label(l2);                                        \
772
}
773
OP_COND(eq, TCG_COND_EQ);
774
OP_COND(ne, TCG_COND_NE);
775
OP_COND(ge, TCG_COND_GE);
776
OP_COND(geu, TCG_COND_GEU);
777
OP_COND(lt, TCG_COND_LT);
778
OP_COND(ltu, TCG_COND_LTU);
779
#undef OP_COND
780

    
781
#define OP_CONDI(name, cond)                                  \
782
void glue(gen_op_, name) (TCGv t, target_ulong val)           \
783
{                                                             \
784
    int l1 = gen_new_label();                                 \
785
    int l2 = gen_new_label();                                 \
786
                                                              \
787
    tcg_gen_brcondi_tl(cond, t, val, l1);                     \
788
    tcg_gen_movi_tl(t, 0);                                    \
789
    tcg_gen_br(l2);                                           \
790
    gen_set_label(l1);                                        \
791
    tcg_gen_movi_tl(t, 1);                                    \
792
    gen_set_label(l2);                                        \
793
}
794
OP_CONDI(lti, TCG_COND_LT);
795
OP_CONDI(ltiu, TCG_COND_LTU);
796
#undef OP_CONDI
797

    
798
#define OP_CONDZ(name, cond)                                  \
799
void glue(gen_op_, name) (TCGv t)                             \
800
{                                                             \
801
    int l1 = gen_new_label();                                 \
802
    int l2 = gen_new_label();                                 \
803
                                                              \
804
    tcg_gen_brcondi_tl(cond, t, 0, l1);                       \
805
    tcg_gen_movi_tl(t, 0);                                    \
806
    tcg_gen_br(l2);                                           \
807
    gen_set_label(l1);                                        \
808
    tcg_gen_movi_tl(t, 1);                                    \
809
    gen_set_label(l2);                                        \
810
}
811
OP_CONDZ(gez, TCG_COND_GE);
812
OP_CONDZ(gtz, TCG_COND_GT);
813
OP_CONDZ(lez, TCG_COND_LE);
814
OP_CONDZ(ltz, TCG_COND_LT);
815
#undef OP_CONDZ
816

    
817
static inline void gen_save_pc(target_ulong pc)
818
{
819
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_TL);
820

    
821
    tcg_gen_movi_tl(r_tmp, pc);
822
    tcg_gen_st_tl(r_tmp, cpu_env, offsetof(CPUState, active_tc.PC));
823
    tcg_temp_free(r_tmp);
824
}
825

    
826
static inline void gen_breg_pc(void)
827
{
828
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_TL);
829

    
830
    tcg_gen_ld_tl(r_tmp, cpu_env, offsetof(CPUState, btarget));
831
    tcg_gen_st_tl(r_tmp, cpu_env, offsetof(CPUState, active_tc.PC));
832
    tcg_temp_free(r_tmp);
833
}
834

    
835
static inline void gen_save_btarget(target_ulong btarget)
836
{
837
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_TL);
838

    
839
    tcg_gen_movi_tl(r_tmp, btarget);
840
    tcg_gen_st_tl(r_tmp, cpu_env, offsetof(CPUState, btarget));
841
    tcg_temp_free(r_tmp);
842
}
843

    
844
static always_inline void gen_save_breg_target(int reg)
845
{
846
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_TL);
847

    
848
    gen_load_gpr(r_tmp, reg);
849
    tcg_gen_st_tl(r_tmp, cpu_env, offsetof(CPUState, btarget));
850
    tcg_temp_free(r_tmp);
851
}
852

    
853
static always_inline void save_cpu_state (DisasContext *ctx, int do_save_pc)
854
{
855
#if defined MIPS_DEBUG_DISAS
856
    if (loglevel & CPU_LOG_TB_IN_ASM) {
857
            fprintf(logfile, "hflags %08x saved %08x\n",
858
                    ctx->hflags, ctx->saved_hflags);
859
    }
860
#endif
861
    if (do_save_pc && ctx->pc != ctx->saved_pc) {
862
        gen_save_pc(ctx->pc);
863
        ctx->saved_pc = ctx->pc;
864
    }
865
    if (ctx->hflags != ctx->saved_hflags) {
866
        TCGv r_tmp = tcg_temp_new(TCG_TYPE_I32);
867

    
868
        tcg_gen_movi_i32(r_tmp, ctx->hflags);
869
        tcg_gen_st_i32(r_tmp, cpu_env, offsetof(CPUState, hflags));
870
        tcg_temp_free(r_tmp);
871
        ctx->saved_hflags = ctx->hflags;
872
        switch (ctx->hflags & MIPS_HFLAG_BMASK) {
873
        case MIPS_HFLAG_BR:
874
            break;
875
        case MIPS_HFLAG_BC:
876
        case MIPS_HFLAG_BL:
877
        case MIPS_HFLAG_B:
878
            gen_save_btarget(ctx->btarget);
879
            break;
880
        }
881
    }
882
}
883

    
884
static always_inline void restore_cpu_state (CPUState *env, DisasContext *ctx)
885
{
886
    ctx->saved_hflags = ctx->hflags;
887
    switch (ctx->hflags & MIPS_HFLAG_BMASK) {
888
    case MIPS_HFLAG_BR:
889
        break;
890
    case MIPS_HFLAG_BC:
891
    case MIPS_HFLAG_BL:
892
    case MIPS_HFLAG_B:
893
        ctx->btarget = env->btarget;
894
        break;
895
    }
896
}
897

    
898
static always_inline void
899
generate_exception_err (DisasContext *ctx, int excp, int err)
900
{
901
    save_cpu_state(ctx, 1);
902
    tcg_gen_helper_0_ii(do_raise_exception_err, excp, err);
903
    tcg_gen_helper_0_0(do_interrupt_restart);
904
    tcg_gen_exit_tb(0);
905
}
906

    
907
static always_inline void
908
generate_exception (DisasContext *ctx, int excp)
909
{
910
    save_cpu_state(ctx, 1);
911
    tcg_gen_helper_0_i(do_raise_exception, excp);
912
    tcg_gen_helper_0_0(do_interrupt_restart);
913
    tcg_gen_exit_tb(0);
914
}
915

    
916
/* Addresses computation */
917
static inline void gen_op_addr_add (TCGv t0, TCGv t1)
918
{
919
    tcg_gen_add_tl(t0, t0, t1);
920

    
921
#if defined(TARGET_MIPS64)
922
    /* For compatibility with 32-bit code, data reference in user mode
923
       with Status_UX = 0 should be casted to 32-bit and sign extended.
924
       See the MIPS64 PRA manual, section 4.10. */
925
    {
926
        int l1 = gen_new_label();
927
        TCGv r_tmp = tcg_temp_local_new(TCG_TYPE_I32);
928

    
929
        tcg_gen_ld_i32(r_tmp, cpu_env, offsetof(CPUState, hflags));
930
        tcg_gen_andi_i32(r_tmp, r_tmp, MIPS_HFLAG_KSU);
931
        tcg_gen_brcondi_i32(TCG_COND_NE, r_tmp, MIPS_HFLAG_UM, l1);
932
        tcg_gen_ld_i32(r_tmp, cpu_env, offsetof(CPUState, CP0_Status));
933
        tcg_gen_andi_i32(r_tmp, r_tmp, (1 << CP0St_UX));
934
        tcg_gen_brcondi_i32(TCG_COND_NE, r_tmp, 0, l1);
935
        tcg_temp_free(r_tmp);
936
        tcg_gen_ext32s_i64(t0, t0);
937
        gen_set_label(l1);
938
    }
939
#endif
940
}
941

    
942
static always_inline void check_cp0_enabled(DisasContext *ctx)
943
{
944
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_CP0)))
945
        generate_exception_err(ctx, EXCP_CpU, 1);
946
}
947

    
948
static always_inline void check_cp1_enabled(DisasContext *ctx)
949
{
950
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_FPU)))
951
        generate_exception_err(ctx, EXCP_CpU, 1);
952
}
953

    
954
/* Verify that the processor is running with COP1X instructions enabled.
955
   This is associated with the nabla symbol in the MIPS32 and MIPS64
956
   opcode tables.  */
957

    
958
static always_inline void check_cop1x(DisasContext *ctx)
959
{
960
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_COP1X)))
961
        generate_exception(ctx, EXCP_RI);
962
}
963

    
964
/* Verify that the processor is running with 64-bit floating-point
965
   operations enabled.  */
966

    
967
static always_inline void check_cp1_64bitmode(DisasContext *ctx)
968
{
969
    if (unlikely(~ctx->hflags & (MIPS_HFLAG_F64 | MIPS_HFLAG_COP1X)))
970
        generate_exception(ctx, EXCP_RI);
971
}
972

    
973
/*
974
 * Verify if floating point register is valid; an operation is not defined
975
 * if bit 0 of any register specification is set and the FR bit in the
976
 * Status register equals zero, since the register numbers specify an
977
 * even-odd pair of adjacent coprocessor general registers. When the FR bit
978
 * in the Status register equals one, both even and odd register numbers
979
 * are valid. This limitation exists only for 64 bit wide (d,l,ps) registers.
980
 *
981
 * Multiple 64 bit wide registers can be checked by calling
982
 * gen_op_cp1_registers(freg1 | freg2 | ... | fregN);
983
 */
984
void check_cp1_registers(DisasContext *ctx, int regs)
985
{
986
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_F64) && (regs & 1)))
987
        generate_exception(ctx, EXCP_RI);
988
}
989

    
990
/* This code generates a "reserved instruction" exception if the
991
   CPU does not support the instruction set corresponding to flags. */
992
static always_inline void check_insn(CPUState *env, DisasContext *ctx, int flags)
993
{
994
    if (unlikely(!(env->insn_flags & flags)))
995
        generate_exception(ctx, EXCP_RI);
996
}
997

    
998
/* This code generates a "reserved instruction" exception if 64-bit
999
   instructions are not enabled. */
1000
static always_inline void check_mips_64(DisasContext *ctx)
1001
{
1002
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_64)))
1003
        generate_exception(ctx, EXCP_RI);
1004
}
1005

    
1006
/* load/store instructions. */
1007
#define OP_LD(insn,fname)                                        \
1008
void inline op_ldst_##insn(TCGv t0, DisasContext *ctx)           \
1009
{                                                                \
1010
    tcg_gen_qemu_##fname(t0, t0, ctx->mem_idx);                  \
1011
}
1012
OP_LD(lb,ld8s);
1013
OP_LD(lbu,ld8u);
1014
OP_LD(lh,ld16s);
1015
OP_LD(lhu,ld16u);
1016
OP_LD(lw,ld32s);
1017
#if defined(TARGET_MIPS64)
1018
OP_LD(lwu,ld32u);
1019
OP_LD(ld,ld64);
1020
#endif
1021
#undef OP_LD
1022

    
1023
#define OP_ST(insn,fname)                                        \
1024
void inline op_ldst_##insn(TCGv t0, TCGv t1, DisasContext *ctx)  \
1025
{                                                                \
1026
    tcg_gen_qemu_##fname(t1, t0, ctx->mem_idx);                  \
1027
}
1028
OP_ST(sb,st8);
1029
OP_ST(sh,st16);
1030
OP_ST(sw,st32);
1031
#if defined(TARGET_MIPS64)
1032
OP_ST(sd,st64);
1033
#endif
1034
#undef OP_ST
1035

    
1036
#define OP_LD_ATOMIC(insn,fname)                                        \
1037
void inline op_ldst_##insn(TCGv t0, TCGv t1, DisasContext *ctx)         \
1038
{                                                                       \
1039
    tcg_gen_mov_tl(t1, t0);                                             \
1040
    tcg_gen_qemu_##fname(t0, t0, ctx->mem_idx);                         \
1041
    tcg_gen_st_tl(t1, cpu_env, offsetof(CPUState, CP0_LLAddr));         \
1042
}
1043
OP_LD_ATOMIC(ll,ld32s);
1044
#if defined(TARGET_MIPS64)
1045
OP_LD_ATOMIC(lld,ld64);
1046
#endif
1047
#undef OP_LD_ATOMIC
1048

    
1049
#define OP_ST_ATOMIC(insn,fname,almask)                                 \
1050
void inline op_ldst_##insn(TCGv t0, TCGv t1, DisasContext *ctx)         \
1051
{                                                                       \
1052
    TCGv r_tmp = tcg_temp_local_new(TCG_TYPE_TL);                       \
1053
    int l1 = gen_new_label();                                           \
1054
    int l2 = gen_new_label();                                           \
1055
    int l3 = gen_new_label();                                           \
1056
                                                                        \
1057
    tcg_gen_andi_tl(r_tmp, t0, almask);                                 \
1058
    tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp, 0, l1);                      \
1059
    tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_BadVAddr));       \
1060
    generate_exception(ctx, EXCP_AdES);                                 \
1061
    gen_set_label(l1);                                                  \
1062
    tcg_gen_ld_tl(r_tmp, cpu_env, offsetof(CPUState, CP0_LLAddr));      \
1063
    tcg_gen_brcond_tl(TCG_COND_NE, t0, r_tmp, l2);                      \
1064
    tcg_temp_free(r_tmp);                                               \
1065
    tcg_gen_qemu_##fname(t1, t0, ctx->mem_idx);                         \
1066
    tcg_gen_movi_tl(t0, 1);                                             \
1067
    tcg_gen_br(l3);                                                     \
1068
    gen_set_label(l2);                                                  \
1069
    tcg_gen_movi_tl(t0, 0);                                             \
1070
    gen_set_label(l3);                                                  \
1071
}
1072
OP_ST_ATOMIC(sc,st32,0x3);
1073
#if defined(TARGET_MIPS64)
1074
OP_ST_ATOMIC(scd,st64,0x7);
1075
#endif
1076
#undef OP_ST_ATOMIC
1077

    
1078
/* Load and store */
1079
static void gen_ldst (DisasContext *ctx, uint32_t opc, int rt,
1080
                      int base, int16_t offset)
1081
{
1082
    const char *opn = "ldst";
1083
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
1084
    TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
1085

    
1086
    if (base == 0) {
1087
        tcg_gen_movi_tl(t0, offset);
1088
    } else if (offset == 0) {
1089
        gen_load_gpr(t0, base);
1090
    } else {
1091
        gen_load_gpr(t0, base);
1092
        tcg_gen_movi_tl(t1, offset);
1093
        gen_op_addr_add(t0, t1);
1094
    }
1095
    /* Don't do NOP if destination is zero: we must perform the actual
1096
       memory access. */
1097
    switch (opc) {
1098
#if defined(TARGET_MIPS64)
1099
    case OPC_LWU:
1100
        op_ldst_lwu(t0, ctx);
1101
        gen_store_gpr(t0, rt);
1102
        opn = "lwu";
1103
        break;
1104
    case OPC_LD:
1105
        op_ldst_ld(t0, ctx);
1106
        gen_store_gpr(t0, rt);
1107
        opn = "ld";
1108
        break;
1109
    case OPC_LLD:
1110
        op_ldst_lld(t0, t1, ctx);
1111
        gen_store_gpr(t0, rt);
1112
        opn = "lld";
1113
        break;
1114
    case OPC_SD:
1115
        gen_load_gpr(t1, rt);
1116
        op_ldst_sd(t0, t1, ctx);
1117
        opn = "sd";
1118
        break;
1119
    case OPC_SCD:
1120
        save_cpu_state(ctx, 1);
1121
        gen_load_gpr(t1, rt);
1122
        op_ldst_scd(t0, t1, ctx);
1123
        gen_store_gpr(t0, rt);
1124
        opn = "scd";
1125
        break;
1126
    case OPC_LDL:
1127
        save_cpu_state(ctx, 1);
1128
        gen_load_gpr(t1, rt);
1129
        tcg_gen_helper_1_2i(do_ldl, t1, t0, t1, ctx->mem_idx);
1130
        gen_store_gpr(t1, rt);
1131
        opn = "ldl";
1132
        break;
1133
    case OPC_SDL:
1134
        save_cpu_state(ctx, 1);
1135
        gen_load_gpr(t1, rt);
1136
        tcg_gen_helper_0_2i(do_sdl, t0, t1, ctx->mem_idx);
1137
        opn = "sdl";
1138
        break;
1139
    case OPC_LDR:
1140
        save_cpu_state(ctx, 1);
1141
        gen_load_gpr(t1, rt);
1142
        tcg_gen_helper_1_2i(do_ldr, t1, t0, t1, ctx->mem_idx);
1143
        gen_store_gpr(t1, rt);
1144
        opn = "ldr";
1145
        break;
1146
    case OPC_SDR:
1147
        save_cpu_state(ctx, 1);
1148
        gen_load_gpr(t1, rt);
1149
        tcg_gen_helper_0_2i(do_sdr, t0, t1, ctx->mem_idx);
1150
        opn = "sdr";
1151
        break;
1152
#endif
1153
    case OPC_LW:
1154
        op_ldst_lw(t0, ctx);
1155
        gen_store_gpr(t0, rt);
1156
        opn = "lw";
1157
        break;
1158
    case OPC_SW:
1159
        gen_load_gpr(t1, rt);
1160
        op_ldst_sw(t0, t1, ctx);
1161
        opn = "sw";
1162
        break;
1163
    case OPC_LH:
1164
        op_ldst_lh(t0, ctx);
1165
        gen_store_gpr(t0, rt);
1166
        opn = "lh";
1167
        break;
1168
    case OPC_SH:
1169
        gen_load_gpr(t1, rt);
1170
        op_ldst_sh(t0, t1, ctx);
1171
        opn = "sh";
1172
        break;
1173
    case OPC_LHU:
1174
        op_ldst_lhu(t0, ctx);
1175
        gen_store_gpr(t0, rt);
1176
        opn = "lhu";
1177
        break;
1178
    case OPC_LB:
1179
        op_ldst_lb(t0, ctx);
1180
        gen_store_gpr(t0, rt);
1181
        opn = "lb";
1182
        break;
1183
    case OPC_SB:
1184
        gen_load_gpr(t1, rt);
1185
        op_ldst_sb(t0, t1, ctx);
1186
        opn = "sb";
1187
        break;
1188
    case OPC_LBU:
1189
        op_ldst_lbu(t0, ctx);
1190
        gen_store_gpr(t0, rt);
1191
        opn = "lbu";
1192
        break;
1193
    case OPC_LWL:
1194
        save_cpu_state(ctx, 1);
1195
        gen_load_gpr(t1, rt);
1196
        tcg_gen_helper_1_2i(do_lwl, t1, t0, t1, ctx->mem_idx);
1197
        gen_store_gpr(t1, rt);
1198
        opn = "lwl";
1199
        break;
1200
    case OPC_SWL:
1201
        save_cpu_state(ctx, 1);
1202
        gen_load_gpr(t1, rt);
1203
        tcg_gen_helper_0_2i(do_swl, t0, t1, ctx->mem_idx);
1204
        opn = "swr";
1205
        break;
1206
    case OPC_LWR:
1207
        save_cpu_state(ctx, 1);
1208
        gen_load_gpr(t1, rt);
1209
        tcg_gen_helper_1_2i(do_lwr, t1, t0, t1, ctx->mem_idx);
1210
        gen_store_gpr(t1, rt);
1211
        opn = "lwr";
1212
        break;
1213
    case OPC_SWR:
1214
        save_cpu_state(ctx, 1);
1215
        gen_load_gpr(t1, rt);
1216
        tcg_gen_helper_0_2i(do_swr, t0, t1, ctx->mem_idx);
1217
        opn = "swr";
1218
        break;
1219
    case OPC_LL:
1220
        op_ldst_ll(t0, t1, ctx);
1221
        gen_store_gpr(t0, rt);
1222
        opn = "ll";
1223
        break;
1224
    case OPC_SC:
1225
        save_cpu_state(ctx, 1);
1226
        gen_load_gpr(t1, rt);
1227
        op_ldst_sc(t0, t1, ctx);
1228
        gen_store_gpr(t0, rt);
1229
        opn = "sc";
1230
        break;
1231
    default:
1232
        MIPS_INVAL(opn);
1233
        generate_exception(ctx, EXCP_RI);
1234
        goto out;
1235
    }
1236
    MIPS_DEBUG("%s %s, %d(%s)", opn, regnames[rt], offset, regnames[base]);
1237
 out:
1238
    tcg_temp_free(t0);
1239
    tcg_temp_free(t1);
1240
}
1241

    
1242
/* Load and store */
1243
static void gen_flt_ldst (DisasContext *ctx, uint32_t opc, int ft,
1244
                      int base, int16_t offset)
1245
{
1246
    const char *opn = "flt_ldst";
1247
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
1248

    
1249
    if (base == 0) {
1250
        tcg_gen_movi_tl(t0, offset);
1251
    } else if (offset == 0) {
1252
        gen_load_gpr(t0, base);
1253
    } else {
1254
        TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
1255

    
1256
        gen_load_gpr(t0, base);
1257
        tcg_gen_movi_tl(t1, offset);
1258
        gen_op_addr_add(t0, t1);
1259
        tcg_temp_free(t1);
1260
    }
1261
    /* Don't do NOP if destination is zero: we must perform the actual
1262
       memory access. */
1263
    switch (opc) {
1264
    case OPC_LWC1:
1265
        tcg_gen_qemu_ld32s(fpu32_T[0], t0, ctx->mem_idx);
1266
        gen_store_fpr32(fpu32_T[0], ft);
1267
        opn = "lwc1";
1268
        break;
1269
    case OPC_SWC1:
1270
        gen_load_fpr32(fpu32_T[0], ft);
1271
        tcg_gen_qemu_st32(fpu32_T[0], t0, ctx->mem_idx);
1272
        opn = "swc1";
1273
        break;
1274
    case OPC_LDC1:
1275
        tcg_gen_qemu_ld64(fpu64_T[0], t0, ctx->mem_idx);
1276
        gen_store_fpr64(ctx, fpu64_T[0], ft);
1277
        opn = "ldc1";
1278
        break;
1279
    case OPC_SDC1:
1280
        gen_load_fpr64(ctx, fpu64_T[0], ft);
1281
        tcg_gen_qemu_st64(fpu64_T[0], t0, ctx->mem_idx);
1282
        opn = "sdc1";
1283
        break;
1284
    default:
1285
        MIPS_INVAL(opn);
1286
        generate_exception(ctx, EXCP_RI);
1287
        goto out;
1288
    }
1289
    MIPS_DEBUG("%s %s, %d(%s)", opn, fregnames[ft], offset, regnames[base]);
1290
 out:
1291
    tcg_temp_free(t0);
1292
}
1293

    
1294
/* Arithmetic with immediate operand */
1295
static void gen_arith_imm (CPUState *env, DisasContext *ctx, uint32_t opc,
1296
                           int rt, int rs, int16_t imm)
1297
{
1298
    target_ulong uimm;
1299
    const char *opn = "imm arith";
1300
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
1301

    
1302
    if (rt == 0 && opc != OPC_ADDI && opc != OPC_DADDI) {
1303
        /* If no destination, treat it as a NOP.
1304
           For addi, we must generate the overflow exception when needed. */
1305
        MIPS_DEBUG("NOP");
1306
        goto out;
1307
    }
1308
    uimm = (uint16_t)imm;
1309
    switch (opc) {
1310
    case OPC_ADDI:
1311
    case OPC_ADDIU:
1312
#if defined(TARGET_MIPS64)
1313
    case OPC_DADDI:
1314
    case OPC_DADDIU:
1315
#endif
1316
    case OPC_SLTI:
1317
    case OPC_SLTIU:
1318
        uimm = (target_long)imm; /* Sign extend to 32/64 bits */
1319
        /* Fall through. */
1320
    case OPC_ANDI:
1321
    case OPC_ORI:
1322
    case OPC_XORI:
1323
        gen_load_gpr(t0, rs);
1324
        break;
1325
    case OPC_LUI:
1326
        tcg_gen_movi_tl(t0, imm << 16);
1327
        break;
1328
    case OPC_SLL:
1329
    case OPC_SRA:
1330
    case OPC_SRL:
1331
#if defined(TARGET_MIPS64)
1332
    case OPC_DSLL:
1333
    case OPC_DSRA:
1334
    case OPC_DSRL:
1335
    case OPC_DSLL32:
1336
    case OPC_DSRA32:
1337
    case OPC_DSRL32:
1338
#endif
1339
        uimm &= 0x1f;
1340
        gen_load_gpr(t0, rs);
1341
        break;
1342
    }
1343
    switch (opc) {
1344
    case OPC_ADDI:
1345
        {
1346
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1347
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1348
            int l1 = gen_new_label();
1349

    
1350
            save_cpu_state(ctx, 1);
1351
            tcg_gen_ext32s_tl(r_tmp1, t0);
1352
            tcg_gen_addi_tl(t0, r_tmp1, uimm);
1353

    
1354
            tcg_gen_xori_tl(r_tmp1, r_tmp1, uimm);
1355
            tcg_gen_xori_tl(r_tmp1, r_tmp1, -1);
1356
            tcg_gen_xori_tl(r_tmp2, t0, uimm);
1357
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1358
            tcg_temp_free(r_tmp2);
1359
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 31);
1360
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1361
            tcg_temp_free(r_tmp1);
1362
            /* operands of same sign, result different sign */
1363
            generate_exception(ctx, EXCP_OVERFLOW);
1364
            gen_set_label(l1);
1365

    
1366
            tcg_gen_ext32s_tl(t0, t0);
1367
        }
1368
        opn = "addi";
1369
        break;
1370
    case OPC_ADDIU:
1371
        tcg_gen_ext32s_tl(t0, t0);
1372
        tcg_gen_addi_tl(t0, t0, uimm);
1373
        tcg_gen_ext32s_tl(t0, t0);
1374
        opn = "addiu";
1375
        break;
1376
#if defined(TARGET_MIPS64)
1377
    case OPC_DADDI:
1378
        {
1379
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1380
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1381
            int l1 = gen_new_label();
1382

    
1383
            save_cpu_state(ctx, 1);
1384
            tcg_gen_mov_tl(r_tmp1, t0);
1385
            tcg_gen_addi_tl(t0, t0, uimm);
1386

    
1387
            tcg_gen_xori_tl(r_tmp1, r_tmp1, uimm);
1388
            tcg_gen_xori_tl(r_tmp1, r_tmp1, -1);
1389
            tcg_gen_xori_tl(r_tmp2, t0, uimm);
1390
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1391
            tcg_temp_free(r_tmp2);
1392
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 63);
1393
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1394
            tcg_temp_free(r_tmp1);
1395
            /* operands of same sign, result different sign */
1396
            generate_exception(ctx, EXCP_OVERFLOW);
1397
            gen_set_label(l1);
1398
        }
1399
        opn = "daddi";
1400
        break;
1401
    case OPC_DADDIU:
1402
        tcg_gen_addi_tl(t0, t0, uimm);
1403
        opn = "daddiu";
1404
        break;
1405
#endif
1406
    case OPC_SLTI:
1407
        gen_op_lti(t0, uimm);
1408
        opn = "slti";
1409
        break;
1410
    case OPC_SLTIU:
1411
        gen_op_ltiu(t0, uimm);
1412
        opn = "sltiu";
1413
        break;
1414
    case OPC_ANDI:
1415
        tcg_gen_andi_tl(t0, t0, uimm);
1416
        opn = "andi";
1417
        break;
1418
    case OPC_ORI:
1419
        tcg_gen_ori_tl(t0, t0, uimm);
1420
        opn = "ori";
1421
        break;
1422
    case OPC_XORI:
1423
        tcg_gen_xori_tl(t0, t0, uimm);
1424
        opn = "xori";
1425
        break;
1426
    case OPC_LUI:
1427
        opn = "lui";
1428
        break;
1429
    case OPC_SLL:
1430
        tcg_gen_ext32u_tl(t0, t0);
1431
        tcg_gen_shli_tl(t0, t0, uimm);
1432
        tcg_gen_ext32s_tl(t0, t0);
1433
        opn = "sll";
1434
        break;
1435
    case OPC_SRA:
1436
        tcg_gen_ext32s_tl(t0, t0);
1437
        tcg_gen_sari_tl(t0, t0, uimm);
1438
        tcg_gen_ext32s_tl(t0, t0);
1439
        opn = "sra";
1440
        break;
1441
    case OPC_SRL:
1442
        switch ((ctx->opcode >> 21) & 0x1f) {
1443
        case 0:
1444
            tcg_gen_ext32u_tl(t0, t0);
1445
            tcg_gen_shri_tl(t0, t0, uimm);
1446
            tcg_gen_ext32s_tl(t0, t0);
1447
            opn = "srl";
1448
            break;
1449
        case 1:
1450
            /* rotr is decoded as srl on non-R2 CPUs */
1451
            if (env->insn_flags & ISA_MIPS32R2) {
1452
                if (uimm != 0) {
1453
                    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
1454
                    TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
1455

    
1456
                    tcg_gen_trunc_tl_i32(r_tmp1, t0);
1457
                    tcg_gen_movi_i32(r_tmp2, 0x20);
1458
                    tcg_gen_subi_i32(r_tmp2, r_tmp2, uimm);
1459
                    tcg_gen_shl_i32(r_tmp2, r_tmp1, r_tmp2);
1460
                    tcg_gen_shri_i32(r_tmp1, r_tmp1, uimm);
1461
                    tcg_gen_or_i32(r_tmp1, r_tmp1, r_tmp2);
1462
                    tcg_gen_ext_i32_tl(t0, r_tmp1);
1463
                    tcg_temp_free(r_tmp1);
1464
                    tcg_temp_free(r_tmp2);
1465
                }
1466
                opn = "rotr";
1467
            } else {
1468
                tcg_gen_ext32u_tl(t0, t0);
1469
                tcg_gen_shri_tl(t0, t0, uimm);
1470
                tcg_gen_ext32s_tl(t0, t0);
1471
                opn = "srl";
1472
            }
1473
            break;
1474
        default:
1475
            MIPS_INVAL("invalid srl flag");
1476
            generate_exception(ctx, EXCP_RI);
1477
            break;
1478
        }
1479
        break;
1480
#if defined(TARGET_MIPS64)
1481
    case OPC_DSLL:
1482
        tcg_gen_shli_tl(t0, t0, uimm);
1483
        opn = "dsll";
1484
        break;
1485
    case OPC_DSRA:
1486
        tcg_gen_sari_tl(t0, t0, uimm);
1487
        opn = "dsra";
1488
        break;
1489
    case OPC_DSRL:
1490
        switch ((ctx->opcode >> 21) & 0x1f) {
1491
        case 0:
1492
            tcg_gen_shri_tl(t0, t0, uimm);
1493
            opn = "dsrl";
1494
            break;
1495
        case 1:
1496
            /* drotr is decoded as dsrl on non-R2 CPUs */
1497
            if (env->insn_flags & ISA_MIPS32R2) {
1498
                if (uimm != 0) {
1499
                    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_TL);
1500

    
1501
                    tcg_gen_movi_tl(r_tmp1, 0x40);
1502
                    tcg_gen_subi_tl(r_tmp1, r_tmp1, uimm);
1503
                    tcg_gen_shl_tl(r_tmp1, t0, r_tmp1);
1504
                    tcg_gen_shri_tl(t0, t0, uimm);
1505
                    tcg_gen_or_tl(t0, t0, r_tmp1);
1506
                    tcg_temp_free(r_tmp1);
1507
                }
1508
                opn = "drotr";
1509
            } else {
1510
                tcg_gen_shri_tl(t0, t0, uimm);
1511
                opn = "dsrl";
1512
            }
1513
            break;
1514
        default:
1515
            MIPS_INVAL("invalid dsrl flag");
1516
            generate_exception(ctx, EXCP_RI);
1517
            break;
1518
        }
1519
        break;
1520
    case OPC_DSLL32:
1521
        tcg_gen_shli_tl(t0, t0, uimm + 32);
1522
        opn = "dsll32";
1523
        break;
1524
    case OPC_DSRA32:
1525
        tcg_gen_sari_tl(t0, t0, uimm + 32);
1526
        opn = "dsra32";
1527
        break;
1528
    case OPC_DSRL32:
1529
        switch ((ctx->opcode >> 21) & 0x1f) {
1530
        case 0:
1531
            tcg_gen_shri_tl(t0, t0, uimm + 32);
1532
            opn = "dsrl32";
1533
            break;
1534
        case 1:
1535
            /* drotr32 is decoded as dsrl32 on non-R2 CPUs */
1536
            if (env->insn_flags & ISA_MIPS32R2) {
1537
                TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_TL);
1538
                TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1539

    
1540
                tcg_gen_movi_tl(r_tmp1, 0x40);
1541
                tcg_gen_movi_tl(r_tmp2, 32);
1542
                tcg_gen_addi_tl(r_tmp2, r_tmp2, uimm);
1543
                tcg_gen_sub_tl(r_tmp1, r_tmp1, r_tmp2);
1544
                tcg_gen_shl_tl(r_tmp1, t0, r_tmp1);
1545
                tcg_gen_shr_tl(t0, t0, r_tmp2);
1546
                tcg_gen_or_tl(t0, t0, r_tmp1);
1547
                tcg_temp_free(r_tmp1);
1548
                tcg_temp_free(r_tmp2);
1549
                opn = "drotr32";
1550
            } else {
1551
                tcg_gen_shri_tl(t0, t0, uimm + 32);
1552
                opn = "dsrl32";
1553
            }
1554
            break;
1555
        default:
1556
            MIPS_INVAL("invalid dsrl32 flag");
1557
            generate_exception(ctx, EXCP_RI);
1558
            break;
1559
        }
1560
        break;
1561
#endif
1562
    default:
1563
        MIPS_INVAL(opn);
1564
        generate_exception(ctx, EXCP_RI);
1565
        goto out;
1566
    }
1567
    gen_store_gpr(t0, rt);
1568
    MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1569
 out:
1570
    tcg_temp_free(t0);
1571
}
1572

    
1573
/* Arithmetic */
1574
static void gen_arith (CPUState *env, DisasContext *ctx, uint32_t opc,
1575
                       int rd, int rs, int rt)
1576
{
1577
    const char *opn = "arith";
1578
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
1579
    TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
1580

    
1581
    if (rd == 0 && opc != OPC_ADD && opc != OPC_SUB
1582
       && opc != OPC_DADD && opc != OPC_DSUB) {
1583
        /* If no destination, treat it as a NOP.
1584
           For add & sub, we must generate the overflow exception when needed. */
1585
        MIPS_DEBUG("NOP");
1586
        goto out;
1587
    }
1588
    gen_load_gpr(t0, rs);
1589
    /* Specialcase the conventional move operation. */
1590
    if (rt == 0 && (opc == OPC_ADDU || opc == OPC_DADDU
1591
                    || opc == OPC_SUBU || opc == OPC_DSUBU)) {
1592
        gen_store_gpr(t0, rd);
1593
        goto out;
1594
    }
1595
    gen_load_gpr(t1, rt);
1596
    switch (opc) {
1597
    case OPC_ADD:
1598
        {
1599
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1600
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1601
            int l1 = gen_new_label();
1602

    
1603
            save_cpu_state(ctx, 1);
1604
            tcg_gen_ext32s_tl(r_tmp1, t0);
1605
            tcg_gen_ext32s_tl(r_tmp2, t1);
1606
            tcg_gen_add_tl(t0, r_tmp1, r_tmp2);
1607

    
1608
            tcg_gen_xor_tl(r_tmp1, r_tmp1, t1);
1609
            tcg_gen_xori_tl(r_tmp1, r_tmp1, -1);
1610
            tcg_gen_xor_tl(r_tmp2, t0, t1);
1611
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1612
            tcg_temp_free(r_tmp2);
1613
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 31);
1614
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1615
            tcg_temp_free(r_tmp1);
1616
            /* operands of same sign, result different sign */
1617
            generate_exception(ctx, EXCP_OVERFLOW);
1618
            gen_set_label(l1);
1619

    
1620
            tcg_gen_ext32s_tl(t0, t0);
1621
        }
1622
        opn = "add";
1623
        break;
1624
    case OPC_ADDU:
1625
        tcg_gen_ext32s_tl(t0, t0);
1626
        tcg_gen_ext32s_tl(t1, t1);
1627
        tcg_gen_add_tl(t0, t0, t1);
1628
        tcg_gen_ext32s_tl(t0, t0);
1629
        opn = "addu";
1630
        break;
1631
    case OPC_SUB:
1632
        {
1633
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1634
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1635
            int l1 = gen_new_label();
1636

    
1637
            save_cpu_state(ctx, 1);
1638
            tcg_gen_ext32s_tl(r_tmp1, t0);
1639
            tcg_gen_ext32s_tl(r_tmp2, t1);
1640
            tcg_gen_sub_tl(t0, r_tmp1, r_tmp2);
1641

    
1642
            tcg_gen_xor_tl(r_tmp2, r_tmp1, t1);
1643
            tcg_gen_xor_tl(r_tmp1, r_tmp1, t0);
1644
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1645
            tcg_temp_free(r_tmp2);
1646
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 31);
1647
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1648
            tcg_temp_free(r_tmp1);
1649
            /* operands of different sign, first operand and result different sign */
1650
            generate_exception(ctx, EXCP_OVERFLOW);
1651
            gen_set_label(l1);
1652

    
1653
            tcg_gen_ext32s_tl(t0, t0);
1654
        }
1655
        opn = "sub";
1656
        break;
1657
    case OPC_SUBU:
1658
        tcg_gen_ext32s_tl(t0, t0);
1659
        tcg_gen_ext32s_tl(t1, t1);
1660
        tcg_gen_sub_tl(t0, t0, t1);
1661
        tcg_gen_ext32s_tl(t0, t0);
1662
        opn = "subu";
1663
        break;
1664
#if defined(TARGET_MIPS64)
1665
    case OPC_DADD:
1666
        {
1667
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1668
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1669
            int l1 = gen_new_label();
1670

    
1671
            save_cpu_state(ctx, 1);
1672
            tcg_gen_mov_tl(r_tmp1, t0);
1673
            tcg_gen_add_tl(t0, t0, t1);
1674

    
1675
            tcg_gen_xor_tl(r_tmp1, r_tmp1, t1);
1676
            tcg_gen_xori_tl(r_tmp1, r_tmp1, -1);
1677
            tcg_gen_xor_tl(r_tmp2, t0, t1);
1678
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1679
            tcg_temp_free(r_tmp2);
1680
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 63);
1681
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1682
            tcg_temp_free(r_tmp1);
1683
            /* operands of same sign, result different sign */
1684
            generate_exception(ctx, EXCP_OVERFLOW);
1685
            gen_set_label(l1);
1686
        }
1687
        opn = "dadd";
1688
        break;
1689
    case OPC_DADDU:
1690
        tcg_gen_add_tl(t0, t0, t1);
1691
        opn = "daddu";
1692
        break;
1693
    case OPC_DSUB:
1694
        {
1695
            TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_TL);
1696
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_TL);
1697
            int l1 = gen_new_label();
1698

    
1699
            save_cpu_state(ctx, 1);
1700
            tcg_gen_mov_tl(r_tmp1, t0);
1701
            tcg_gen_sub_tl(t0, t0, t1);
1702

    
1703
            tcg_gen_xor_tl(r_tmp2, r_tmp1, t1);
1704
            tcg_gen_xor_tl(r_tmp1, r_tmp1, t0);
1705
            tcg_gen_and_tl(r_tmp1, r_tmp1, r_tmp2);
1706
            tcg_temp_free(r_tmp2);
1707
            tcg_gen_shri_tl(r_tmp1, r_tmp1, 63);
1708
            tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp1, 0, l1);
1709
            tcg_temp_free(r_tmp1);
1710
            /* operands of different sign, first operand and result different sign */
1711
            generate_exception(ctx, EXCP_OVERFLOW);
1712
            gen_set_label(l1);
1713
        }
1714
        opn = "dsub";
1715
        break;
1716
    case OPC_DSUBU:
1717
        tcg_gen_sub_tl(t0, t0, t1);
1718
        opn = "dsubu";
1719
        break;
1720
#endif
1721
    case OPC_SLT:
1722
        gen_op_lt(t0, t1);
1723
        opn = "slt";
1724
        break;
1725
    case OPC_SLTU:
1726
        gen_op_ltu(t0, t1);
1727
        opn = "sltu";
1728
        break;
1729
    case OPC_AND:
1730
        tcg_gen_and_tl(t0, t0, t1);
1731
        opn = "and";
1732
        break;
1733
    case OPC_NOR:
1734
        tcg_gen_or_tl(t0, t0, t1);
1735
        tcg_gen_not_tl(t0, t0);
1736
        opn = "nor";
1737
        break;
1738
    case OPC_OR:
1739
        tcg_gen_or_tl(t0, t0, t1);
1740
        opn = "or";
1741
        break;
1742
    case OPC_XOR:
1743
        tcg_gen_xor_tl(t0, t0, t1);
1744
        opn = "xor";
1745
        break;
1746
    case OPC_MUL:
1747
        tcg_gen_ext32s_tl(t0, t0);
1748
        tcg_gen_ext32s_tl(t1, t1);
1749
        tcg_gen_mul_tl(t0, t0, t1);
1750
        tcg_gen_ext32s_tl(t0, t0);
1751
        opn = "mul";
1752
        break;
1753
    case OPC_MOVN:
1754
        {
1755
            int l1 = gen_new_label();
1756

    
1757
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
1758
            gen_store_gpr(t0, rd);
1759
            gen_set_label(l1);
1760
        }
1761
        opn = "movn";
1762
        goto print;
1763
    case OPC_MOVZ:
1764
        {
1765
            int l1 = gen_new_label();
1766

    
1767
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
1768
            gen_store_gpr(t0, rd);
1769
            gen_set_label(l1);
1770
        }
1771
        opn = "movz";
1772
        goto print;
1773
    case OPC_SLLV:
1774
        tcg_gen_ext32u_tl(t0, t0);
1775
        tcg_gen_ext32u_tl(t1, t1);
1776
        tcg_gen_andi_tl(t0, t0, 0x1f);
1777
        tcg_gen_shl_tl(t0, t1, t0);
1778
        tcg_gen_ext32s_tl(t0, t0);
1779
        opn = "sllv";
1780
        break;
1781
    case OPC_SRAV:
1782
        tcg_gen_ext32s_tl(t1, t1);
1783
        tcg_gen_andi_tl(t0, t0, 0x1f);
1784
        tcg_gen_sar_tl(t0, t1, t0);
1785
        tcg_gen_ext32s_tl(t0, t0);
1786
        opn = "srav";
1787
        break;
1788
    case OPC_SRLV:
1789
        switch ((ctx->opcode >> 6) & 0x1f) {
1790
        case 0:
1791
            tcg_gen_ext32u_tl(t1, t1);
1792
            tcg_gen_andi_tl(t0, t0, 0x1f);
1793
            tcg_gen_shr_tl(t0, t1, t0);
1794
            tcg_gen_ext32s_tl(t0, t0);
1795
            opn = "srlv";
1796
            break;
1797
        case 1:
1798
            /* rotrv is decoded as srlv on non-R2 CPUs */
1799
            if (env->insn_flags & ISA_MIPS32R2) {
1800
                int l1 = gen_new_label();
1801
                int l2 = gen_new_label();
1802

    
1803
                tcg_gen_andi_tl(t0, t0, 0x1f);
1804
                tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);
1805
                {
1806
                    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
1807
                    TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
1808
                    TCGv r_tmp3 = tcg_temp_new(TCG_TYPE_I32);
1809

    
1810
                    tcg_gen_trunc_tl_i32(r_tmp1, t0);
1811
                    tcg_gen_trunc_tl_i32(r_tmp2, t1);
1812
                    tcg_gen_movi_i32(r_tmp3, 0x20);
1813
                    tcg_gen_sub_i32(r_tmp3, r_tmp3, r_tmp1);
1814
                    tcg_gen_shl_i32(r_tmp3, r_tmp2, r_tmp3);
1815
                    tcg_gen_shr_i32(r_tmp1, r_tmp2, r_tmp1);
1816
                    tcg_gen_or_i32(r_tmp1, r_tmp1, r_tmp3);
1817
                    tcg_gen_ext_i32_tl(t0, r_tmp1);
1818
                    tcg_temp_free(r_tmp1);
1819
                    tcg_temp_free(r_tmp2);
1820
                    tcg_temp_free(r_tmp3);
1821
                    tcg_gen_br(l2);
1822
                }
1823
                gen_set_label(l1);
1824
                tcg_gen_mov_tl(t0, t1);
1825
                gen_set_label(l2);
1826
                opn = "rotrv";
1827
            } else {
1828
                tcg_gen_ext32u_tl(t1, t1);
1829
                tcg_gen_andi_tl(t0, t0, 0x1f);
1830
                tcg_gen_shr_tl(t0, t1, t0);
1831
                tcg_gen_ext32s_tl(t0, t0);
1832
                opn = "srlv";
1833
            }
1834
            break;
1835
        default:
1836
            MIPS_INVAL("invalid srlv flag");
1837
            generate_exception(ctx, EXCP_RI);
1838
            break;
1839
        }
1840
        break;
1841
#if defined(TARGET_MIPS64)
1842
    case OPC_DSLLV:
1843
        tcg_gen_andi_tl(t0, t0, 0x3f);
1844
        tcg_gen_shl_tl(t0, t1, t0);
1845
        opn = "dsllv";
1846
        break;
1847
    case OPC_DSRAV:
1848
        tcg_gen_andi_tl(t0, t0, 0x3f);
1849
        tcg_gen_sar_tl(t0, t1, t0);
1850
        opn = "dsrav";
1851
        break;
1852
    case OPC_DSRLV:
1853
        switch ((ctx->opcode >> 6) & 0x1f) {
1854
        case 0:
1855
            tcg_gen_andi_tl(t0, t0, 0x3f);
1856
            tcg_gen_shr_tl(t0, t1, t0);
1857
            opn = "dsrlv";
1858
            break;
1859
        case 1:
1860
            /* drotrv is decoded as dsrlv on non-R2 CPUs */
1861
            if (env->insn_flags & ISA_MIPS32R2) {
1862
                int l1 = gen_new_label();
1863
                int l2 = gen_new_label();
1864

    
1865
                tcg_gen_andi_tl(t0, t0, 0x3f);
1866
                tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);
1867
                {
1868
                    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_TL);
1869

    
1870
                    tcg_gen_movi_tl(r_tmp1, 0x40);
1871
                    tcg_gen_sub_tl(r_tmp1, r_tmp1, t0);
1872
                    tcg_gen_shl_tl(r_tmp1, t1, r_tmp1);
1873
                    tcg_gen_shr_tl(t0, t1, t0);
1874
                    tcg_gen_or_tl(t0, t0, r_tmp1);
1875
                    tcg_temp_free(r_tmp1);
1876
                    tcg_gen_br(l2);
1877
                }
1878
                gen_set_label(l1);
1879
                tcg_gen_mov_tl(t0, t1);
1880
                gen_set_label(l2);
1881
                opn = "drotrv";
1882
            } else {
1883
                tcg_gen_andi_tl(t0, t0, 0x3f);
1884
                tcg_gen_shr_tl(t0, t1, t0);
1885
                opn = "dsrlv";
1886
            }
1887
            break;
1888
        default:
1889
            MIPS_INVAL("invalid dsrlv flag");
1890
            generate_exception(ctx, EXCP_RI);
1891
            break;
1892
        }
1893
        break;
1894
#endif
1895
    default:
1896
        MIPS_INVAL(opn);
1897
        generate_exception(ctx, EXCP_RI);
1898
        goto out;
1899
    }
1900
    gen_store_gpr(t0, rd);
1901
 print:
1902
    MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1903
 out:
1904
    tcg_temp_free(t0);
1905
    tcg_temp_free(t1);
1906
}
1907

    
1908
/* Arithmetic on HI/LO registers */
1909
static void gen_HILO (DisasContext *ctx, uint32_t opc, int reg)
1910
{
1911
    const char *opn = "hilo";
1912
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
1913

    
1914
    if (reg == 0 && (opc == OPC_MFHI || opc == OPC_MFLO)) {
1915
        /* Treat as NOP. */
1916
        MIPS_DEBUG("NOP");
1917
        goto out;
1918
    }
1919
    switch (opc) {
1920
    case OPC_MFHI:
1921
        gen_load_HI(t0, 0);
1922
        gen_store_gpr(t0, reg);
1923
        opn = "mfhi";
1924
        break;
1925
    case OPC_MFLO:
1926
        gen_load_LO(t0, 0);
1927
        gen_store_gpr(t0, reg);
1928
        opn = "mflo";
1929
        break;
1930
    case OPC_MTHI:
1931
        gen_load_gpr(t0, reg);
1932
        gen_store_HI(t0, 0);
1933
        opn = "mthi";
1934
        break;
1935
    case OPC_MTLO:
1936
        gen_load_gpr(t0, reg);
1937
        gen_store_LO(t0, 0);
1938
        opn = "mtlo";
1939
        break;
1940
    default:
1941
        MIPS_INVAL(opn);
1942
        generate_exception(ctx, EXCP_RI);
1943
        goto out;
1944
    }
1945
    MIPS_DEBUG("%s %s", opn, regnames[reg]);
1946
 out:
1947
    tcg_temp_free(t0);
1948
}
1949

    
1950
static void gen_muldiv (DisasContext *ctx, uint32_t opc,
1951
                        int rs, int rt)
1952
{
1953
    const char *opn = "mul/div";
1954
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
1955
    TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
1956

    
1957
    gen_load_gpr(t0, rs);
1958
    gen_load_gpr(t1, rt);
1959
    switch (opc) {
1960
    case OPC_DIV:
1961
        {
1962
            int l1 = gen_new_label();
1963

    
1964
            tcg_gen_ext32s_tl(t0, t0);
1965
            tcg_gen_ext32s_tl(t1, t1);
1966
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
1967
            {
1968
                TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
1969
                TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
1970
                TCGv r_tmp3 = tcg_temp_new(TCG_TYPE_I64);
1971

    
1972
                tcg_gen_ext_tl_i64(r_tmp1, t0);
1973
                tcg_gen_ext_tl_i64(r_tmp2, t1);
1974
                tcg_gen_div_i64(r_tmp3, r_tmp1, r_tmp2);
1975
                tcg_gen_rem_i64(r_tmp2, r_tmp1, r_tmp2);
1976
                tcg_gen_trunc_i64_tl(t0, r_tmp3);
1977
                tcg_gen_trunc_i64_tl(t1, r_tmp2);
1978
                tcg_temp_free(r_tmp1);
1979
                tcg_temp_free(r_tmp2);
1980
                tcg_temp_free(r_tmp3);
1981
                tcg_gen_ext32s_tl(t0, t0);
1982
                tcg_gen_ext32s_tl(t1, t1);
1983
                gen_store_LO(t0, 0);
1984
                gen_store_HI(t1, 0);
1985
            }
1986
            gen_set_label(l1);
1987
        }
1988
        opn = "div";
1989
        break;
1990
    case OPC_DIVU:
1991
        {
1992
            int l1 = gen_new_label();
1993

    
1994
            tcg_gen_ext32s_tl(t1, t1);
1995
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
1996
            {
1997
                TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
1998
                TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
1999
                TCGv r_tmp3 = tcg_temp_new(TCG_TYPE_I32);
2000

    
2001
                tcg_gen_trunc_tl_i32(r_tmp1, t0);
2002
                tcg_gen_trunc_tl_i32(r_tmp2, t1);
2003
                tcg_gen_divu_i32(r_tmp3, r_tmp1, r_tmp2);
2004
                tcg_gen_remu_i32(r_tmp1, r_tmp1, r_tmp2);
2005
                tcg_gen_ext_i32_tl(t0, r_tmp3);
2006
                tcg_gen_ext_i32_tl(t1, r_tmp1);
2007
                tcg_temp_free(r_tmp1);
2008
                tcg_temp_free(r_tmp2);
2009
                tcg_temp_free(r_tmp3);
2010
                gen_store_LO(t0, 0);
2011
                gen_store_HI(t1, 0);
2012
            }
2013
            gen_set_label(l1);
2014
        }
2015
        opn = "divu";
2016
        break;
2017
    case OPC_MULT:
2018
        {
2019
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
2020
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
2021

    
2022
            tcg_gen_ext32s_tl(t0, t0);
2023
            tcg_gen_ext32s_tl(t1, t1);
2024
            tcg_gen_ext_tl_i64(r_tmp1, t0);
2025
            tcg_gen_ext_tl_i64(r_tmp2, t1);
2026
            tcg_gen_mul_i64(r_tmp1, r_tmp1, r_tmp2);
2027
            tcg_temp_free(r_tmp2);
2028
            tcg_gen_trunc_i64_tl(t0, r_tmp1);
2029
            tcg_gen_shri_i64(r_tmp1, r_tmp1, 32);
2030
            tcg_gen_trunc_i64_tl(t1, r_tmp1);
2031
            tcg_temp_free(r_tmp1);
2032
            tcg_gen_ext32s_tl(t0, t0);
2033
            tcg_gen_ext32s_tl(t1, t1);
2034
            gen_store_LO(t0, 0);
2035
            gen_store_HI(t1, 0);
2036
        }
2037
        opn = "mult";
2038
        break;
2039
    case OPC_MULTU:
2040
        {
2041
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
2042
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
2043

    
2044
            tcg_gen_ext32u_tl(t0, t0);
2045
            tcg_gen_ext32u_tl(t1, t1);
2046
            tcg_gen_extu_tl_i64(r_tmp1, t0);
2047
            tcg_gen_extu_tl_i64(r_tmp2, t1);
2048
            tcg_gen_mul_i64(r_tmp1, r_tmp1, r_tmp2);
2049
            tcg_temp_free(r_tmp2);
2050
            tcg_gen_trunc_i64_tl(t0, r_tmp1);
2051
            tcg_gen_shri_i64(r_tmp1, r_tmp1, 32);
2052
            tcg_gen_trunc_i64_tl(t1, r_tmp1);
2053
            tcg_temp_free(r_tmp1);
2054
            tcg_gen_ext32s_tl(t0, t0);
2055
            tcg_gen_ext32s_tl(t1, t1);
2056
            gen_store_LO(t0, 0);
2057
            gen_store_HI(t1, 0);
2058
        }
2059
        opn = "multu";
2060
        break;
2061
#if defined(TARGET_MIPS64)
2062
    case OPC_DDIV:
2063
        {
2064
            int l1 = gen_new_label();
2065

    
2066
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2067
            {
2068
                int l2 = gen_new_label();
2069

    
2070
                tcg_gen_brcondi_tl(TCG_COND_NE, t0, -1LL << 63, l2);
2071
                tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1LL, l2);
2072
                {
2073
                    tcg_gen_movi_tl(t1, 0);
2074
                    gen_store_LO(t0, 0);
2075
                    gen_store_HI(t1, 0);
2076
                    tcg_gen_br(l1);
2077
                }
2078
                gen_set_label(l2);
2079
                {
2080
                    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
2081
                    TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
2082

    
2083
                    tcg_gen_div_i64(r_tmp1, t0, t1);
2084
                    tcg_gen_rem_i64(r_tmp2, t0, t1);
2085
                    gen_store_LO(r_tmp1, 0);
2086
                    gen_store_HI(r_tmp2, 0);
2087
                    tcg_temp_free(r_tmp1);
2088
                    tcg_temp_free(r_tmp2);
2089
                }
2090
            }
2091
            gen_set_label(l1);
2092
        }
2093
        opn = "ddiv";
2094
        break;
2095
    case OPC_DDIVU:
2096
        {
2097
            int l1 = gen_new_label();
2098

    
2099
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2100
            {
2101
                TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
2102
                TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
2103

    
2104
                tcg_gen_divu_i64(r_tmp1, t0, t1);
2105
                tcg_gen_remu_i64(r_tmp2, t0, t1);
2106
                tcg_temp_free(r_tmp1);
2107
                tcg_temp_free(r_tmp2);
2108
                gen_store_LO(r_tmp1, 0);
2109
                gen_store_HI(r_tmp2, 0);
2110
            }
2111
            gen_set_label(l1);
2112
        }
2113
        opn = "ddivu";
2114
        break;
2115
    case OPC_DMULT:
2116
        tcg_gen_helper_0_2(do_dmult, t0, t1);
2117
        opn = "dmult";
2118
        break;
2119
    case OPC_DMULTU:
2120
        tcg_gen_helper_0_2(do_dmultu, t0, t1);
2121
        opn = "dmultu";
2122
        break;
2123
#endif
2124
    case OPC_MADD:
2125
        {
2126
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
2127
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
2128
            TCGv r_tmp3 = tcg_temp_new(TCG_TYPE_I64);
2129

    
2130
            tcg_gen_ext32s_tl(t0, t0);
2131
            tcg_gen_ext32s_tl(t1, t1);
2132
            tcg_gen_ext_tl_i64(r_tmp1, t0);
2133
            tcg_gen_ext_tl_i64(r_tmp2, t1);
2134
            tcg_gen_mul_i64(r_tmp1, r_tmp1, r_tmp2);
2135
            gen_load_LO(t0, 0);
2136
            gen_load_HI(t1, 0);
2137
            tcg_gen_extu_tl_i64(r_tmp2, t0);
2138
            tcg_gen_extu_tl_i64(r_tmp3, t1);
2139
            tcg_gen_shli_i64(r_tmp3, r_tmp3, 32);
2140
            tcg_gen_or_i64(r_tmp2, r_tmp2, r_tmp3);
2141
            tcg_temp_free(r_tmp3);
2142
            tcg_gen_add_i64(r_tmp1, r_tmp1, r_tmp2);
2143
            tcg_temp_free(r_tmp2);
2144
            tcg_gen_trunc_i64_tl(t0, r_tmp1);
2145
            tcg_gen_shri_i64(r_tmp1, r_tmp1, 32);
2146
            tcg_gen_trunc_i64_tl(t1, r_tmp1);
2147
            tcg_temp_free(r_tmp1);
2148
            tcg_gen_ext32s_tl(t0, t0);
2149
            tcg_gen_ext32s_tl(t1, t1);
2150
            gen_store_LO(t0, 0);
2151
            gen_store_HI(t1, 0);
2152
        }
2153
        opn = "madd";
2154
        break;
2155
    case OPC_MADDU:
2156
       {
2157
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
2158
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
2159
            TCGv r_tmp3 = tcg_temp_new(TCG_TYPE_I64);
2160

    
2161
            tcg_gen_ext32u_tl(t0, t0);
2162
            tcg_gen_ext32u_tl(t1, t1);
2163
            tcg_gen_extu_tl_i64(r_tmp1, t0);
2164
            tcg_gen_extu_tl_i64(r_tmp2, t1);
2165
            tcg_gen_mul_i64(r_tmp1, r_tmp1, r_tmp2);
2166
            gen_load_LO(t0, 0);
2167
            gen_load_HI(t1, 0);
2168
            tcg_gen_extu_tl_i64(r_tmp2, t0);
2169
            tcg_gen_extu_tl_i64(r_tmp3, t1);
2170
            tcg_gen_shli_i64(r_tmp3, r_tmp3, 32);
2171
            tcg_gen_or_i64(r_tmp2, r_tmp2, r_tmp3);
2172
            tcg_temp_free(r_tmp3);
2173
            tcg_gen_add_i64(r_tmp1, r_tmp1, r_tmp2);
2174
            tcg_temp_free(r_tmp2);
2175
            tcg_gen_trunc_i64_tl(t0, r_tmp1);
2176
            tcg_gen_shri_i64(r_tmp1, r_tmp1, 32);
2177
            tcg_gen_trunc_i64_tl(t1, r_tmp1);
2178
            tcg_temp_free(r_tmp1);
2179
            tcg_gen_ext32s_tl(t0, t0);
2180
            tcg_gen_ext32s_tl(t1, t1);
2181
            gen_store_LO(t0, 0);
2182
            gen_store_HI(t1, 0);
2183
        }
2184
        opn = "maddu";
2185
        break;
2186
    case OPC_MSUB:
2187
        {
2188
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
2189
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
2190
            TCGv r_tmp3 = tcg_temp_new(TCG_TYPE_I64);
2191

    
2192
            tcg_gen_ext32s_tl(t0, t0);
2193
            tcg_gen_ext32s_tl(t1, t1);
2194
            tcg_gen_ext_tl_i64(r_tmp1, t0);
2195
            tcg_gen_ext_tl_i64(r_tmp2, t1);
2196
            tcg_gen_mul_i64(r_tmp1, r_tmp1, r_tmp2);
2197
            gen_load_LO(t0, 0);
2198
            gen_load_HI(t1, 0);
2199
            tcg_gen_extu_tl_i64(r_tmp2, t0);
2200
            tcg_gen_extu_tl_i64(r_tmp3, t1);
2201
            tcg_gen_shli_i64(r_tmp3, r_tmp3, 32);
2202
            tcg_gen_or_i64(r_tmp2, r_tmp2, r_tmp3);
2203
            tcg_temp_free(r_tmp3);
2204
            tcg_gen_sub_i64(r_tmp1, r_tmp1, r_tmp2);
2205
            tcg_temp_free(r_tmp2);
2206
            tcg_gen_trunc_i64_tl(t0, r_tmp1);
2207
            tcg_gen_shri_i64(r_tmp1, r_tmp1, 32);
2208
            tcg_gen_trunc_i64_tl(t1, r_tmp1);
2209
            tcg_temp_free(r_tmp1);
2210
            tcg_gen_ext32s_tl(t0, t0);
2211
            tcg_gen_ext32s_tl(t1, t1);
2212
            gen_store_LO(t0, 0);
2213
            gen_store_HI(t1, 0);
2214
        }
2215
        opn = "msub";
2216
        break;
2217
    case OPC_MSUBU:
2218
        {
2219
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I64);
2220
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I64);
2221
            TCGv r_tmp3 = tcg_temp_new(TCG_TYPE_I64);
2222

    
2223
            tcg_gen_ext32u_tl(t0, t0);
2224
            tcg_gen_ext32u_tl(t1, t1);
2225
            tcg_gen_extu_tl_i64(r_tmp1, t0);
2226
            tcg_gen_extu_tl_i64(r_tmp2, t1);
2227
            tcg_gen_mul_i64(r_tmp1, r_tmp1, r_tmp2);
2228
            gen_load_LO(t0, 0);
2229
            gen_load_HI(t1, 0);
2230
            tcg_gen_extu_tl_i64(r_tmp2, t0);
2231
            tcg_gen_extu_tl_i64(r_tmp3, t1);
2232
            tcg_gen_shli_i64(r_tmp3, r_tmp3, 32);
2233
            tcg_gen_or_i64(r_tmp2, r_tmp2, r_tmp3);
2234
            tcg_temp_free(r_tmp3);
2235
            tcg_gen_sub_i64(r_tmp1, r_tmp1, r_tmp2);
2236
            tcg_temp_free(r_tmp2);
2237
            tcg_gen_trunc_i64_tl(t0, r_tmp1);
2238
            tcg_gen_shri_i64(r_tmp1, r_tmp1, 32);
2239
            tcg_gen_trunc_i64_tl(t1, r_tmp1);
2240
            tcg_temp_free(r_tmp1);
2241
            tcg_gen_ext32s_tl(t0, t0);
2242
            tcg_gen_ext32s_tl(t1, t1);
2243
            gen_store_LO(t0, 0);
2244
            gen_store_HI(t1, 0);
2245
        }
2246
        opn = "msubu";
2247
        break;
2248
    default:
2249
        MIPS_INVAL(opn);
2250
        generate_exception(ctx, EXCP_RI);
2251
        goto out;
2252
    }
2253
    MIPS_DEBUG("%s %s %s", opn, regnames[rs], regnames[rt]);
2254
 out:
2255
    tcg_temp_free(t0);
2256
    tcg_temp_free(t1);
2257
}
2258

    
2259
static void gen_mul_vr54xx (DisasContext *ctx, uint32_t opc,
2260
                            int rd, int rs, int rt)
2261
{
2262
    const char *opn = "mul vr54xx";
2263
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
2264
    TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
2265

    
2266
    gen_load_gpr(t0, rs);
2267
    gen_load_gpr(t1, rt);
2268

    
2269
    switch (opc) {
2270
    case OPC_VR54XX_MULS:
2271
        tcg_gen_helper_1_2(do_muls, t0, t0, t1);
2272
        opn = "muls";
2273
        break;
2274
    case OPC_VR54XX_MULSU:
2275
        tcg_gen_helper_1_2(do_mulsu, t0, t0, t1);
2276
        opn = "mulsu";
2277
        break;
2278
    case OPC_VR54XX_MACC:
2279
        tcg_gen_helper_1_2(do_macc, t0, t0, t1);
2280
        opn = "macc";
2281
        break;
2282
    case OPC_VR54XX_MACCU:
2283
        tcg_gen_helper_1_2(do_maccu, t0, t0, t1);
2284
        opn = "maccu";
2285
        break;
2286
    case OPC_VR54XX_MSAC:
2287
        tcg_gen_helper_1_2(do_msac, t0, t0, t1);
2288
        opn = "msac";
2289
        break;
2290
    case OPC_VR54XX_MSACU:
2291
        tcg_gen_helper_1_2(do_msacu, t0, t0, t1);
2292
        opn = "msacu";
2293
        break;
2294
    case OPC_VR54XX_MULHI:
2295
        tcg_gen_helper_1_2(do_mulhi, t0, t0, t1);
2296
        opn = "mulhi";
2297
        break;
2298
    case OPC_VR54XX_MULHIU:
2299
        tcg_gen_helper_1_2(do_mulhiu, t0, t0, t1);
2300
        opn = "mulhiu";
2301
        break;
2302
    case OPC_VR54XX_MULSHI:
2303
        tcg_gen_helper_1_2(do_mulshi, t0, t0, t1);
2304
        opn = "mulshi";
2305
        break;
2306
    case OPC_VR54XX_MULSHIU:
2307
        tcg_gen_helper_1_2(do_mulshiu, t0, t0, t1);
2308
        opn = "mulshiu";
2309
        break;
2310
    case OPC_VR54XX_MACCHI:
2311
        tcg_gen_helper_1_2(do_macchi, t0, t0, t1);
2312
        opn = "macchi";
2313
        break;
2314
    case OPC_VR54XX_MACCHIU:
2315
        tcg_gen_helper_1_2(do_macchiu, t0, t0, t1);
2316
        opn = "macchiu";
2317
        break;
2318
    case OPC_VR54XX_MSACHI:
2319
        tcg_gen_helper_1_2(do_msachi, t0, t0, t1);
2320
        opn = "msachi";
2321
        break;
2322
    case OPC_VR54XX_MSACHIU:
2323
        tcg_gen_helper_1_2(do_msachiu, t0, t0, t1);
2324
        opn = "msachiu";
2325
        break;
2326
    default:
2327
        MIPS_INVAL("mul vr54xx");
2328
        generate_exception(ctx, EXCP_RI);
2329
        goto out;
2330
    }
2331
    gen_store_gpr(t0, rd);
2332
    MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
2333

    
2334
 out:
2335
    tcg_temp_free(t0);
2336
    tcg_temp_free(t1);
2337
}
2338

    
2339
static void gen_cl (DisasContext *ctx, uint32_t opc,
2340
                    int rd, int rs)
2341
{
2342
    const char *opn = "CLx";
2343
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
2344

    
2345
    if (rd == 0) {
2346
        /* Treat as NOP. */
2347
        MIPS_DEBUG("NOP");
2348
        goto out;
2349
    }
2350
    gen_load_gpr(t0, rs);
2351
    switch (opc) {
2352
    case OPC_CLO:
2353
        tcg_gen_helper_1_1(do_clo, t0, t0);
2354
        opn = "clo";
2355
        break;
2356
    case OPC_CLZ:
2357
        tcg_gen_helper_1_1(do_clz, t0, t0);
2358
        opn = "clz";
2359
        break;
2360
#if defined(TARGET_MIPS64)
2361
    case OPC_DCLO:
2362
        tcg_gen_helper_1_1(do_dclo, t0, t0);
2363
        opn = "dclo";
2364
        break;
2365
    case OPC_DCLZ:
2366
        tcg_gen_helper_1_1(do_dclz, t0, t0);
2367
        opn = "dclz";
2368
        break;
2369
#endif
2370
    default:
2371
        MIPS_INVAL(opn);
2372
        generate_exception(ctx, EXCP_RI);
2373
        goto out;
2374
    }
2375
    gen_store_gpr(t0, rd);
2376
    MIPS_DEBUG("%s %s, %s", opn, regnames[rd], regnames[rs]);
2377

    
2378
 out:
2379
    tcg_temp_free(t0);
2380
}
2381

    
2382
/* Traps */
2383
static void gen_trap (DisasContext *ctx, uint32_t opc,
2384
                      int rs, int rt, int16_t imm)
2385
{
2386
    int cond;
2387
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
2388
    TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
2389

    
2390
    cond = 0;
2391
    /* Load needed operands */
2392
    switch (opc) {
2393
    case OPC_TEQ:
2394
    case OPC_TGE:
2395
    case OPC_TGEU:
2396
    case OPC_TLT:
2397
    case OPC_TLTU:
2398
    case OPC_TNE:
2399
        /* Compare two registers */
2400
        if (rs != rt) {
2401
            gen_load_gpr(t0, rs);
2402
            gen_load_gpr(t1, rt);
2403
            cond = 1;
2404
        }
2405
        break;
2406
    case OPC_TEQI:
2407
    case OPC_TGEI:
2408
    case OPC_TGEIU:
2409
    case OPC_TLTI:
2410
    case OPC_TLTIU:
2411
    case OPC_TNEI:
2412
        /* Compare register to immediate */
2413
        if (rs != 0 || imm != 0) {
2414
            gen_load_gpr(t0, rs);
2415
            tcg_gen_movi_tl(t1, (int32_t)imm);
2416
            cond = 1;
2417
        }
2418
        break;
2419
    }
2420
    if (cond == 0) {
2421
        switch (opc) {
2422
        case OPC_TEQ:   /* rs == rs */
2423
        case OPC_TEQI:  /* r0 == 0  */
2424
        case OPC_TGE:   /* rs >= rs */
2425
        case OPC_TGEI:  /* r0 >= 0  */
2426
        case OPC_TGEU:  /* rs >= rs unsigned */
2427
        case OPC_TGEIU: /* r0 >= 0  unsigned */
2428
            /* Always trap */
2429
            tcg_gen_movi_tl(t0, 1);
2430
            break;
2431
        case OPC_TLT:   /* rs < rs           */
2432
        case OPC_TLTI:  /* r0 < 0            */
2433
        case OPC_TLTU:  /* rs < rs unsigned  */
2434
        case OPC_TLTIU: /* r0 < 0  unsigned  */
2435
        case OPC_TNE:   /* rs != rs          */
2436
        case OPC_TNEI:  /* r0 != 0           */
2437
            /* Never trap: treat as NOP. */
2438
            goto out;
2439
        default:
2440
            MIPS_INVAL("trap");
2441
            generate_exception(ctx, EXCP_RI);
2442
            goto out;
2443
        }
2444
    } else {
2445
        switch (opc) {
2446
        case OPC_TEQ:
2447
        case OPC_TEQI:
2448
            gen_op_eq(t0, t1);
2449
            break;
2450
        case OPC_TGE:
2451
        case OPC_TGEI:
2452
            gen_op_ge(t0, t1);
2453
            break;
2454
        case OPC_TGEU:
2455
        case OPC_TGEIU:
2456
            gen_op_geu(t0, t1);
2457
            break;
2458
        case OPC_TLT:
2459
        case OPC_TLTI:
2460
            gen_op_lt(t0, t1);
2461
            break;
2462
        case OPC_TLTU:
2463
        case OPC_TLTIU:
2464
            gen_op_ltu(t0, t1);
2465
            break;
2466
        case OPC_TNE:
2467
        case OPC_TNEI:
2468
            gen_op_ne(t0, t1);
2469
            break;
2470
        default:
2471
            MIPS_INVAL("trap");
2472
            generate_exception(ctx, EXCP_RI);
2473
            goto out;
2474
        }
2475
    }
2476
    save_cpu_state(ctx, 1);
2477
    {
2478
        int l1 = gen_new_label();
2479

    
2480
        tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);
2481
        tcg_gen_helper_0_i(do_raise_exception, EXCP_TRAP);
2482
        gen_set_label(l1);
2483
    }
2484
    ctx->bstate = BS_STOP;
2485
 out:
2486
    tcg_temp_free(t0);
2487
    tcg_temp_free(t1);
2488
}
2489

    
2490
static always_inline void gen_goto_tb(DisasContext *ctx, int n, target_ulong dest)
2491
{
2492
    TranslationBlock *tb;
2493
    tb = ctx->tb;
2494
    if ((tb->pc & TARGET_PAGE_MASK) == (dest & TARGET_PAGE_MASK)) {
2495
        tcg_gen_goto_tb(n);
2496
        gen_save_pc(dest);
2497
        tcg_gen_exit_tb((long)tb + n);
2498
    } else {
2499
        gen_save_pc(dest);
2500
        tcg_gen_exit_tb(0);
2501
    }
2502
}
2503

    
2504
/* Branches (before delay slot) */
2505
static void gen_compute_branch (DisasContext *ctx, uint32_t opc,
2506
                                int rs, int rt, int32_t offset)
2507
{
2508
    target_ulong btarget = -1;
2509
    int blink = 0;
2510
    int bcond = 0;
2511
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
2512
    TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
2513

    
2514
    if (ctx->hflags & MIPS_HFLAG_BMASK) {
2515
#ifdef MIPS_DEBUG_DISAS
2516
        if (loglevel & CPU_LOG_TB_IN_ASM) {
2517
            fprintf(logfile,
2518
                    "Branch in delay slot at PC 0x" TARGET_FMT_lx "\n",
2519
                    ctx->pc);
2520
        }
2521
#endif
2522
        generate_exception(ctx, EXCP_RI);
2523
        goto out;
2524
    }
2525

    
2526
    /* Load needed operands */
2527
    switch (opc) {
2528
    case OPC_BEQ:
2529
    case OPC_BEQL:
2530
    case OPC_BNE:
2531
    case OPC_BNEL:
2532
        /* Compare two registers */
2533
        if (rs != rt) {
2534
            gen_load_gpr(t0, rs);
2535
            gen_load_gpr(t1, rt);
2536
            bcond = 1;
2537
        }
2538
        btarget = ctx->pc + 4 + offset;
2539
        break;
2540
    case OPC_BGEZ:
2541
    case OPC_BGEZAL:
2542
    case OPC_BGEZALL:
2543
    case OPC_BGEZL:
2544
    case OPC_BGTZ:
2545
    case OPC_BGTZL:
2546
    case OPC_BLEZ:
2547
    case OPC_BLEZL:
2548
    case OPC_BLTZ:
2549
    case OPC_BLTZAL:
2550
    case OPC_BLTZALL:
2551
    case OPC_BLTZL:
2552
        /* Compare to zero */
2553
        if (rs != 0) {
2554
            gen_load_gpr(t0, rs);
2555
            bcond = 1;
2556
        }
2557
        btarget = ctx->pc + 4 + offset;
2558
        break;
2559
    case OPC_J:
2560
    case OPC_JAL:
2561
        /* Jump to immediate */
2562
        btarget = ((ctx->pc + 4) & (int32_t)0xF0000000) | (uint32_t)offset;
2563
        break;
2564
    case OPC_JR:
2565
    case OPC_JALR:
2566
        /* Jump to register */
2567
        if (offset != 0 && offset != 16) {
2568
            /* Hint = 0 is JR/JALR, hint 16 is JR.HB/JALR.HB, the
2569
               others are reserved. */
2570
            MIPS_INVAL("jump hint");
2571
            generate_exception(ctx, EXCP_RI);
2572
            goto out;
2573
        }
2574
        gen_save_breg_target(rs);
2575
        break;
2576
    default:
2577
        MIPS_INVAL("branch/jump");
2578
        generate_exception(ctx, EXCP_RI);
2579
        goto out;
2580
    }
2581
    if (bcond == 0) {
2582
        /* No condition to be computed */
2583
        switch (opc) {
2584
        case OPC_BEQ:     /* rx == rx        */
2585
        case OPC_BEQL:    /* rx == rx likely */
2586
        case OPC_BGEZ:    /* 0 >= 0          */
2587
        case OPC_BGEZL:   /* 0 >= 0 likely   */
2588
        case OPC_BLEZ:    /* 0 <= 0          */
2589
        case OPC_BLEZL:   /* 0 <= 0 likely   */
2590
            /* Always take */
2591
            ctx->hflags |= MIPS_HFLAG_B;
2592
            MIPS_DEBUG("balways");
2593
            break;
2594
        case OPC_BGEZAL:  /* 0 >= 0          */
2595
        case OPC_BGEZALL: /* 0 >= 0 likely   */
2596
            /* Always take and link */
2597
            blink = 31;
2598
            ctx->hflags |= MIPS_HFLAG_B;
2599
            MIPS_DEBUG("balways and link");
2600
            break;
2601
        case OPC_BNE:     /* rx != rx        */
2602
        case OPC_BGTZ:    /* 0 > 0           */
2603
        case OPC_BLTZ:    /* 0 < 0           */
2604
            /* Treat as NOP. */
2605
            MIPS_DEBUG("bnever (NOP)");
2606
            goto out;
2607
        case OPC_BLTZAL:  /* 0 < 0           */
2608
            tcg_gen_movi_tl(t0, ctx->pc + 8);
2609
            gen_store_gpr(t0, 31);
2610
            MIPS_DEBUG("bnever and link");
2611
            goto out;
2612
        case OPC_BLTZALL: /* 0 < 0 likely */
2613
            tcg_gen_movi_tl(t0, ctx->pc + 8);
2614
            gen_store_gpr(t0, 31);
2615
            /* Skip the instruction in the delay slot */
2616
            MIPS_DEBUG("bnever, link and skip");
2617
            ctx->pc += 4;
2618
            goto out;
2619
        case OPC_BNEL:    /* rx != rx likely */
2620
        case OPC_BGTZL:   /* 0 > 0 likely */
2621
        case OPC_BLTZL:   /* 0 < 0 likely */
2622
            /* Skip the instruction in the delay slot */
2623
            MIPS_DEBUG("bnever and skip");
2624
            ctx->pc += 4;
2625
            goto out;
2626
        case OPC_J:
2627
            ctx->hflags |= MIPS_HFLAG_B;
2628
            MIPS_DEBUG("j " TARGET_FMT_lx, btarget);
2629
            break;
2630
        case OPC_JAL:
2631
            blink = 31;
2632
            ctx->hflags |= MIPS_HFLAG_B;
2633
            MIPS_DEBUG("jal " TARGET_FMT_lx, btarget);
2634
            break;
2635
        case OPC_JR:
2636
            ctx->hflags |= MIPS_HFLAG_BR;
2637
            MIPS_DEBUG("jr %s", regnames[rs]);
2638
            break;
2639
        case OPC_JALR:
2640
            blink = rt;
2641
            ctx->hflags |= MIPS_HFLAG_BR;
2642
            MIPS_DEBUG("jalr %s, %s", regnames[rt], regnames[rs]);
2643
            break;
2644
        default:
2645
            MIPS_INVAL("branch/jump");
2646
            generate_exception(ctx, EXCP_RI);
2647
            goto out;
2648
        }
2649
    } else {
2650
        switch (opc) {
2651
        case OPC_BEQ:
2652
            gen_op_eq(t0, t1);
2653
            MIPS_DEBUG("beq %s, %s, " TARGET_FMT_lx,
2654
                       regnames[rs], regnames[rt], btarget);
2655
            goto not_likely;
2656
        case OPC_BEQL:
2657
            gen_op_eq(t0, t1);
2658
            MIPS_DEBUG("beql %s, %s, " TARGET_FMT_lx,
2659
                       regnames[rs], regnames[rt], btarget);
2660
            goto likely;
2661
        case OPC_BNE:
2662
            gen_op_ne(t0, t1);
2663
            MIPS_DEBUG("bne %s, %s, " TARGET_FMT_lx,
2664
                       regnames[rs], regnames[rt], btarget);
2665
            goto not_likely;
2666
        case OPC_BNEL:
2667
            gen_op_ne(t0, t1);
2668
            MIPS_DEBUG("bnel %s, %s, " TARGET_FMT_lx,
2669
                       regnames[rs], regnames[rt], btarget);
2670
            goto likely;
2671
        case OPC_BGEZ:
2672
            gen_op_gez(t0);
2673
            MIPS_DEBUG("bgez %s, " TARGET_FMT_lx, regnames[rs], btarget);
2674
            goto not_likely;
2675
        case OPC_BGEZL:
2676
            gen_op_gez(t0);
2677
            MIPS_DEBUG("bgezl %s, " TARGET_FMT_lx, regnames[rs], btarget);
2678
            goto likely;
2679
        case OPC_BGEZAL:
2680
            gen_op_gez(t0);
2681
            MIPS_DEBUG("bgezal %s, " TARGET_FMT_lx, regnames[rs], btarget);
2682
            blink = 31;
2683
            goto not_likely;
2684
        case OPC_BGEZALL:
2685
            gen_op_gez(t0);
2686
            blink = 31;
2687
            MIPS_DEBUG("bgezall %s, " TARGET_FMT_lx, regnames[rs], btarget);
2688
            goto likely;
2689
        case OPC_BGTZ:
2690
            gen_op_gtz(t0);
2691
            MIPS_DEBUG("bgtz %s, " TARGET_FMT_lx, regnames[rs], btarget);
2692
            goto not_likely;
2693
        case OPC_BGTZL:
2694
            gen_op_gtz(t0);
2695
            MIPS_DEBUG("bgtzl %s, " TARGET_FMT_lx, regnames[rs], btarget);
2696
            goto likely;
2697
        case OPC_BLEZ:
2698
            gen_op_lez(t0);
2699
            MIPS_DEBUG("blez %s, " TARGET_FMT_lx, regnames[rs], btarget);
2700
            goto not_likely;
2701
        case OPC_BLEZL:
2702
            gen_op_lez(t0);
2703
            MIPS_DEBUG("blezl %s, " TARGET_FMT_lx, regnames[rs], btarget);
2704
            goto likely;
2705
        case OPC_BLTZ:
2706
            gen_op_ltz(t0);
2707
            MIPS_DEBUG("bltz %s, " TARGET_FMT_lx, regnames[rs], btarget);
2708
            goto not_likely;
2709
        case OPC_BLTZL:
2710
            gen_op_ltz(t0);
2711
            MIPS_DEBUG("bltzl %s, " TARGET_FMT_lx, regnames[rs], btarget);
2712
            goto likely;
2713
        case OPC_BLTZAL:
2714
            gen_op_ltz(t0);
2715
            blink = 31;
2716
            MIPS_DEBUG("bltzal %s, " TARGET_FMT_lx, regnames[rs], btarget);
2717
        not_likely:
2718
            ctx->hflags |= MIPS_HFLAG_BC;
2719
            tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, bcond));
2720
            break;
2721
        case OPC_BLTZALL:
2722
            gen_op_ltz(t0);
2723
            blink = 31;
2724
            MIPS_DEBUG("bltzall %s, " TARGET_FMT_lx, regnames[rs], btarget);
2725
        likely:
2726
            ctx->hflags |= MIPS_HFLAG_BL;
2727
            tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, bcond));
2728
            break;
2729
        default:
2730
            MIPS_INVAL("conditional branch/jump");
2731
            generate_exception(ctx, EXCP_RI);
2732
            goto out;
2733
        }
2734
    }
2735
    MIPS_DEBUG("enter ds: link %d cond %02x target " TARGET_FMT_lx,
2736
               blink, ctx->hflags, btarget);
2737

    
2738
    ctx->btarget = btarget;
2739
    if (blink > 0) {
2740
        tcg_gen_movi_tl(t0, ctx->pc + 8);
2741
        gen_store_gpr(t0, blink);
2742
    }
2743

    
2744
 out:
2745
    tcg_temp_free(t0);
2746
    tcg_temp_free(t1);
2747
}
2748

    
2749
/* special3 bitfield operations */
2750
static void gen_bitops (DisasContext *ctx, uint32_t opc, int rt,
2751
                       int rs, int lsb, int msb)
2752
{
2753
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
2754
    TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
2755

    
2756
    gen_load_gpr(t1, rs);
2757
    switch (opc) {
2758
    case OPC_EXT:
2759
        if (lsb + msb > 31)
2760
            goto fail;
2761
        tcg_gen_helper_1_1ii(do_ext, t0, t1, lsb, msb + 1);
2762
        break;
2763
#if defined(TARGET_MIPS64)
2764
    case OPC_DEXTM:
2765
        if (lsb + msb > 63)
2766
            goto fail;
2767
        tcg_gen_helper_1_1ii(do_dext, t0, t1, lsb, msb + 1 + 32);
2768
        break;
2769
    case OPC_DEXTU:
2770
        if (lsb + msb > 63)
2771
            goto fail;
2772
        tcg_gen_helper_1_1ii(do_dext, t0, t1, lsb + 32, msb + 1);
2773
        break;
2774
    case OPC_DEXT:
2775
        if (lsb + msb > 63)
2776
            goto fail;
2777
        tcg_gen_helper_1_1ii(do_dext, t0, t1, lsb, msb + 1);
2778
        break;
2779
#endif
2780
    case OPC_INS:
2781
        if (lsb > msb)
2782
            goto fail;
2783
        gen_load_gpr(t0, rt);
2784
        tcg_gen_helper_1_2ii(do_ins, t0, t0, t1, lsb, msb - lsb + 1);
2785
        break;
2786
#if defined(TARGET_MIPS64)
2787
    case OPC_DINSM:
2788
        if (lsb > msb)
2789
            goto fail;
2790
        gen_load_gpr(t0, rt);
2791
        tcg_gen_helper_1_2ii(do_dins, t0, t0, t1, lsb, msb - lsb + 1 + 32);
2792
        break;
2793
    case OPC_DINSU:
2794
        if (lsb > msb)
2795
            goto fail;
2796
        gen_load_gpr(t0, rt);
2797
        tcg_gen_helper_1_2ii(do_dins, t0, t0, t1, lsb + 32, msb - lsb + 1);
2798
        break;
2799
    case OPC_DINS:
2800
        if (lsb > msb)
2801
            goto fail;
2802
        gen_load_gpr(t0, rt);
2803
        tcg_gen_helper_1_2ii(do_dins, t0, t0, t1, lsb, msb - lsb + 1);
2804
        break;
2805
#endif
2806
    default:
2807
fail:
2808
        MIPS_INVAL("bitops");
2809
        generate_exception(ctx, EXCP_RI);
2810
        tcg_temp_free(t0);
2811
        tcg_temp_free(t1);
2812
        return;
2813
    }
2814
    gen_store_gpr(t0, rt);
2815
    tcg_temp_free(t0);
2816
    tcg_temp_free(t1);
2817
}
2818

    
2819
/* CP0 (MMU and control) */
2820
#ifndef CONFIG_USER_ONLY
2821
static inline void gen_mfc0_load32 (TCGv t, target_ulong off)
2822
{
2823
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_I32);
2824

    
2825
    tcg_gen_ld_i32(r_tmp, cpu_env, off);
2826
    tcg_gen_ext_i32_tl(t, r_tmp);
2827
    tcg_temp_free(r_tmp);
2828
}
2829

    
2830
static inline void gen_mfc0_load64 (TCGv t, target_ulong off)
2831
{
2832
    tcg_gen_ld_tl(t, cpu_env, off);
2833
    tcg_gen_ext32s_tl(t, t);
2834
}
2835

    
2836
static inline void gen_mtc0_store32 (TCGv t, target_ulong off)
2837
{
2838
    TCGv r_tmp = tcg_temp_new(TCG_TYPE_I32);
2839

    
2840
    tcg_gen_trunc_tl_i32(r_tmp, t);
2841
    tcg_gen_st_i32(r_tmp, cpu_env, off);
2842
    tcg_temp_free(r_tmp);
2843
}
2844

    
2845
static inline void gen_mtc0_store64 (TCGv t, target_ulong off)
2846
{
2847
    tcg_gen_ext32s_tl(t, t);
2848
    tcg_gen_st_tl(t, cpu_env, off);
2849
}
2850

    
2851
static void gen_mfc0 (CPUState *env, DisasContext *ctx, TCGv t0, int reg, int sel)
2852
{
2853
    const char *rn = "invalid";
2854

    
2855
    if (sel != 0)
2856
        check_insn(env, ctx, ISA_MIPS32);
2857

    
2858
    switch (reg) {
2859
    case 0:
2860
        switch (sel) {
2861
        case 0:
2862
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Index));
2863
            rn = "Index";
2864
            break;
2865
        case 1:
2866
            check_insn(env, ctx, ASE_MT);
2867
            tcg_gen_helper_1_0(do_mfc0_mvpcontrol, t0);
2868
            rn = "MVPControl";
2869
            break;
2870
        case 2:
2871
            check_insn(env, ctx, ASE_MT);
2872
            tcg_gen_helper_1_0(do_mfc0_mvpconf0, t0);
2873
            rn = "MVPConf0";
2874
            break;
2875
        case 3:
2876
            check_insn(env, ctx, ASE_MT);
2877
            tcg_gen_helper_1_0(do_mfc0_mvpconf1, t0);
2878
            rn = "MVPConf1";
2879
            break;
2880
        default:
2881
            goto die;
2882
        }
2883
        break;
2884
    case 1:
2885
        switch (sel) {
2886
        case 0:
2887
            tcg_gen_helper_1_0(do_mfc0_random, t0);
2888
            rn = "Random";
2889
            break;
2890
        case 1:
2891
            check_insn(env, ctx, ASE_MT);
2892
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEControl));
2893
            rn = "VPEControl";
2894
            break;
2895
        case 2:
2896
            check_insn(env, ctx, ASE_MT);
2897
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEConf0));
2898
            rn = "VPEConf0";
2899
            break;
2900
        case 3:
2901
            check_insn(env, ctx, ASE_MT);
2902
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEConf1));
2903
            rn = "VPEConf1";
2904
            break;
2905
        case 4:
2906
            check_insn(env, ctx, ASE_MT);
2907
            gen_mfc0_load64(t0, offsetof(CPUState, CP0_YQMask));
2908
            rn = "YQMask";
2909
            break;
2910
        case 5:
2911
            check_insn(env, ctx, ASE_MT);
2912
            gen_mfc0_load64(t0, offsetof(CPUState, CP0_VPESchedule));
2913
            rn = "VPESchedule";
2914
            break;
2915
        case 6:
2916
            check_insn(env, ctx, ASE_MT);
2917
            gen_mfc0_load64(t0, offsetof(CPUState, CP0_VPEScheFBack));
2918
            rn = "VPEScheFBack";
2919
            break;
2920
        case 7:
2921
            check_insn(env, ctx, ASE_MT);
2922
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEOpt));
2923
            rn = "VPEOpt";
2924
            break;
2925
        default:
2926
            goto die;
2927
        }
2928
        break;
2929
    case 2:
2930
        switch (sel) {
2931
        case 0:
2932
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryLo0));
2933
            tcg_gen_ext32s_tl(t0, t0);
2934
            rn = "EntryLo0";
2935
            break;
2936
        case 1:
2937
            check_insn(env, ctx, ASE_MT);
2938
            tcg_gen_helper_1_0(do_mfc0_tcstatus, t0);
2939
            rn = "TCStatus";
2940
            break;
2941
        case 2:
2942
            check_insn(env, ctx, ASE_MT);
2943
            tcg_gen_helper_1_0(do_mfc0_tcbind, t0);
2944
            rn = "TCBind";
2945
            break;
2946
        case 3:
2947
            check_insn(env, ctx, ASE_MT);
2948
            tcg_gen_helper_1_0(do_mfc0_tcrestart, t0);
2949
            rn = "TCRestart";
2950
            break;
2951
        case 4:
2952
            check_insn(env, ctx, ASE_MT);
2953
            tcg_gen_helper_1_0(do_mfc0_tchalt, t0);
2954
            rn = "TCHalt";
2955
            break;
2956
        case 5:
2957
            check_insn(env, ctx, ASE_MT);
2958
            tcg_gen_helper_1_0(do_mfc0_tccontext, t0);
2959
            rn = "TCContext";
2960
            break;
2961
        case 6:
2962
            check_insn(env, ctx, ASE_MT);
2963
            tcg_gen_helper_1_0(do_mfc0_tcschedule, t0);
2964
            rn = "TCSchedule";
2965
            break;
2966
        case 7:
2967
            check_insn(env, ctx, ASE_MT);
2968
            tcg_gen_helper_1_0(do_mfc0_tcschefback, t0);
2969
            rn = "TCScheFBack";
2970
            break;
2971
        default:
2972
            goto die;
2973
        }
2974
        break;
2975
    case 3:
2976
        switch (sel) {
2977
        case 0:
2978
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryLo1));
2979
            tcg_gen_ext32s_tl(t0, t0);
2980
            rn = "EntryLo1";
2981
            break;
2982
        default:
2983
            goto die;
2984
        }
2985
        break;
2986
    case 4:
2987
        switch (sel) {
2988
        case 0:
2989
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_Context));
2990
            tcg_gen_ext32s_tl(t0, t0);
2991
            rn = "Context";
2992
            break;
2993
        case 1:
2994
//            tcg_gen_helper_1_0(do_mfc0_contextconfig, t0); /* SmartMIPS ASE */
2995
            rn = "ContextConfig";
2996
//            break;
2997
        default:
2998
            goto die;
2999
        }
3000
        break;
3001
    case 5:
3002
        switch (sel) {
3003
        case 0:
3004
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_PageMask));
3005
            rn = "PageMask";
3006
            break;
3007
        case 1:
3008
            check_insn(env, ctx, ISA_MIPS32R2);
3009
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_PageGrain));
3010
            rn = "PageGrain";
3011
            break;
3012
        default:
3013
            goto die;
3014
        }
3015
        break;
3016
    case 6:
3017
        switch (sel) {
3018
        case 0:
3019
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Wired));
3020
            rn = "Wired";
3021
            break;
3022
        case 1:
3023
            check_insn(env, ctx, ISA_MIPS32R2);
3024
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf0));
3025
            rn = "SRSConf0";
3026
            break;
3027
        case 2:
3028
            check_insn(env, ctx, ISA_MIPS32R2);
3029
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf1));
3030
            rn = "SRSConf1";
3031
            break;
3032
        case 3:
3033
            check_insn(env, ctx, ISA_MIPS32R2);
3034
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf2));
3035
            rn = "SRSConf2";
3036
            break;
3037
        case 4:
3038
            check_insn(env, ctx, ISA_MIPS32R2);
3039
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf3));
3040
            rn = "SRSConf3";
3041
            break;
3042
        case 5:
3043
            check_insn(env, ctx, ISA_MIPS32R2);
3044
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf4));
3045
            rn = "SRSConf4";
3046
            break;
3047
        default:
3048
            goto die;
3049
        }
3050
        break;
3051
    case 7:
3052
        switch (sel) {
3053
        case 0:
3054
            check_insn(env, ctx, ISA_MIPS32R2);
3055
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_HWREna));
3056
            rn = "HWREna";
3057
            break;
3058
        default:
3059
            goto die;
3060
        }
3061
        break;
3062
    case 8:
3063
        switch (sel) {
3064
        case 0:
3065
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_BadVAddr));
3066
            tcg_gen_ext32s_tl(t0, t0);
3067
            rn = "BadVAddr";
3068
            break;
3069
        default:
3070
            goto die;
3071
       }
3072
        break;
3073
    case 9:
3074
        switch (sel) {
3075
        case 0:
3076
            /* Mark as an IO operation because we read the time.  */
3077
            if (use_icount)
3078
                gen_io_start();
3079
            tcg_gen_helper_1_0(do_mfc0_count, t0);
3080
            if (use_icount) {
3081
                gen_io_end();
3082
                ctx->bstate = BS_STOP;
3083
            }
3084
            rn = "Count";
3085
            break;
3086
        /* 6,7 are implementation dependent */
3087
        default:
3088
            goto die;
3089
        }
3090
        break;
3091
    case 10:
3092
        switch (sel) {
3093
        case 0:
3094
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryHi));
3095
            tcg_gen_ext32s_tl(t0, t0);
3096
            rn = "EntryHi";
3097
            break;
3098
        default:
3099
            goto die;
3100
        }
3101
        break;
3102
    case 11:
3103
        switch (sel) {
3104
        case 0:
3105
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Compare));
3106
            rn = "Compare";
3107
            break;
3108
        /* 6,7 are implementation dependent */
3109
        default:
3110
            goto die;
3111
        }
3112
        break;
3113
    case 12:
3114
        switch (sel) {
3115
        case 0:
3116
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Status));
3117
            rn = "Status";
3118
            break;
3119
        case 1:
3120
            check_insn(env, ctx, ISA_MIPS32R2);
3121
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_IntCtl));
3122
            rn = "IntCtl";
3123
            break;
3124
        case 2:
3125
            check_insn(env, ctx, ISA_MIPS32R2);
3126
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSCtl));
3127
            rn = "SRSCtl";
3128
            break;
3129
        case 3:
3130
            check_insn(env, ctx, ISA_MIPS32R2);
3131
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSMap));
3132
            rn = "SRSMap";
3133
            break;
3134
        default:
3135
            goto die;
3136
       }
3137
        break;
3138
    case 13:
3139
        switch (sel) {
3140
        case 0:
3141
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Cause));
3142
            rn = "Cause";
3143
            break;
3144
        default:
3145
            goto die;
3146
       }
3147
        break;
3148
    case 14:
3149
        switch (sel) {
3150
        case 0:
3151
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EPC));
3152
            tcg_gen_ext32s_tl(t0, t0);
3153
            rn = "EPC";
3154
            break;
3155
        default:
3156
            goto die;
3157
        }
3158
        break;
3159
    case 15:
3160
        switch (sel) {
3161
        case 0:
3162
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_PRid));
3163
            rn = "PRid";
3164
            break;
3165
        case 1:
3166
            check_insn(env, ctx, ISA_MIPS32R2);
3167
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_EBase));
3168
            rn = "EBase";
3169
            break;
3170
        default:
3171
            goto die;
3172
       }
3173
        break;
3174
    case 16:
3175
        switch (sel) {
3176
        case 0:
3177
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config0));
3178
            rn = "Config";
3179
            break;
3180
        case 1:
3181
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config1));
3182
            rn = "Config1";
3183
            break;
3184
        case 2:
3185
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config2));
3186
            rn = "Config2";
3187
            break;
3188
        case 3:
3189
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config3));
3190
            rn = "Config3";
3191
            break;
3192
        /* 4,5 are reserved */
3193
        /* 6,7 are implementation dependent */
3194
        case 6:
3195
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config6));
3196
            rn = "Config6";
3197
            break;
3198
        case 7:
3199
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config7));
3200
            rn = "Config7";
3201
            break;
3202
        default:
3203
            goto die;
3204
        }
3205
        break;
3206
    case 17:
3207
        switch (sel) {
3208
        case 0:
3209
            tcg_gen_helper_1_0(do_mfc0_lladdr, t0);
3210
            rn = "LLAddr";
3211
            break;
3212
        default:
3213
            goto die;
3214
        }
3215
        break;
3216
    case 18:
3217
        switch (sel) {
3218
        case 0 ... 7:
3219
            tcg_gen_helper_1_i(do_mfc0_watchlo, t0, sel);
3220
            rn = "WatchLo";
3221
            break;
3222
        default:
3223
            goto die;
3224
        }
3225
        break;
3226
    case 19:
3227
        switch (sel) {
3228
        case 0 ...7:
3229
            tcg_gen_helper_1_i(do_mfc0_watchhi, t0, sel);
3230
            rn = "WatchHi";
3231
            break;
3232
        default:
3233
            goto die;
3234
        }
3235
        break;
3236
    case 20:
3237
        switch (sel) {
3238
        case 0:
3239
#if defined(TARGET_MIPS64)
3240
            check_insn(env, ctx, ISA_MIPS3);
3241
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_XContext));
3242
            tcg_gen_ext32s_tl(t0, t0);
3243
            rn = "XContext";
3244
            break;
3245
#endif
3246
        default:
3247
            goto die;
3248
        }
3249
        break;
3250
    case 21:
3251
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
3252
        switch (sel) {
3253
        case 0:
3254
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Framemask));
3255
            rn = "Framemask";
3256
            break;
3257
        default:
3258
            goto die;
3259
        }
3260
        break;
3261
    case 22:
3262
        /* ignored */
3263
        rn = "'Diagnostic"; /* implementation dependent */
3264
        break;
3265
    case 23:
3266
        switch (sel) {
3267
        case 0:
3268
            tcg_gen_helper_1_0(do_mfc0_debug, t0); /* EJTAG support */
3269
            rn = "Debug";
3270
            break;
3271
        case 1:
3272
//            tcg_gen_helper_1_0(do_mfc0_tracecontrol, t0); /* PDtrace support */
3273
            rn = "TraceControl";
3274
//            break;
3275
        case 2:
3276
//            tcg_gen_helper_1_0(do_mfc0_tracecontrol2, t0); /* PDtrace support */
3277
            rn = "TraceControl2";
3278
//            break;
3279
        case 3:
3280
//            tcg_gen_helper_1_0(do_mfc0_usertracedata, t0); /* PDtrace support */
3281
            rn = "UserTraceData";
3282
//            break;
3283
        case 4:
3284
//            tcg_gen_helper_1_0(do_mfc0_tracebpc, t0); /* PDtrace support */
3285
            rn = "TraceBPC";
3286
//            break;
3287
        default:
3288
            goto die;
3289
        }
3290
        break;
3291
    case 24:
3292
        switch (sel) {
3293
        case 0:
3294
            /* EJTAG support */
3295
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_DEPC));
3296
            tcg_gen_ext32s_tl(t0, t0);
3297
            rn = "DEPC";
3298
            break;
3299
        default:
3300
            goto die;
3301
        }
3302
        break;
3303
    case 25:
3304
        switch (sel) {
3305
        case 0:
3306
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Performance0));
3307
            rn = "Performance0";
3308
            break;
3309
        case 1:
3310
//            tcg_gen_helper_1_0(do_mfc0_performance1, t0);
3311
            rn = "Performance1";
3312
//            break;
3313
        case 2:
3314
//            tcg_gen_helper_1_0(do_mfc0_performance2, t0);
3315
            rn = "Performance2";
3316
//            break;
3317
        case 3:
3318
//            tcg_gen_helper_1_0(do_mfc0_performance3, t0);
3319
            rn = "Performance3";
3320
//            break;
3321
        case 4:
3322
//            tcg_gen_helper_1_0(do_mfc0_performance4, t0);
3323
            rn = "Performance4";
3324
//            break;
3325
        case 5:
3326
//            tcg_gen_helper_1_0(do_mfc0_performance5, t0);
3327
            rn = "Performance5";
3328
//            break;
3329
        case 6:
3330
//            tcg_gen_helper_1_0(do_mfc0_performance6, t0);
3331
            rn = "Performance6";
3332
//            break;
3333
        case 7:
3334
//            tcg_gen_helper_1_0(do_mfc0_performance7, t0);
3335
            rn = "Performance7";
3336
//            break;
3337
        default:
3338
            goto die;
3339
        }
3340
        break;
3341
    case 26:
3342
       rn = "ECC";
3343
       break;
3344
    case 27:
3345
        switch (sel) {
3346
        /* ignored */
3347
        case 0 ... 3:
3348
            rn = "CacheErr";
3349
            break;
3350
        default:
3351
            goto die;
3352
        }
3353
        break;
3354
    case 28:
3355
        switch (sel) {
3356
        case 0:
3357
        case 2:
3358
        case 4:
3359
        case 6:
3360
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_TagLo));
3361
            rn = "TagLo";
3362
            break;
3363
        case 1:
3364
        case 3:
3365
        case 5:
3366
        case 7:
3367
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_DataLo));
3368
            rn = "DataLo";
3369
            break;
3370
        default:
3371
            goto die;
3372
        }
3373
        break;
3374
    case 29:
3375
        switch (sel) {
3376
        case 0:
3377
        case 2:
3378
        case 4:
3379
        case 6:
3380
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_TagHi));
3381
            rn = "TagHi";
3382
            break;
3383
        case 1:
3384
        case 3:
3385
        case 5:
3386
        case 7:
3387
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_DataHi));
3388
            rn = "DataHi";
3389
            break;
3390
        default:
3391
            goto die;
3392
        }
3393
        break;
3394
    case 30:
3395
        switch (sel) {
3396
        case 0:
3397
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_ErrorEPC));
3398
            tcg_gen_ext32s_tl(t0, t0);
3399
            rn = "ErrorEPC";
3400
            break;
3401
        default:
3402
            goto die;
3403
        }
3404
        break;
3405
    case 31:
3406
        switch (sel) {
3407
        case 0:
3408
            /* EJTAG support */
3409
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_DESAVE));
3410
            rn = "DESAVE";
3411
            break;
3412
        default:
3413
            goto die;
3414
        }
3415
        break;
3416
    default:
3417
       goto die;
3418
    }
3419
#if defined MIPS_DEBUG_DISAS
3420
    if (loglevel & CPU_LOG_TB_IN_ASM) {
3421
        fprintf(logfile, "mfc0 %s (reg %d sel %d)\n",
3422
                rn, reg, sel);
3423
    }
3424
#endif
3425
    return;
3426

    
3427
die:
3428
#if defined MIPS_DEBUG_DISAS
3429
    if (loglevel & CPU_LOG_TB_IN_ASM) {
3430
        fprintf(logfile, "mfc0 %s (reg %d sel %d)\n",
3431
                rn, reg, sel);
3432
    }
3433
#endif
3434
    generate_exception(ctx, EXCP_RI);
3435
}
3436

    
3437
static void gen_mtc0 (CPUState *env, DisasContext *ctx, TCGv t0, int reg, int sel)
3438
{
3439
    const char *rn = "invalid";
3440

    
3441
    if (sel != 0)
3442
        check_insn(env, ctx, ISA_MIPS32);
3443

    
3444
    if (use_icount)
3445
        gen_io_start();
3446

    
3447
    switch (reg) {
3448
    case 0:
3449
        switch (sel) {
3450
        case 0:
3451
            tcg_gen_helper_0_1(do_mtc0_index, t0);
3452
            rn = "Index";
3453
            break;
3454
        case 1:
3455
            check_insn(env, ctx, ASE_MT);
3456
            tcg_gen_helper_0_1(do_mtc0_mvpcontrol, t0);
3457
            rn = "MVPControl";
3458
            break;
3459
        case 2:
3460
            check_insn(env, ctx, ASE_MT);
3461
            /* ignored */
3462
            rn = "MVPConf0";
3463
            break;
3464
        case 3:
3465
            check_insn(env, ctx, ASE_MT);
3466
            /* ignored */
3467
            rn = "MVPConf1";
3468
            break;
3469
        default:
3470
            goto die;
3471
        }
3472
        break;
3473
    case 1:
3474
        switch (sel) {
3475
        case 0:
3476
            /* ignored */
3477
            rn = "Random";
3478
            break;
3479
        case 1:
3480
            check_insn(env, ctx, ASE_MT);
3481
            tcg_gen_helper_0_1(do_mtc0_vpecontrol, t0);
3482
            rn = "VPEControl";
3483
            break;
3484
        case 2:
3485
            check_insn(env, ctx, ASE_MT);
3486
            tcg_gen_helper_0_1(do_mtc0_vpeconf0, t0);
3487
            rn = "VPEConf0";
3488
            break;
3489
        case 3:
3490
            check_insn(env, ctx, ASE_MT);
3491
            tcg_gen_helper_0_1(do_mtc0_vpeconf1, t0);
3492
            rn = "VPEConf1";
3493
            break;
3494
        case 4:
3495
            check_insn(env, ctx, ASE_MT);
3496
            tcg_gen_helper_0_1(do_mtc0_yqmask, t0);
3497
            rn = "YQMask";
3498
            break;
3499
        case 5:
3500
            check_insn(env, ctx, ASE_MT);
3501
            gen_mtc0_store64(t0, offsetof(CPUState, CP0_VPESchedule));
3502
            rn = "VPESchedule";
3503
            break;
3504
        case 6:
3505
            check_insn(env, ctx, ASE_MT);
3506
            gen_mtc0_store64(t0, offsetof(CPUState, CP0_VPEScheFBack));
3507
            rn = "VPEScheFBack";
3508
            break;
3509
        case 7:
3510
            check_insn(env, ctx, ASE_MT);
3511
            tcg_gen_helper_0_1(do_mtc0_vpeopt, t0);
3512
            rn = "VPEOpt";
3513
            break;
3514
        default:
3515
            goto die;
3516
        }
3517
        break;
3518
    case 2:
3519
        switch (sel) {
3520
        case 0:
3521
            tcg_gen_helper_0_1(do_mtc0_entrylo0, t0);
3522
            rn = "EntryLo0";
3523
            break;
3524
        case 1:
3525
            check_insn(env, ctx, ASE_MT);
3526
            tcg_gen_helper_0_1(do_mtc0_tcstatus, t0);
3527
            rn = "TCStatus";
3528
            break;
3529
        case 2:
3530
            check_insn(env, ctx, ASE_MT);
3531
            tcg_gen_helper_0_1(do_mtc0_tcbind, t0);
3532
            rn = "TCBind";
3533
            break;
3534
        case 3:
3535
            check_insn(env, ctx, ASE_MT);
3536
            tcg_gen_helper_0_1(do_mtc0_tcrestart, t0);
3537
            rn = "TCRestart";
3538
            break;
3539
        case 4:
3540
            check_insn(env, ctx, ASE_MT);
3541
            tcg_gen_helper_0_1(do_mtc0_tchalt, t0);
3542
            rn = "TCHalt";
3543
            break;
3544
        case 5:
3545
            check_insn(env, ctx, ASE_MT);
3546
            tcg_gen_helper_0_1(do_mtc0_tccontext, t0);
3547
            rn = "TCContext";
3548
            break;
3549
        case 6:
3550
            check_insn(env, ctx, ASE_MT);
3551
            tcg_gen_helper_0_1(do_mtc0_tcschedule, t0);
3552
            rn = "TCSchedule";
3553
            break;
3554
        case 7:
3555
            check_insn(env, ctx, ASE_MT);
3556
            tcg_gen_helper_0_1(do_mtc0_tcschefback, t0);
3557
            rn = "TCScheFBack";
3558
            break;
3559
        default:
3560
            goto die;
3561
        }
3562
        break;
3563
    case 3:
3564
        switch (sel) {
3565
        case 0:
3566
            tcg_gen_helper_0_1(do_mtc0_entrylo1, t0);
3567
            rn = "EntryLo1";
3568
            break;
3569
        default:
3570
            goto die;
3571
        }
3572
        break;
3573
    case 4:
3574
        switch (sel) {
3575
        case 0:
3576
            tcg_gen_helper_0_1(do_mtc0_context, t0);
3577
            rn = "Context";
3578
            break;
3579
        case 1:
3580
//            tcg_gen_helper_0_1(do_mtc0_contextconfig, t0); /* SmartMIPS ASE */
3581
            rn = "ContextConfig";
3582
//            break;
3583
        default:
3584
            goto die;
3585
        }
3586
        break;
3587
    case 5:
3588
        switch (sel) {
3589
        case 0:
3590
            tcg_gen_helper_0_1(do_mtc0_pagemask, t0);
3591
            rn = "PageMask";
3592
            break;
3593
        case 1:
3594
            check_insn(env, ctx, ISA_MIPS32R2);
3595
            tcg_gen_helper_0_1(do_mtc0_pagegrain, t0);
3596
            rn = "PageGrain";
3597
            break;
3598
        default:
3599
            goto die;
3600
        }
3601
        break;
3602
    case 6:
3603
        switch (sel) {
3604
        case 0:
3605
            tcg_gen_helper_0_1(do_mtc0_wired, t0);
3606
            rn = "Wired";
3607
            break;
3608
        case 1:
3609
            check_insn(env, ctx, ISA_MIPS32R2);
3610
            tcg_gen_helper_0_1(do_mtc0_srsconf0, t0);
3611
            rn = "SRSConf0";
3612
            break;
3613
        case 2:
3614
            check_insn(env, ctx, ISA_MIPS32R2);
3615
            tcg_gen_helper_0_1(do_mtc0_srsconf1, t0);
3616
            rn = "SRSConf1";
3617
            break;
3618
        case 3:
3619
            check_insn(env, ctx, ISA_MIPS32R2);
3620
            tcg_gen_helper_0_1(do_mtc0_srsconf2, t0);
3621
            rn = "SRSConf2";
3622
            break;
3623
        case 4:
3624
            check_insn(env, ctx, ISA_MIPS32R2);
3625
            tcg_gen_helper_0_1(do_mtc0_srsconf3, t0);
3626
            rn = "SRSConf3";
3627
            break;
3628
        case 5:
3629
            check_insn(env, ctx, ISA_MIPS32R2);
3630
            tcg_gen_helper_0_1(do_mtc0_srsconf4, t0);
3631
            rn = "SRSConf4";
3632
            break;
3633
        default:
3634
            goto die;
3635
        }
3636
        break;
3637
    case 7:
3638
        switch (sel) {
3639
        case 0:
3640
            check_insn(env, ctx, ISA_MIPS32R2);
3641
            tcg_gen_helper_0_1(do_mtc0_hwrena, t0);
3642
            rn = "HWREna";
3643
            break;
3644
        default:
3645
            goto die;
3646
        }
3647
        break;
3648
    case 8:
3649
        /* ignored */
3650
        rn = "BadVAddr";
3651
        break;
3652
    case 9:
3653
        switch (sel) {
3654
        case 0:
3655
            tcg_gen_helper_0_1(do_mtc0_count, t0);
3656
            rn = "Count";
3657
            break;
3658
        /* 6,7 are implementation dependent */
3659
        default:
3660
            goto die;
3661
        }
3662
        /* Stop translation as we may have switched the execution mode */
3663
        ctx->bstate = BS_STOP;
3664
        break;
3665
    case 10:
3666
        switch (sel) {
3667
        case 0:
3668
            tcg_gen_helper_0_1(do_mtc0_entryhi, t0);
3669
            rn = "EntryHi";
3670
            break;
3671
        default:
3672
            goto die;
3673
        }
3674
        break;
3675
    case 11:
3676
        switch (sel) {
3677
        case 0:
3678
            tcg_gen_helper_0_1(do_mtc0_compare, t0);
3679
            rn = "Compare";
3680
            break;
3681
        /* 6,7 are implementation dependent */
3682
        default:
3683
            goto die;
3684
        }
3685
        /* Stop translation as we may have switched the execution mode */
3686
        ctx->bstate = BS_STOP;
3687
        break;
3688
    case 12:
3689
        switch (sel) {
3690
        case 0:
3691
            tcg_gen_helper_0_1(do_mtc0_status, t0);
3692
            /* BS_STOP isn't good enough here, hflags may have changed. */
3693
            gen_save_pc(ctx->pc + 4);
3694
            ctx->bstate = BS_EXCP;
3695
            rn = "Status";
3696
            break;
3697
        case 1:
3698
            check_insn(env, ctx, ISA_MIPS32R2);
3699
            tcg_gen_helper_0_1(do_mtc0_intctl, t0);
3700
            /* Stop translation as we may have switched the execution mode */
3701
            ctx->bstate = BS_STOP;
3702
            rn = "IntCtl";
3703
            break;
3704
        case 2:
3705
            check_insn(env, ctx, ISA_MIPS32R2);
3706
            tcg_gen_helper_0_1(do_mtc0_srsctl, t0);
3707
            /* Stop translation as we may have switched the execution mode */
3708
            ctx->bstate = BS_STOP;
3709
            rn = "SRSCtl";
3710
            break;
3711
        case 3:
3712
            check_insn(env, ctx, ISA_MIPS32R2);
3713
            gen_mtc0_store32(t0, offsetof(CPUState, CP0_SRSMap));
3714
            /* Stop translation as we may have switched the execution mode */
3715
            ctx->bstate = BS_STOP;
3716
            rn = "SRSMap";
3717
            break;
3718
        default:
3719
            goto die;
3720
        }
3721
        break;
3722
    case 13:
3723
        switch (sel) {
3724
        case 0:
3725
            tcg_gen_helper_0_1(do_mtc0_cause, t0);
3726
            rn = "Cause";
3727
            break;
3728
        default:
3729
            goto die;
3730
        }
3731
        /* Stop translation as we may have switched the execution mode */
3732
        ctx->bstate = BS_STOP;
3733
        break;
3734
    case 14:
3735
        switch (sel) {
3736
        case 0:
3737
            gen_mtc0_store64(t0, offsetof(CPUState, CP0_EPC));
3738
            rn = "EPC";
3739
            break;
3740
        default:
3741
            goto die;
3742
        }
3743
        break;
3744
    case 15:
3745
        switch (sel) {
3746
        case 0:
3747
            /* ignored */
3748
            rn = "PRid";
3749
            break;
3750
        case 1:
3751
            check_insn(env, ctx, ISA_MIPS32R2);
3752
            tcg_gen_helper_0_1(do_mtc0_ebase, t0);
3753
            rn = "EBase";
3754
            break;
3755
        default:
3756
            goto die;
3757
        }
3758
        break;
3759
    case 16:
3760
        switch (sel) {
3761
        case 0:
3762
            tcg_gen_helper_0_1(do_mtc0_config0, t0);
3763
            rn = "Config";
3764
            /* Stop translation as we may have switched the execution mode */
3765
            ctx->bstate = BS_STOP;
3766
            break;
3767
        case 1:
3768
            /* ignored, read only */
3769
            rn = "Config1";
3770
            break;
3771
        case 2:
3772
            tcg_gen_helper_0_1(do_mtc0_config2, t0);
3773
            rn = "Config2";
3774
            /* Stop translation as we may have switched the execution mode */
3775
            ctx->bstate = BS_STOP;
3776
            break;
3777
        case 3:
3778
            /* ignored, read only */
3779
            rn = "Config3";
3780
            break;
3781
        /* 4,5 are reserved */
3782
        /* 6,7 are implementation dependent */
3783
        case 6:
3784
            /* ignored */
3785
            rn = "Config6";
3786
            break;
3787
        case 7:
3788
            /* ignored */
3789
            rn = "Config7";
3790
            break;
3791
        default:
3792
            rn = "Invalid config selector";
3793
            goto die;
3794
        }
3795
        break;
3796
    case 17:
3797
        switch (sel) {
3798
        case 0:
3799
            /* ignored */
3800
            rn = "LLAddr";
3801
            break;
3802
        default:
3803
            goto die;
3804
        }
3805
        break;
3806
    case 18:
3807
        switch (sel) {
3808
        case 0 ... 7:
3809
            tcg_gen_helper_0_1i(do_mtc0_watchlo, t0, sel);
3810
            rn = "WatchLo";
3811
            break;
3812
        default:
3813
            goto die;
3814
        }
3815
        break;
3816
    case 19:
3817
        switch (sel) {
3818
        case 0 ... 7:
3819
            tcg_gen_helper_0_1i(do_mtc0_watchhi, t0, sel);
3820
            rn = "WatchHi";
3821
            break;
3822
        default:
3823
            goto die;
3824
        }
3825
        break;
3826
    case 20:
3827
        switch (sel) {
3828
        case 0:
3829
#if defined(TARGET_MIPS64)
3830
            check_insn(env, ctx, ISA_MIPS3);
3831
            tcg_gen_helper_0_1(do_mtc0_xcontext, t0);
3832
            rn = "XContext";
3833
            break;
3834
#endif
3835
        default:
3836
            goto die;
3837
        }
3838
        break;
3839
    case 21:
3840
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
3841
        switch (sel) {
3842
        case 0:
3843
            tcg_gen_helper_0_1(do_mtc0_framemask, t0);
3844
            rn = "Framemask";
3845
            break;
3846
        default:
3847
            goto die;
3848
        }
3849
        break;
3850
    case 22:
3851
        /* ignored */
3852
        rn = "Diagnostic"; /* implementation dependent */
3853
        break;
3854
    case 23:
3855
        switch (sel) {
3856
        case 0:
3857
            tcg_gen_helper_0_1(do_mtc0_debug, t0); /* EJTAG support */
3858
            /* BS_STOP isn't good enough here, hflags may have changed. */
3859
            gen_save_pc(ctx->pc + 4);
3860
            ctx->bstate = BS_EXCP;
3861
            rn = "Debug";
3862
            break;
3863
        case 1:
3864
//            tcg_gen_helper_0_1(do_mtc0_tracecontrol, t0); /* PDtrace support */
3865
            rn = "TraceControl";
3866
            /* Stop translation as we may have switched the execution mode */
3867
            ctx->bstate = BS_STOP;
3868
//            break;
3869
        case 2:
3870
//            tcg_gen_helper_0_1(do_mtc0_tracecontrol2, t0); /* PDtrace support */
3871
            rn = "TraceControl2";
3872
            /* Stop translation as we may have switched the execution mode */
3873
            ctx->bstate = BS_STOP;
3874
//            break;
3875
        case 3:
3876
            /* Stop translation as we may have switched the execution mode */
3877
            ctx->bstate = BS_STOP;
3878
//            tcg_gen_helper_0_1(do_mtc0_usertracedata, t0); /* PDtrace support */
3879
            rn = "UserTraceData";
3880
            /* Stop translation as we may have switched the execution mode */
3881
            ctx->bstate = BS_STOP;
3882
//            break;
3883
        case 4:
3884
//            tcg_gen_helper_0_1(do_mtc0_tracebpc, t0); /* PDtrace support */
3885
            /* Stop translation as we may have switched the execution mode */
3886
            ctx->bstate = BS_STOP;
3887
            rn = "TraceBPC";
3888
//            break;
3889
        default:
3890
            goto die;
3891
        }
3892
        break;
3893
    case 24:
3894
        switch (sel) {
3895
        case 0:
3896
            /* EJTAG support */
3897
            gen_mtc0_store64(t0, offsetof(CPUState, CP0_DEPC));
3898
            rn = "DEPC";
3899
            break;
3900
        default:
3901
            goto die;
3902
        }
3903
        break;
3904
    case 25:
3905
        switch (sel) {
3906
        case 0:
3907
            tcg_gen_helper_0_1(do_mtc0_performance0, t0);
3908
            rn = "Performance0";
3909
            break;
3910
        case 1:
3911
//            tcg_gen_helper_0_1(do_mtc0_performance1, t0);
3912
            rn = "Performance1";
3913
//            break;
3914
        case 2:
3915
//            tcg_gen_helper_0_1(do_mtc0_performance2, t0);
3916
            rn = "Performance2";
3917
//            break;
3918
        case 3:
3919
//            tcg_gen_helper_0_1(do_mtc0_performance3, t0);
3920
            rn = "Performance3";
3921
//            break;
3922
        case 4:
3923
//            tcg_gen_helper_0_1(do_mtc0_performance4, t0);
3924
            rn = "Performance4";
3925
//            break;
3926
        case 5:
3927
//            tcg_gen_helper_0_1(do_mtc0_performance5, t0);
3928
            rn = "Performance5";
3929
//            break;
3930
        case 6:
3931
//            tcg_gen_helper_0_1(do_mtc0_performance6, t0);
3932
            rn = "Performance6";
3933
//            break;
3934
        case 7:
3935
//            tcg_gen_helper_0_1(do_mtc0_performance7, t0);
3936
            rn = "Performance7";
3937
//            break;
3938
        default:
3939
            goto die;
3940
        }
3941
       break;
3942
    case 26:
3943
        /* ignored */
3944
        rn = "ECC";
3945
        break;
3946
    case 27:
3947
        switch (sel) {
3948
        case 0 ... 3:
3949
            /* ignored */
3950
            rn = "CacheErr";
3951
            break;
3952
        default:
3953
            goto die;
3954
        }
3955
       break;
3956
    case 28:
3957
        switch (sel) {
3958
        case 0:
3959
        case 2:
3960
        case 4:
3961
        case 6:
3962
            tcg_gen_helper_0_1(do_mtc0_taglo, t0);
3963
            rn = "TagLo";
3964
            break;
3965
        case 1:
3966
        case 3:
3967
        case 5:
3968
        case 7:
3969
            tcg_gen_helper_0_1(do_mtc0_datalo, t0);
3970
            rn = "DataLo";
3971
            break;
3972
        default:
3973
            goto die;
3974
        }
3975
        break;
3976
    case 29:
3977
        switch (sel) {
3978
        case 0:
3979
        case 2:
3980
        case 4:
3981
        case 6:
3982
            tcg_gen_helper_0_1(do_mtc0_taghi, t0);
3983
            rn = "TagHi";
3984
            break;
3985
        case 1:
3986
        case 3:
3987
        case 5:
3988
        case 7:
3989
            tcg_gen_helper_0_1(do_mtc0_datahi, t0);
3990
            rn = "DataHi";
3991
            break;
3992
        default:
3993
            rn = "invalid sel";
3994
            goto die;
3995
        }
3996
       break;
3997
    case 30:
3998
        switch (sel) {
3999
        case 0:
4000
            gen_mtc0_store64(t0, offsetof(CPUState, CP0_ErrorEPC));
4001
            rn = "ErrorEPC";
4002
            break;
4003
        default:
4004
            goto die;
4005
        }
4006
        break;
4007
    case 31:
4008
        switch (sel) {
4009
        case 0:
4010
            /* EJTAG support */
4011
            gen_mtc0_store32(t0, offsetof(CPUState, CP0_DESAVE));
4012
            rn = "DESAVE";
4013
            break;
4014
        default:
4015
            goto die;
4016
        }
4017
        /* Stop translation as we may have switched the execution mode */
4018
        ctx->bstate = BS_STOP;
4019
        break;
4020
    default:
4021
       goto die;
4022
    }
4023
#if defined MIPS_DEBUG_DISAS
4024
    if (loglevel & CPU_LOG_TB_IN_ASM) {
4025
        fprintf(logfile, "mtc0 %s (reg %d sel %d)\n",
4026
                rn, reg, sel);
4027
    }
4028
#endif
4029
    /* For simplicitly assume that all writes can cause interrupts.  */
4030
    if (use_icount) {
4031
        gen_io_end();
4032
        ctx->bstate = BS_STOP;
4033
    }
4034
    return;
4035

    
4036
die:
4037
#if defined MIPS_DEBUG_DISAS
4038
    if (loglevel & CPU_LOG_TB_IN_ASM) {
4039
        fprintf(logfile, "mtc0 %s (reg %d sel %d)\n",
4040
                rn, reg, sel);
4041
    }
4042
#endif
4043
    generate_exception(ctx, EXCP_RI);
4044
}
4045

    
4046
#if defined(TARGET_MIPS64)
4047
static void gen_dmfc0 (CPUState *env, DisasContext *ctx, TCGv t0, int reg, int sel)
4048
{
4049
    const char *rn = "invalid";
4050

    
4051
    if (sel != 0)
4052
        check_insn(env, ctx, ISA_MIPS64);
4053

    
4054
    switch (reg) {
4055
    case 0:
4056
        switch (sel) {
4057
        case 0:
4058
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Index));
4059
            rn = "Index";
4060
            break;
4061
        case 1:
4062
            check_insn(env, ctx, ASE_MT);
4063
            tcg_gen_helper_1_0(do_mfc0_mvpcontrol, t0);
4064
            rn = "MVPControl";
4065
            break;
4066
        case 2:
4067
            check_insn(env, ctx, ASE_MT);
4068
            tcg_gen_helper_1_0(do_mfc0_mvpconf0, t0);
4069
            rn = "MVPConf0";
4070
            break;
4071
        case 3:
4072
            check_insn(env, ctx, ASE_MT);
4073
            tcg_gen_helper_1_0(do_mfc0_mvpconf1, t0);
4074
            rn = "MVPConf1";
4075
            break;
4076
        default:
4077
            goto die;
4078
        }
4079
        break;
4080
    case 1:
4081
        switch (sel) {
4082
        case 0:
4083
            tcg_gen_helper_1_0(do_mfc0_random, t0);
4084
            rn = "Random";
4085
            break;
4086
        case 1:
4087
            check_insn(env, ctx, ASE_MT);
4088
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEControl));
4089
            rn = "VPEControl";
4090
            break;
4091
        case 2:
4092
            check_insn(env, ctx, ASE_MT);
4093
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEConf0));
4094
            rn = "VPEConf0";
4095
            break;
4096
        case 3:
4097
            check_insn(env, ctx, ASE_MT);
4098
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEConf1));
4099
            rn = "VPEConf1";
4100
            break;
4101
        case 4:
4102
            check_insn(env, ctx, ASE_MT);
4103
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_YQMask));
4104
            rn = "YQMask";
4105
            break;
4106
        case 5:
4107
            check_insn(env, ctx, ASE_MT);
4108
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_VPESchedule));
4109
            rn = "VPESchedule";
4110
            break;
4111
        case 6:
4112
            check_insn(env, ctx, ASE_MT);
4113
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_VPEScheFBack));
4114
            rn = "VPEScheFBack";
4115
            break;
4116
        case 7:
4117
            check_insn(env, ctx, ASE_MT);
4118
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEOpt));
4119
            rn = "VPEOpt";
4120
            break;
4121
        default:
4122
            goto die;
4123
        }
4124
        break;
4125
    case 2:
4126
        switch (sel) {
4127
        case 0:
4128
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryLo0));
4129
            rn = "EntryLo0";
4130
            break;
4131
        case 1:
4132
            check_insn(env, ctx, ASE_MT);
4133
            tcg_gen_helper_1_0(do_mfc0_tcstatus, t0);
4134
            rn = "TCStatus";
4135
            break;
4136
        case 2:
4137
            check_insn(env, ctx, ASE_MT);
4138
            tcg_gen_helper_1_0(do_mfc0_tcbind, t0);
4139
            rn = "TCBind";
4140
            break;
4141
        case 3:
4142
            check_insn(env, ctx, ASE_MT);
4143
            tcg_gen_helper_1_0(do_dmfc0_tcrestart, t0);
4144
            rn = "TCRestart";
4145
            break;
4146
        case 4:
4147
            check_insn(env, ctx, ASE_MT);
4148
            tcg_gen_helper_1_0(do_dmfc0_tchalt, t0);
4149
            rn = "TCHalt";
4150
            break;
4151
        case 5:
4152
            check_insn(env, ctx, ASE_MT);
4153
            tcg_gen_helper_1_0(do_dmfc0_tccontext, t0);
4154
            rn = "TCContext";
4155
            break;
4156
        case 6:
4157
            check_insn(env, ctx, ASE_MT);
4158
            tcg_gen_helper_1_0(do_dmfc0_tcschedule, t0);
4159
            rn = "TCSchedule";
4160
            break;
4161
        case 7:
4162
            check_insn(env, ctx, ASE_MT);
4163
            tcg_gen_helper_1_0(do_dmfc0_tcschefback, t0);
4164
            rn = "TCScheFBack";
4165
            break;
4166
        default:
4167
            goto die;
4168
        }
4169
        break;
4170
    case 3:
4171
        switch (sel) {
4172
        case 0:
4173
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryLo1));
4174
            rn = "EntryLo1";
4175
            break;
4176
        default:
4177
            goto die;
4178
        }
4179
        break;
4180
    case 4:
4181
        switch (sel) {
4182
        case 0:
4183
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_Context));
4184
            rn = "Context";
4185
            break;
4186
        case 1:
4187
//            tcg_gen_helper_1_0(do_dmfc0_contextconfig, t0); /* SmartMIPS ASE */
4188
            rn = "ContextConfig";
4189
//            break;
4190
        default:
4191
            goto die;
4192
        }
4193
        break;
4194
    case 5:
4195
        switch (sel) {
4196
        case 0:
4197
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_PageMask));
4198
            rn = "PageMask";
4199
            break;
4200
        case 1:
4201
            check_insn(env, ctx, ISA_MIPS32R2);
4202
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_PageGrain));
4203
            rn = "PageGrain";
4204
            break;
4205
        default:
4206
            goto die;
4207
        }
4208
        break;
4209
    case 6:
4210
        switch (sel) {
4211
        case 0:
4212
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Wired));
4213
            rn = "Wired";
4214
            break;
4215
        case 1:
4216
            check_insn(env, ctx, ISA_MIPS32R2);
4217
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf0));
4218
            rn = "SRSConf0";
4219
            break;
4220
        case 2:
4221
            check_insn(env, ctx, ISA_MIPS32R2);
4222
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf1));
4223
            rn = "SRSConf1";
4224
            break;
4225
        case 3:
4226
            check_insn(env, ctx, ISA_MIPS32R2);
4227
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf2));
4228
            rn = "SRSConf2";
4229
            break;
4230
        case 4:
4231
            check_insn(env, ctx, ISA_MIPS32R2);
4232
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf3));
4233
            rn = "SRSConf3";
4234
            break;
4235
        case 5:
4236
            check_insn(env, ctx, ISA_MIPS32R2);
4237
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf4));
4238
            rn = "SRSConf4";
4239
            break;
4240
        default:
4241
            goto die;
4242
        }
4243
        break;
4244
    case 7:
4245
        switch (sel) {
4246
        case 0:
4247
            check_insn(env, ctx, ISA_MIPS32R2);
4248
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_HWREna));
4249
            rn = "HWREna";
4250
            break;
4251
        default:
4252
            goto die;
4253
        }
4254
        break;
4255
    case 8:
4256
        switch (sel) {
4257
        case 0:
4258
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_BadVAddr));
4259
            rn = "BadVAddr";
4260
            break;
4261
        default:
4262
            goto die;
4263
        }
4264
        break;
4265
    case 9:
4266
        switch (sel) {
4267
        case 0:
4268
            /* Mark as an IO operation because we read the time.  */
4269
            if (use_icount)
4270
                gen_io_start();
4271
            tcg_gen_helper_1_0(do_mfc0_count, t0);
4272
            if (use_icount) {
4273
                gen_io_end();
4274
                ctx->bstate = BS_STOP;
4275
            }
4276
            rn = "Count";
4277
            break;
4278
        /* 6,7 are implementation dependent */
4279
        default:
4280
            goto die;
4281
        }
4282
        break;
4283
    case 10:
4284
        switch (sel) {
4285
        case 0:
4286
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryHi));
4287
            rn = "EntryHi";
4288
            break;
4289
        default:
4290
            goto die;
4291
        }
4292
        break;
4293
    case 11:
4294
        switch (sel) {
4295
        case 0:
4296
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Compare));
4297
            rn = "Compare";
4298
            break;
4299
        /* 6,7 are implementation dependent */
4300
        default:
4301
            goto die;
4302
        }
4303
        break;
4304
    case 12:
4305
        switch (sel) {
4306
        case 0:
4307
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Status));
4308
            rn = "Status";
4309
            break;
4310
        case 1:
4311
            check_insn(env, ctx, ISA_MIPS32R2);
4312
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_IntCtl));
4313
            rn = "IntCtl";
4314
            break;
4315
        case 2:
4316
            check_insn(env, ctx, ISA_MIPS32R2);
4317
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSCtl));
4318
            rn = "SRSCtl";
4319
            break;
4320
        case 3:
4321
            check_insn(env, ctx, ISA_MIPS32R2);
4322
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSMap));
4323
            rn = "SRSMap";
4324
            break;
4325
        default:
4326
            goto die;
4327
        }
4328
        break;
4329
    case 13:
4330
        switch (sel) {
4331
        case 0:
4332
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Cause));
4333
            rn = "Cause";
4334
            break;
4335
        default:
4336
            goto die;
4337
        }
4338
        break;
4339
    case 14:
4340
        switch (sel) {
4341
        case 0:
4342
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EPC));
4343
            rn = "EPC";
4344
            break;
4345
        default:
4346
            goto die;
4347
        }
4348
        break;
4349
    case 15:
4350
        switch (sel) {
4351
        case 0:
4352
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_PRid));
4353
            rn = "PRid";
4354
            break;
4355
        case 1:
4356
            check_insn(env, ctx, ISA_MIPS32R2);
4357
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_EBase));
4358
            rn = "EBase";
4359
            break;
4360
        default:
4361
            goto die;
4362
        }
4363
        break;
4364
    case 16:
4365
        switch (sel) {
4366
        case 0:
4367
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config0));
4368
            rn = "Config";
4369
            break;
4370
        case 1:
4371
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config1));
4372
            rn = "Config1";
4373
            break;
4374
        case 2:
4375
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config2));
4376
            rn = "Config2";
4377
            break;
4378
        case 3:
4379
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config3));
4380
            rn = "Config3";
4381
            break;
4382
       /* 6,7 are implementation dependent */
4383
        case 6:
4384
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config6));
4385
            rn = "Config6";
4386
            break;
4387
        case 7:
4388
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config7));
4389
            rn = "Config7";
4390
            break;
4391
        default:
4392
            goto die;
4393
        }
4394
        break;
4395
    case 17:
4396
        switch (sel) {
4397
        case 0:
4398
            tcg_gen_helper_1_0(do_dmfc0_lladdr, t0);
4399
            rn = "LLAddr";
4400
            break;
4401
        default:
4402
            goto die;
4403
        }
4404
        break;
4405
    case 18:
4406
        switch (sel) {
4407
        case 0 ... 7:
4408
            tcg_gen_helper_1_i(do_dmfc0_watchlo, t0, sel);
4409
            rn = "WatchLo";
4410
            break;
4411
        default:
4412
            goto die;
4413
        }
4414
        break;
4415
    case 19:
4416
        switch (sel) {
4417
        case 0 ... 7:
4418
            tcg_gen_helper_1_i(do_mfc0_watchhi, t0, sel);
4419
            rn = "WatchHi";
4420
            break;
4421
        default:
4422
            goto die;
4423
        }
4424
        break;
4425
    case 20:
4426
        switch (sel) {
4427
        case 0:
4428
            check_insn(env, ctx, ISA_MIPS3);
4429
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_XContext));
4430
            rn = "XContext";
4431
            break;
4432
        default:
4433
            goto die;
4434
        }
4435
        break;
4436
    case 21:
4437
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
4438
        switch (sel) {
4439
        case 0:
4440
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Framemask));
4441
            rn = "Framemask";
4442
            break;
4443
        default:
4444
            goto die;
4445
        }
4446
        break;
4447
    case 22:
4448
        /* ignored */
4449
        rn = "'Diagnostic"; /* implementation dependent */
4450
        break;
4451
    case 23:
4452
        switch (sel) {
4453
        case 0:
4454
            tcg_gen_helper_1_0(do_mfc0_debug, t0); /* EJTAG support */
4455
            rn = "Debug";
4456
            break;
4457
        case 1:
4458
//            tcg_gen_helper_1_0(do_dmfc0_tracecontrol, t0); /* PDtrace support */
4459
            rn = "TraceControl";
4460
//            break;
4461
        case 2:
4462
//            tcg_gen_helper_1_0(do_dmfc0_tracecontrol2, t0); /* PDtrace support */
4463
            rn = "TraceControl2";
4464
//            break;
4465
        case 3:
4466
//            tcg_gen_helper_1_0(do_dmfc0_usertracedata, t0); /* PDtrace support */
4467
            rn = "UserTraceData";
4468
//            break;
4469
        case 4:
4470
//            tcg_gen_helper_1_0(do_dmfc0_tracebpc, t0); /* PDtrace support */
4471
            rn = "TraceBPC";
4472
//            break;
4473
        default:
4474
            goto die;
4475
        }
4476
        break;
4477
    case 24:
4478
        switch (sel) {
4479
        case 0:
4480
            /* EJTAG support */
4481
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_DEPC));
4482
            rn = "DEPC";
4483
            break;
4484
        default:
4485
            goto die;
4486
        }
4487
        break;
4488
    case 25:
4489
        switch (sel) {
4490
        case 0:
4491
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_Performance0));
4492
            rn = "Performance0";
4493
            break;
4494
        case 1:
4495
//            tcg_gen_helper_1_0(do_dmfc0_performance1, t0);
4496
            rn = "Performance1";
4497
//            break;
4498
        case 2:
4499
//            tcg_gen_helper_1_0(do_dmfc0_performance2, t0);
4500
            rn = "Performance2";
4501
//            break;
4502
        case 3:
4503
//            tcg_gen_helper_1_0(do_dmfc0_performance3, t0);
4504
            rn = "Performance3";
4505
//            break;
4506
        case 4:
4507
//            tcg_gen_helper_1_0(do_dmfc0_performance4, t0);
4508
            rn = "Performance4";
4509
//            break;
4510
        case 5:
4511
//            tcg_gen_helper_1_0(do_dmfc0_performance5, t0);
4512
            rn = "Performance5";
4513
//            break;
4514
        case 6:
4515
//            tcg_gen_helper_1_0(do_dmfc0_performance6, t0);
4516
            rn = "Performance6";
4517
//            break;
4518
        case 7:
4519
//            tcg_gen_helper_1_0(do_dmfc0_performance7, t0);
4520
            rn = "Performance7";
4521
//            break;
4522
        default:
4523
            goto die;
4524
        }
4525
        break;
4526
    case 26:
4527
       rn = "ECC";
4528
       break;
4529
    case 27:
4530
        switch (sel) {
4531
        /* ignored */
4532
        case 0 ... 3:
4533
            rn = "CacheErr";
4534
            break;
4535
        default:
4536
            goto die;
4537
        }
4538
        break;
4539
    case 28:
4540
        switch (sel) {
4541
        case 0:
4542
        case 2:
4543
        case 4:
4544
        case 6:
4545
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_TagLo));
4546
            rn = "TagLo";
4547
            break;
4548
        case 1:
4549
        case 3:
4550
        case 5:
4551
        case 7:
4552
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_DataLo));
4553
            rn = "DataLo";
4554
            break;
4555
        default:
4556
            goto die;
4557
        }
4558
        break;
4559
    case 29:
4560
        switch (sel) {
4561
        case 0:
4562
        case 2:
4563
        case 4:
4564
        case 6:
4565
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_TagHi));
4566
            rn = "TagHi";
4567
            break;
4568
        case 1:
4569
        case 3:
4570
        case 5:
4571
        case 7:
4572
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_DataHi));
4573
            rn = "DataHi";
4574
            break;
4575
        default:
4576
            goto die;
4577
        }
4578
        break;
4579
    case 30:
4580
        switch (sel) {
4581
        case 0:
4582
            tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_ErrorEPC));
4583
            rn = "ErrorEPC";
4584
            break;
4585
        default:
4586
            goto die;
4587
        }
4588
        break;
4589
    case 31:
4590
        switch (sel) {
4591
        case 0:
4592
            /* EJTAG support */
4593
            gen_mfc0_load32(t0, offsetof(CPUState, CP0_DESAVE));
4594
            rn = "DESAVE";
4595
            break;
4596
        default:
4597
            goto die;
4598
        }
4599
        break;
4600
    default:
4601
        goto die;
4602
    }
4603
#if defined MIPS_DEBUG_DISAS
4604
    if (loglevel & CPU_LOG_TB_IN_ASM) {
4605
        fprintf(logfile, "dmfc0 %s (reg %d sel %d)\n",
4606
                rn, reg, sel);
4607
    }
4608
#endif
4609
    return;
4610

    
4611
die:
4612
#if defined MIPS_DEBUG_DISAS
4613
    if (loglevel & CPU_LOG_TB_IN_ASM) {
4614
        fprintf(logfile, "dmfc0 %s (reg %d sel %d)\n",
4615
                rn, reg, sel);
4616
    }
4617
#endif
4618
    generate_exception(ctx, EXCP_RI);
4619
}
4620

    
4621
static void gen_dmtc0 (CPUState *env, DisasContext *ctx, TCGv t0, int reg, int sel)
4622
{
4623
    const char *rn = "invalid";
4624

    
4625
    if (sel != 0)
4626
        check_insn(env, ctx, ISA_MIPS64);
4627

    
4628
    if (use_icount)
4629
        gen_io_start();
4630

    
4631
    switch (reg) {
4632
    case 0:
4633
        switch (sel) {
4634
        case 0:
4635
            tcg_gen_helper_0_1(do_mtc0_index, t0);
4636
            rn = "Index";
4637
            break;
4638
        case 1:
4639
            check_insn(env, ctx, ASE_MT);
4640
            tcg_gen_helper_0_1(do_mtc0_mvpcontrol, t0);
4641
            rn = "MVPControl";
4642
            break;
4643
        case 2:
4644
            check_insn(env, ctx, ASE_MT);
4645
            /* ignored */
4646
            rn = "MVPConf0";
4647
            break;
4648
        case 3:
4649
            check_insn(env, ctx, ASE_MT);
4650
            /* ignored */
4651
            rn = "MVPConf1";
4652
            break;
4653
        default:
4654
            goto die;
4655
        }
4656
        break;
4657
    case 1:
4658
        switch (sel) {
4659
        case 0:
4660
            /* ignored */
4661
            rn = "Random";
4662
            break;
4663
        case 1:
4664
            check_insn(env, ctx, ASE_MT);
4665
            tcg_gen_helper_0_1(do_mtc0_vpecontrol, t0);
4666
            rn = "VPEControl";
4667
            break;
4668
        case 2:
4669
            check_insn(env, ctx, ASE_MT);
4670
            tcg_gen_helper_0_1(do_mtc0_vpeconf0, t0);
4671
            rn = "VPEConf0";
4672
            break;
4673
        case 3:
4674
            check_insn(env, ctx, ASE_MT);
4675
            tcg_gen_helper_0_1(do_mtc0_vpeconf1, t0);
4676
            rn = "VPEConf1";
4677
            break;
4678
        case 4:
4679
            check_insn(env, ctx, ASE_MT);
4680
            tcg_gen_helper_0_1(do_mtc0_yqmask, t0);
4681
            rn = "YQMask";
4682
            break;
4683
        case 5:
4684
            check_insn(env, ctx, ASE_MT);
4685
            tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_VPESchedule));
4686
            rn = "VPESchedule";
4687
            break;
4688
        case 6:
4689
            check_insn(env, ctx, ASE_MT);
4690
            tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_VPEScheFBack));
4691
            rn = "VPEScheFBack";
4692
            break;
4693
        case 7:
4694
            check_insn(env, ctx, ASE_MT);
4695
            tcg_gen_helper_0_1(do_mtc0_vpeopt, t0);
4696
            rn = "VPEOpt";
4697
            break;
4698
        default:
4699
            goto die;
4700
        }
4701
        break;
4702
    case 2:
4703
        switch (sel) {
4704
        case 0:
4705
            tcg_gen_helper_0_1(do_mtc0_entrylo0, t0);
4706
            rn = "EntryLo0";
4707
            break;
4708
        case 1:
4709
            check_insn(env, ctx, ASE_MT);
4710
            tcg_gen_helper_0_1(do_mtc0_tcstatus, t0);
4711
            rn = "TCStatus";
4712
            break;
4713
        case 2:
4714
            check_insn(env, ctx, ASE_MT);
4715
            tcg_gen_helper_0_1(do_mtc0_tcbind, t0);
4716
            rn = "TCBind";
4717
            break;
4718
        case 3:
4719
            check_insn(env, ctx, ASE_MT);
4720
            tcg_gen_helper_0_1(do_mtc0_tcrestart, t0);
4721
            rn = "TCRestart";
4722
            break;
4723
        case 4:
4724
            check_insn(env, ctx, ASE_MT);
4725
            tcg_gen_helper_0_1(do_mtc0_tchalt, t0);
4726
            rn = "TCHalt";
4727
            break;
4728
        case 5:
4729
            check_insn(env, ctx, ASE_MT);
4730
            tcg_gen_helper_0_1(do_mtc0_tccontext, t0);
4731
            rn = "TCContext";
4732
            break;
4733
        case 6:
4734
            check_insn(env, ctx, ASE_MT);
4735
            tcg_gen_helper_0_1(do_mtc0_tcschedule, t0);
4736
            rn = "TCSchedule";
4737
            break;
4738
        case 7:
4739
            check_insn(env, ctx, ASE_MT);
4740
            tcg_gen_helper_0_1(do_mtc0_tcschefback, t0);
4741
            rn = "TCScheFBack";
4742
            break;
4743
        default:
4744
            goto die;
4745
        }
4746
        break;
4747
    case 3:
4748
        switch (sel) {
4749
        case 0:
4750
            tcg_gen_helper_0_1(do_mtc0_entrylo1, t0);
4751
            rn = "EntryLo1";
4752
            break;
4753
        default:
4754
            goto die;
4755
        }
4756
        break;
4757
    case 4:
4758
        switch (sel) {
4759
        case 0:
4760
            tcg_gen_helper_0_1(do_mtc0_context, t0);
4761
            rn = "Context";
4762
            break;
4763
        case 1:
4764
//           tcg_gen_helper_0_1(do_mtc0_contextconfig, t0); /* SmartMIPS ASE */
4765
            rn = "ContextConfig";
4766
//           break;
4767
        default:
4768
            goto die;
4769
        }
4770
        break;
4771
    case 5:
4772
        switch (sel) {
4773
        case 0:
4774
            tcg_gen_helper_0_1(do_mtc0_pagemask, t0);
4775
            rn = "PageMask";
4776
            break;
4777
        case 1:
4778
            check_insn(env, ctx, ISA_MIPS32R2);
4779
            tcg_gen_helper_0_1(do_mtc0_pagegrain, t0);
4780
            rn = "PageGrain";
4781
            break;
4782
        default:
4783
            goto die;
4784
        }
4785
        break;
4786
    case 6:
4787
        switch (sel) {
4788
        case 0:
4789
            tcg_gen_helper_0_1(do_mtc0_wired, t0);
4790
            rn = "Wired";
4791
            break;
4792
        case 1:
4793
            check_insn(env, ctx, ISA_MIPS32R2);
4794
            tcg_gen_helper_0_1(do_mtc0_srsconf0, t0);
4795
            rn = "SRSConf0";
4796
            break;
4797
        case 2:
4798
            check_insn(env, ctx, ISA_MIPS32R2);
4799
            tcg_gen_helper_0_1(do_mtc0_srsconf1, t0);
4800
            rn = "SRSConf1";
4801
            break;
4802
        case 3:
4803
            check_insn(env, ctx, ISA_MIPS32R2);
4804
            tcg_gen_helper_0_1(do_mtc0_srsconf2, t0);
4805
            rn = "SRSConf2";
4806
            break;
4807
        case 4:
4808
            check_insn(env, ctx, ISA_MIPS32R2);
4809
            tcg_gen_helper_0_1(do_mtc0_srsconf3, t0);
4810
            rn = "SRSConf3";
4811
            break;
4812
        case 5:
4813
            check_insn(env, ctx, ISA_MIPS32R2);
4814
            tcg_gen_helper_0_1(do_mtc0_srsconf4, t0);
4815
            rn = "SRSConf4";
4816
            break;
4817
        default:
4818
            goto die;
4819
        }
4820
        break;
4821
    case 7:
4822
        switch (sel) {
4823
        case 0:
4824
            check_insn(env, ctx, ISA_MIPS32R2);
4825
            tcg_gen_helper_0_1(do_mtc0_hwrena, t0);
4826
            rn = "HWREna";
4827
            break;
4828
        default:
4829
            goto die;
4830
        }
4831
        break;
4832
    case 8:
4833
        /* ignored */
4834
        rn = "BadVAddr";
4835
        break;
4836
    case 9:
4837
        switch (sel) {
4838
        case 0:
4839
            tcg_gen_helper_0_1(do_mtc0_count, t0);
4840
            rn = "Count";
4841
            break;
4842
        /* 6,7 are implementation dependent */
4843
        default:
4844
            goto die;
4845
        }
4846
        /* Stop translation as we may have switched the execution mode */
4847
        ctx->bstate = BS_STOP;
4848
        break;
4849
    case 10:
4850
        switch (sel) {
4851
        case 0:
4852
            tcg_gen_helper_0_1(do_mtc0_entryhi, t0);
4853
            rn = "EntryHi";
4854
            break;
4855
        default:
4856
            goto die;
4857
        }
4858
        break;
4859
    case 11:
4860
        switch (sel) {
4861
        case 0:
4862
            tcg_gen_helper_0_1(do_mtc0_compare, t0);
4863
            rn = "Compare";
4864
            break;
4865
        /* 6,7 are implementation dependent */
4866
        default:
4867
            goto die;
4868
        }
4869
        /* Stop translation as we may have switched the execution mode */
4870
        ctx->bstate = BS_STOP;
4871
        break;
4872
    case 12:
4873
        switch (sel) {
4874
        case 0:
4875
            tcg_gen_helper_0_1(do_mtc0_status, t0);
4876
            /* BS_STOP isn't good enough here, hflags may have changed. */
4877
            gen_save_pc(ctx->pc + 4);
4878
            ctx->bstate = BS_EXCP;
4879
            rn = "Status";
4880
            break;
4881
        case 1:
4882
            check_insn(env, ctx, ISA_MIPS32R2);
4883
            tcg_gen_helper_0_1(do_mtc0_intctl, t0);
4884
            /* Stop translation as we may have switched the execution mode */
4885
            ctx->bstate = BS_STOP;
4886
            rn = "IntCtl";
4887
            break;
4888
        case 2:
4889
            check_insn(env, ctx, ISA_MIPS32R2);
4890
            tcg_gen_helper_0_1(do_mtc0_srsctl, t0);
4891
            /* Stop translation as we may have switched the execution mode */
4892
            ctx->bstate = BS_STOP;
4893
            rn = "SRSCtl";
4894
            break;
4895
        case 3:
4896
            check_insn(env, ctx, ISA_MIPS32R2);
4897
            gen_mtc0_store32(t0, offsetof(CPUState, CP0_SRSMap));
4898
            /* Stop translation as we may have switched the execution mode */
4899
            ctx->bstate = BS_STOP;
4900
            rn = "SRSMap";
4901
            break;
4902
        default:
4903
            goto die;
4904
        }
4905
        break;
4906
    case 13:
4907
        switch (sel) {
4908
        case 0:
4909
            tcg_gen_helper_0_1(do_mtc0_cause, t0);
4910
            rn = "Cause";
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
    case 14:
4919
        switch (sel) {
4920
        case 0:
4921
            tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_EPC));
4922
            rn = "EPC";
4923
            break;
4924
        default:
4925
            goto die;
4926
        }
4927
        break;
4928
    case 15:
4929
        switch (sel) {
4930
        case 0:
4931
            /* ignored */
4932
            rn = "PRid";
4933
            break;
4934
        case 1:
4935
            check_insn(env, ctx, ISA_MIPS32R2);
4936
            tcg_gen_helper_0_1(do_mtc0_ebase, t0);
4937
            rn = "EBase";
4938
            break;
4939
        default:
4940
            goto die;
4941
        }
4942
        break;
4943
    case 16:
4944
        switch (sel) {
4945
        case 0:
4946
            tcg_gen_helper_0_1(do_mtc0_config0, t0);
4947
            rn = "Config";
4948
            /* Stop translation as we may have switched the execution mode */
4949
            ctx->bstate = BS_STOP;
4950
            break;
4951
        case 1:
4952
            /* ignored */
4953
            rn = "Config1";
4954
            break;
4955
        case 2:
4956
            tcg_gen_helper_0_1(do_mtc0_config2, t0);
4957
            rn = "Config2";
4958
            /* Stop translation as we may have switched the execution mode */
4959
            ctx->bstate = BS_STOP;
4960
            break;
4961
        case 3:
4962
            /* ignored */
4963
            rn = "Config3";
4964
            break;
4965
        /* 6,7 are implementation dependent */
4966
        default:
4967
            rn = "Invalid config selector";
4968
            goto die;
4969
        }
4970
        break;
4971
    case 17:
4972
        switch (sel) {
4973
        case 0:
4974
            /* ignored */
4975
            rn = "LLAddr";
4976
            break;
4977
        default:
4978
            goto die;
4979
        }
4980
        break;
4981
    case 18:
4982
        switch (sel) {
4983
        case 0 ... 7:
4984
            tcg_gen_helper_0_1i(do_mtc0_watchlo, t0, sel);
4985
            rn = "WatchLo";
4986
            break;
4987
        default:
4988
            goto die;
4989
        }
4990
        break;
4991
    case 19:
4992
        switch (sel) {
4993
        case 0 ... 7:
4994
            tcg_gen_helper_0_1i(do_mtc0_watchhi, t0, sel);
4995
            rn = "WatchHi";
4996
            break;
4997
        default:
4998
            goto die;
4999
        }
5000
        break;
5001
    case 20:
5002
        switch (sel) {
5003
        case 0:
5004
            check_insn(env, ctx, ISA_MIPS3);
5005
            tcg_gen_helper_0_1(do_mtc0_xcontext, t0);
5006
            rn = "XContext";
5007
            break;
5008
        default:
5009
            goto die;
5010
        }
5011
        break;
5012
    case 21:
5013
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
5014
        switch (sel) {
5015
        case 0:
5016
            tcg_gen_helper_0_1(do_mtc0_framemask, t0);
5017
            rn = "Framemask";
5018
            break;
5019
        default:
5020
            goto die;
5021
        }
5022
        break;
5023
    case 22:
5024
        /* ignored */
5025
        rn = "Diagnostic"; /* implementation dependent */
5026
        break;
5027
    case 23:
5028
        switch (sel) {
5029
        case 0:
5030
            tcg_gen_helper_0_1(do_mtc0_debug, t0); /* EJTAG support */
5031
            /* BS_STOP isn't good enough here, hflags may have changed. */
5032
            gen_save_pc(ctx->pc + 4);
5033
            ctx->bstate = BS_EXCP;
5034
            rn = "Debug";
5035
            break;
5036
        case 1:
5037
//            tcg_gen_helper_0_1(do_mtc0_tracecontrol, t0); /* PDtrace support */
5038
            /* Stop translation as we may have switched the execution mode */
5039
            ctx->bstate = BS_STOP;
5040
            rn = "TraceControl";
5041
//            break;
5042
        case 2:
5043
//            tcg_gen_helper_0_1(do_mtc0_tracecontrol2, t0); /* PDtrace support */
5044
            /* Stop translation as we may have switched the execution mode */
5045
            ctx->bstate = BS_STOP;
5046
            rn = "TraceControl2";
5047
//            break;
5048
        case 3:
5049
//            tcg_gen_helper_0_1(do_mtc0_usertracedata, t0); /* PDtrace support */
5050
            /* Stop translation as we may have switched the execution mode */
5051
            ctx->bstate = BS_STOP;
5052
            rn = "UserTraceData";
5053
//            break;
5054
        case 4:
5055
//            tcg_gen_helper_0_1(do_mtc0_tracebpc, t0); /* PDtrace support */
5056
            /* Stop translation as we may have switched the execution mode */
5057
            ctx->bstate = BS_STOP;
5058
            rn = "TraceBPC";
5059
//            break;
5060
        default:
5061
            goto die;
5062
        }
5063
        break;
5064
    case 24:
5065
        switch (sel) {
5066
        case 0:
5067
            /* EJTAG support */
5068
            tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_DEPC));
5069
            rn = "DEPC";
5070
            break;
5071
        default:
5072
            goto die;
5073
        }
5074
        break;
5075
    case 25:
5076
        switch (sel) {
5077
        case 0:
5078
            tcg_gen_helper_0_1(do_mtc0_performance0, t0);
5079
            rn = "Performance0";
5080
            break;
5081
        case 1:
5082
//            tcg_gen_helper_0_1(do_mtc0_performance1, t0);
5083
            rn = "Performance1";
5084
//            break;
5085
        case 2:
5086
//            tcg_gen_helper_0_1(do_mtc0_performance2, t0);
5087
            rn = "Performance2";
5088
//            break;
5089
        case 3:
5090
//            tcg_gen_helper_0_1(do_mtc0_performance3, t0);
5091
            rn = "Performance3";
5092
//            break;
5093
        case 4:
5094
//            tcg_gen_helper_0_1(do_mtc0_performance4, t0);
5095
            rn = "Performance4";
5096
//            break;
5097
        case 5:
5098
//            tcg_gen_helper_0_1(do_mtc0_performance5, t0);
5099
            rn = "Performance5";
5100
//            break;
5101
        case 6:
5102
//            tcg_gen_helper_0_1(do_mtc0_performance6, t0);
5103
            rn = "Performance6";
5104
//            break;
5105
        case 7:
5106
//            tcg_gen_helper_0_1(do_mtc0_performance7, t0);
5107
            rn = "Performance7";
5108
//            break;
5109
        default:
5110
            goto die;
5111
        }
5112
        break;
5113
    case 26:
5114
        /* ignored */
5115
        rn = "ECC";
5116
        break;
5117
    case 27:
5118
        switch (sel) {
5119
        case 0 ... 3:
5120
            /* ignored */
5121
            rn = "CacheErr";
5122
            break;
5123
        default:
5124
            goto die;
5125
        }
5126
        break;
5127
    case 28:
5128
        switch (sel) {
5129
        case 0:
5130
        case 2:
5131
        case 4:
5132
        case 6:
5133
            tcg_gen_helper_0_1(do_mtc0_taglo, t0);
5134
            rn = "TagLo";
5135
            break;
5136
        case 1:
5137
        case 3:
5138
        case 5:
5139
        case 7:
5140
            tcg_gen_helper_0_1(do_mtc0_datalo, t0);
5141
            rn = "DataLo";
5142
            break;
5143
        default:
5144
            goto die;
5145
        }
5146
        break;
5147
    case 29:
5148
        switch (sel) {
5149
        case 0:
5150
        case 2:
5151
        case 4:
5152
        case 6:
5153
            tcg_gen_helper_0_1(do_mtc0_taghi, t0);
5154
            rn = "TagHi";
5155
            break;
5156
        case 1:
5157
        case 3:
5158
        case 5:
5159
        case 7:
5160
            tcg_gen_helper_0_1(do_mtc0_datahi, t0);
5161
            rn = "DataHi";
5162
            break;
5163
        default:
5164
            rn = "invalid sel";
5165
            goto die;
5166
        }
5167
        break;
5168
    case 30:
5169
        switch (sel) {
5170
        case 0:
5171
            tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_ErrorEPC));
5172
            rn = "ErrorEPC";
5173
            break;
5174
        default:
5175
            goto die;
5176
        }
5177
        break;
5178
    case 31:
5179
        switch (sel) {
5180
        case 0:
5181
            /* EJTAG support */
5182
            gen_mtc0_store32(t0, offsetof(CPUState, CP0_DESAVE));
5183
            rn = "DESAVE";
5184
            break;
5185
        default:
5186
            goto die;
5187
        }
5188
        /* Stop translation as we may have switched the execution mode */
5189
        ctx->bstate = BS_STOP;
5190
        break;
5191
    default:
5192
        goto die;
5193
    }
5194
#if defined MIPS_DEBUG_DISAS
5195
    if (loglevel & CPU_LOG_TB_IN_ASM) {
5196
        fprintf(logfile, "dmtc0 %s (reg %d sel %d)\n",
5197
                rn, reg, sel);
5198
    }
5199
#endif
5200
    tcg_temp_free(t0);
5201
    /* For simplicitly assume that all writes can cause interrupts.  */
5202
    if (use_icount) {
5203
        gen_io_end();
5204
        ctx->bstate = BS_STOP;
5205
    }
5206
    return;
5207

    
5208
die:
5209
    tcg_temp_free(t0);
5210
#if defined MIPS_DEBUG_DISAS
5211
    if (loglevel & CPU_LOG_TB_IN_ASM) {
5212
        fprintf(logfile, "dmtc0 %s (reg %d sel %d)\n",
5213
                rn, reg, sel);
5214
    }
5215
#endif
5216
    generate_exception(ctx, EXCP_RI);
5217
}
5218
#endif /* TARGET_MIPS64 */
5219

    
5220
static void gen_mftr(CPUState *env, DisasContext *ctx, int rt, int rd,
5221
                     int u, int sel, int h)
5222
{
5223
    int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
5224
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
5225

    
5226
    if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
5227
        ((env->tcs[other_tc].CP0_TCBind & (0xf << CP0TCBd_CurVPE)) !=
5228
         (env->active_tc.CP0_TCBind & (0xf << CP0TCBd_CurVPE))))
5229
        tcg_gen_movi_tl(t0, -1);
5230
    else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
5231
             (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC)))
5232
        tcg_gen_movi_tl(t0, -1);
5233
    else if (u == 0) {
5234
        switch (rt) {
5235
        case 2:
5236
            switch (sel) {
5237
            case 1:
5238
                tcg_gen_helper_1_1(do_mftc0_tcstatus, t0, t0);
5239
                break;
5240
            case 2:
5241
                tcg_gen_helper_1_1(do_mftc0_tcbind, t0, t0);
5242
                break;
5243
            case 3:
5244
                tcg_gen_helper_1_1(do_mftc0_tcrestart, t0, t0);
5245
                break;
5246
            case 4:
5247
                tcg_gen_helper_1_1(do_mftc0_tchalt, t0, t0);
5248
                break;
5249
            case 5:
5250
                tcg_gen_helper_1_1(do_mftc0_tccontext, t0, t0);
5251
                break;
5252
            case 6:
5253
                tcg_gen_helper_1_1(do_mftc0_tcschedule, t0, t0);
5254
                break;
5255
            case 7:
5256
                tcg_gen_helper_1_1(do_mftc0_tcschefback, t0, t0);
5257
                break;
5258
            default:
5259
                gen_mfc0(env, ctx, t0, rt, sel);
5260
                break;
5261
            }
5262
            break;
5263
        case 10:
5264
            switch (sel) {
5265
            case 0:
5266
                tcg_gen_helper_1_1(do_mftc0_entryhi, t0, t0);
5267
                break;
5268
            default:
5269
                gen_mfc0(env, ctx, t0, rt, sel);
5270
                break;
5271
            }
5272
        case 12:
5273
            switch (sel) {
5274
            case 0:
5275
                tcg_gen_helper_1_1(do_mftc0_status, t0, t0);
5276
                break;
5277
            default:
5278
                gen_mfc0(env, ctx, t0, rt, sel);
5279
                break;
5280
            }
5281
        case 23:
5282
            switch (sel) {
5283
            case 0:
5284
                tcg_gen_helper_1_1(do_mftc0_debug, t0, t0);
5285
                break;
5286
            default:
5287
                gen_mfc0(env, ctx, t0, rt, sel);
5288
                break;
5289
            }
5290
            break;
5291
        default:
5292
            gen_mfc0(env, ctx, t0, rt, sel);
5293
        }
5294
    } else switch (sel) {
5295
    /* GPR registers. */
5296
    case 0:
5297
        tcg_gen_helper_1_1i(do_mftgpr, t0, t0, rt);
5298
        break;
5299
    /* Auxiliary CPU registers */
5300
    case 1:
5301
        switch (rt) {
5302
        case 0:
5303
            tcg_gen_helper_1_1i(do_mftlo, t0, t0, 0);
5304
            break;
5305
        case 1:
5306
            tcg_gen_helper_1_1i(do_mfthi, t0, t0, 0);
5307
            break;
5308
        case 2:
5309
            tcg_gen_helper_1_1i(do_mftacx, t0, t0, 0);
5310
            break;
5311
        case 4:
5312
            tcg_gen_helper_1_1i(do_mftlo, t0, t0, 1);
5313
            break;
5314
        case 5:
5315
            tcg_gen_helper_1_1i(do_mfthi, t0, t0, 1);
5316
            break;
5317
        case 6:
5318
            tcg_gen_helper_1_1i(do_mftacx, t0, t0, 1);
5319
            break;
5320
        case 8:
5321
            tcg_gen_helper_1_1i(do_mftlo, t0, t0, 2);
5322
            break;
5323
        case 9:
5324
            tcg_gen_helper_1_1i(do_mfthi, t0, t0, 2);
5325
            break;
5326
        case 10:
5327
            tcg_gen_helper_1_1i(do_mftacx, t0, t0, 2);
5328
            break;
5329
        case 12:
5330
            tcg_gen_helper_1_1i(do_mftlo, t0, t0, 3);
5331
            break;
5332
        case 13:
5333
            tcg_gen_helper_1_1i(do_mfthi, t0, t0, 3);
5334
            break;
5335
        case 14:
5336
            tcg_gen_helper_1_1i(do_mftacx, t0, t0, 3);
5337
            break;
5338
        case 16:
5339
            tcg_gen_helper_1_1(do_mftdsp, t0, t0);
5340
            break;
5341
        default:
5342
            goto die;
5343
        }
5344
        break;
5345
    /* Floating point (COP1). */
5346
    case 2:
5347
        /* XXX: For now we support only a single FPU context. */
5348
        if (h == 0) {
5349
            gen_load_fpr32(fpu32_T[0], rt);
5350
            tcg_gen_ext_i32_tl(t0, fpu32_T[0]);
5351
        } else {
5352
            gen_load_fpr32h(fpu32h_T[0], rt);
5353
            tcg_gen_ext_i32_tl(t0, fpu32h_T[0]);
5354
        }
5355
        break;
5356
    case 3:
5357
        /* XXX: For now we support only a single FPU context. */
5358
        tcg_gen_helper_1_1i(do_cfc1, t0, t0, rt);
5359
        break;
5360
    /* COP2: Not implemented. */
5361
    case 4:
5362
    case 5:
5363
        /* fall through */
5364
    default:
5365
        goto die;
5366
    }
5367
#if defined MIPS_DEBUG_DISAS
5368
    if (loglevel & CPU_LOG_TB_IN_ASM) {
5369
        fprintf(logfile, "mftr (reg %d u %d sel %d h %d)\n",
5370
                rt, u, sel, h);
5371
    }
5372
#endif
5373
    gen_store_gpr(t0, rd);
5374
    tcg_temp_free(t0);
5375
    return;
5376

    
5377
die:
5378
    tcg_temp_free(t0);
5379
#if defined MIPS_DEBUG_DISAS
5380
    if (loglevel & CPU_LOG_TB_IN_ASM) {
5381
        fprintf(logfile, "mftr (reg %d u %d sel %d h %d)\n",
5382
                rt, u, sel, h);
5383
    }
5384
#endif
5385
    generate_exception(ctx, EXCP_RI);
5386
}
5387

    
5388
static void gen_mttr(CPUState *env, DisasContext *ctx, int rd, int rt,
5389
                     int u, int sel, int h)
5390
{
5391
    int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
5392
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
5393

    
5394
    gen_load_gpr(t0, rt);
5395
    if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
5396
        ((env->tcs[other_tc].CP0_TCBind & (0xf << CP0TCBd_CurVPE)) !=
5397
         (env->active_tc.CP0_TCBind & (0xf << CP0TCBd_CurVPE))))
5398
        /* NOP */ ;
5399
    else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
5400
             (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC)))
5401
        /* NOP */ ;
5402
    else if (u == 0) {
5403
        switch (rd) {
5404
        case 2:
5405
            switch (sel) {
5406
            case 1:
5407
                tcg_gen_helper_0_1(do_mttc0_tcstatus, t0);
5408
                break;
5409
            case 2:
5410
                tcg_gen_helper_0_1(do_mttc0_tcbind, t0);
5411
                break;
5412
            case 3:
5413
                tcg_gen_helper_0_1(do_mttc0_tcrestart, t0);
5414
                break;
5415
            case 4:
5416
                tcg_gen_helper_0_1(do_mttc0_tchalt, t0);
5417
                break;
5418
            case 5:
5419
                tcg_gen_helper_0_1(do_mttc0_tccontext, t0);
5420
                break;
5421
            case 6:
5422
                tcg_gen_helper_0_1(do_mttc0_tcschedule, t0);
5423
                break;
5424
            case 7:
5425
                tcg_gen_helper_0_1(do_mttc0_tcschefback, t0);
5426
                break;
5427
            default:
5428
                gen_mtc0(env, ctx, t0, rd, sel);
5429
                break;
5430
            }
5431
            break;
5432
        case 10:
5433
            switch (sel) {
5434
            case 0:
5435
                tcg_gen_helper_0_1(do_mttc0_entryhi, t0);
5436
                break;
5437
            default:
5438
                gen_mtc0(env, ctx, t0, rd, sel);
5439
                break;
5440
            }
5441
        case 12:
5442
            switch (sel) {
5443
            case 0:
5444
                tcg_gen_helper_0_1(do_mttc0_status, t0);
5445
                break;
5446
            default:
5447
                gen_mtc0(env, ctx, t0, rd, sel);
5448
                break;
5449
            }
5450
        case 23:
5451
            switch (sel) {
5452
            case 0:
5453
                tcg_gen_helper_0_1(do_mttc0_debug, t0);
5454
                break;
5455
            default:
5456
                gen_mtc0(env, ctx, t0, rd, sel);
5457
                break;
5458
            }
5459
            break;
5460
        default:
5461
            gen_mtc0(env, ctx, t0, rd, sel);
5462
        }
5463
    } else switch (sel) {
5464
    /* GPR registers. */
5465
    case 0:
5466
        tcg_gen_helper_0_1i(do_mttgpr, t0, rd);
5467
        break;
5468
    /* Auxiliary CPU registers */
5469
    case 1:
5470
        switch (rd) {
5471
        case 0:
5472
            tcg_gen_helper_0_1i(do_mttlo, t0, 0);
5473
            break;
5474
        case 1:
5475
            tcg_gen_helper_0_1i(do_mtthi, t0, 0);
5476
            break;
5477
        case 2:
5478
            tcg_gen_helper_0_1i(do_mttacx, t0, 0);
5479
            break;
5480
        case 4:
5481
            tcg_gen_helper_0_1i(do_mttlo, t0, 1);
5482
            break;
5483
        case 5:
5484
            tcg_gen_helper_0_1i(do_mtthi, t0, 1);
5485
            break;
5486
        case 6:
5487
            tcg_gen_helper_0_1i(do_mttacx, t0, 1);
5488
            break;
5489
        case 8:
5490
            tcg_gen_helper_0_1i(do_mttlo, t0, 2);
5491
            break;
5492
        case 9:
5493
            tcg_gen_helper_0_1i(do_mtthi, t0, 2);
5494
            break;
5495
        case 10:
5496
            tcg_gen_helper_0_1i(do_mttacx, t0, 2);
5497
            break;
5498
        case 12:
5499
            tcg_gen_helper_0_1i(do_mttlo, t0, 3);
5500
            break;
5501
        case 13:
5502
            tcg_gen_helper_0_1i(do_mtthi, t0, 3);
5503
            break;
5504
        case 14:
5505
            tcg_gen_helper_0_1i(do_mttacx, t0, 3);
5506
            break;
5507
        case 16:
5508
            tcg_gen_helper_0_1(do_mttdsp, t0);
5509
            break;
5510
        default:
5511
            goto die;
5512
        }
5513
        break;
5514
    /* Floating point (COP1). */
5515
    case 2:
5516
        /* XXX: For now we support only a single FPU context. */
5517
        if (h == 0) {
5518
            tcg_gen_trunc_tl_i32(fpu32_T[0], t0);
5519
            gen_store_fpr32(fpu32_T[0], rd);
5520
        } else {
5521
            tcg_gen_trunc_tl_i32(fpu32h_T[0], t0);
5522
            gen_store_fpr32h(fpu32h_T[0], rd);
5523
        }
5524
        break;
5525
    case 3:
5526
        /* XXX: For now we support only a single FPU context. */
5527
        tcg_gen_helper_0_1i(do_ctc1, t0, rd);
5528
        break;
5529
    /* COP2: Not implemented. */
5530
    case 4:
5531
    case 5:
5532
        /* fall through */
5533
    default:
5534
        goto die;
5535
    }
5536
#if defined MIPS_DEBUG_DISAS
5537
    if (loglevel & CPU_LOG_TB_IN_ASM) {
5538
        fprintf(logfile, "mttr (reg %d u %d sel %d h %d)\n",
5539
                rd, u, sel, h);
5540
    }
5541
#endif
5542
    tcg_temp_free(t0);
5543
    return;
5544

    
5545
die:
5546
    tcg_temp_free(t0);
5547
#if defined MIPS_DEBUG_DISAS
5548
    if (loglevel & CPU_LOG_TB_IN_ASM) {
5549
        fprintf(logfile, "mttr (reg %d u %d sel %d h %d)\n",
5550
                rd, u, sel, h);
5551
    }
5552
#endif
5553
    generate_exception(ctx, EXCP_RI);
5554
}
5555

    
5556
static void gen_cp0 (CPUState *env, DisasContext *ctx, uint32_t opc, int rt, int rd)
5557
{
5558
    const char *opn = "ldst";
5559

    
5560
    switch (opc) {
5561
    case OPC_MFC0:
5562
        if (rt == 0) {
5563
            /* Treat as NOP. */
5564
            return;
5565
        }
5566
        {
5567
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
5568

    
5569
            gen_mfc0(env, ctx, t0, rd, ctx->opcode & 0x7);
5570
            gen_store_gpr(t0, rt);
5571
            tcg_temp_free(t0);
5572
        }
5573
        opn = "mfc0";
5574
        break;
5575
    case OPC_MTC0:
5576
        {
5577
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
5578

    
5579
            gen_load_gpr(t0, rt);
5580
            save_cpu_state(ctx, 1);
5581
            gen_mtc0(env, ctx, t0, rd, ctx->opcode & 0x7);
5582
            tcg_temp_free(t0);
5583
        }
5584
        opn = "mtc0";
5585
        break;
5586
#if defined(TARGET_MIPS64)
5587
    case OPC_DMFC0:
5588
        check_insn(env, ctx, ISA_MIPS3);
5589
        if (rt == 0) {
5590
            /* Treat as NOP. */
5591
            return;
5592
        }
5593
        {
5594
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
5595

    
5596
            gen_dmfc0(env, ctx, t0, rd, ctx->opcode & 0x7);
5597
            gen_store_gpr(t0, rt);
5598
            tcg_temp_free(t0);
5599
        }
5600
        opn = "dmfc0";
5601
        break;
5602
    case OPC_DMTC0:
5603
        check_insn(env, ctx, ISA_MIPS3);
5604
        {
5605
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
5606

    
5607
            gen_load_gpr(t0, rt);
5608
            save_cpu_state(ctx, 1);
5609
            gen_dmtc0(env, ctx, t0, rd, ctx->opcode & 0x7);
5610
            tcg_temp_free(t0);
5611
        }
5612
        opn = "dmtc0";
5613
        break;
5614
#endif
5615
    case OPC_MFTR:
5616
        check_insn(env, ctx, ASE_MT);
5617
        if (rd == 0) {
5618
            /* Treat as NOP. */
5619
            return;
5620
        }
5621
        gen_mftr(env, ctx, rt, rd, (ctx->opcode >> 5) & 1,
5622
                 ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
5623
        opn = "mftr";
5624
        break;
5625
    case OPC_MTTR:
5626
        check_insn(env, ctx, ASE_MT);
5627
        gen_mttr(env, ctx, rd, rt, (ctx->opcode >> 5) & 1,
5628
                 ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
5629
        opn = "mttr";
5630
        break;
5631
    case OPC_TLBWI:
5632
        opn = "tlbwi";
5633
        if (!env->tlb->do_tlbwi)
5634
            goto die;
5635
        tcg_gen_helper_0_0(env->tlb->do_tlbwi);
5636
        break;
5637
    case OPC_TLBWR:
5638
        opn = "tlbwr";
5639
        if (!env->tlb->do_tlbwr)
5640
            goto die;
5641
        tcg_gen_helper_0_0(env->tlb->do_tlbwr);
5642
        break;
5643
    case OPC_TLBP:
5644
        opn = "tlbp";
5645
        if (!env->tlb->do_tlbp)
5646
            goto die;
5647
        tcg_gen_helper_0_0(env->tlb->do_tlbp);
5648
        break;
5649
    case OPC_TLBR:
5650
        opn = "tlbr";
5651
        if (!env->tlb->do_tlbr)
5652
            goto die;
5653
        tcg_gen_helper_0_0(env->tlb->do_tlbr);
5654
        break;
5655
    case OPC_ERET:
5656
        opn = "eret";
5657
        check_insn(env, ctx, ISA_MIPS2);
5658
        save_cpu_state(ctx, 1);
5659
        tcg_gen_helper_0_0(do_eret);
5660
        ctx->bstate = BS_EXCP;
5661
        break;
5662
    case OPC_DERET:
5663
        opn = "deret";
5664
        check_insn(env, ctx, ISA_MIPS32);
5665
        if (!(ctx->hflags & MIPS_HFLAG_DM)) {
5666
            MIPS_INVAL(opn);
5667
            generate_exception(ctx, EXCP_RI);
5668
        } else {
5669
            save_cpu_state(ctx, 1);
5670
            tcg_gen_helper_0_0(do_deret);
5671
            ctx->bstate = BS_EXCP;
5672
        }
5673
        break;
5674
    case OPC_WAIT:
5675
        opn = "wait";
5676
        check_insn(env, ctx, ISA_MIPS3 | ISA_MIPS32);
5677
        /* If we get an exception, we want to restart at next instruction */
5678
        ctx->pc += 4;
5679
        save_cpu_state(ctx, 1);
5680
        ctx->pc -= 4;
5681
        tcg_gen_helper_0_0(do_wait);
5682
        ctx->bstate = BS_EXCP;
5683
        break;
5684
    default:
5685
 die:
5686
        MIPS_INVAL(opn);
5687
        generate_exception(ctx, EXCP_RI);
5688
        return;
5689
    }
5690
    MIPS_DEBUG("%s %s %d", opn, regnames[rt], rd);
5691
}
5692
#endif /* !CONFIG_USER_ONLY */
5693

    
5694
/* CP1 Branches (before delay slot) */
5695
static void gen_compute_branch1 (CPUState *env, DisasContext *ctx, uint32_t op,
5696
                                 int32_t cc, int32_t offset)
5697
{
5698
    target_ulong btarget;
5699
    const char *opn = "cp1 cond branch";
5700
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
5701
    TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
5702

    
5703
    if (cc != 0)
5704
        check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
5705

    
5706
    btarget = ctx->pc + 4 + offset;
5707

    
5708
    switch (op) {
5709
    case OPC_BC1F:
5710
        {
5711
            int l1 = gen_new_label();
5712
            int l2 = gen_new_label();
5713
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
5714

    
5715
            get_fp_cond(r_tmp1);
5716
            tcg_gen_ext_i32_tl(t0, r_tmp1);
5717
            tcg_temp_free(r_tmp1);
5718
            tcg_gen_not_tl(t0, t0);
5719
            tcg_gen_movi_tl(t1, 0x1 << cc);
5720
            tcg_gen_and_tl(t0, t0, t1);
5721
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
5722
            tcg_gen_movi_tl(t0, 0);
5723
            tcg_gen_br(l2);
5724
            gen_set_label(l1);
5725
            tcg_gen_movi_tl(t0, 1);
5726
            gen_set_label(l2);
5727
        }
5728
        opn = "bc1f";
5729
        goto not_likely;
5730
    case OPC_BC1FL:
5731
        {
5732
            int l1 = gen_new_label();
5733
            int l2 = gen_new_label();
5734
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
5735

    
5736
            get_fp_cond(r_tmp1);
5737
            tcg_gen_ext_i32_tl(t0, r_tmp1);
5738
            tcg_temp_free(r_tmp1);
5739
            tcg_gen_not_tl(t0, t0);
5740
            tcg_gen_movi_tl(t1, 0x1 << cc);
5741
            tcg_gen_and_tl(t0, t0, t1);
5742
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
5743
            tcg_gen_movi_tl(t0, 0);
5744
            tcg_gen_br(l2);
5745
            gen_set_label(l1);
5746
            tcg_gen_movi_tl(t0, 1);
5747
            gen_set_label(l2);
5748
        }
5749
        opn = "bc1fl";
5750
        goto likely;
5751
    case OPC_BC1T:
5752
        {
5753
            int l1 = gen_new_label();
5754
            int l2 = gen_new_label();
5755
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
5756

    
5757
            get_fp_cond(r_tmp1);
5758
            tcg_gen_ext_i32_tl(t0, r_tmp1);
5759
            tcg_temp_free(r_tmp1);
5760
            tcg_gen_movi_tl(t1, 0x1 << cc);
5761
            tcg_gen_and_tl(t0, t0, t1);
5762
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
5763
            tcg_gen_movi_tl(t0, 0);
5764
            tcg_gen_br(l2);
5765
            gen_set_label(l1);
5766
            tcg_gen_movi_tl(t0, 1);
5767
            gen_set_label(l2);
5768
        }
5769
        opn = "bc1t";
5770
        goto not_likely;
5771
    case OPC_BC1TL:
5772
        {
5773
            int l1 = gen_new_label();
5774
            int l2 = gen_new_label();
5775
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
5776

    
5777
            get_fp_cond(r_tmp1);
5778
            tcg_gen_ext_i32_tl(t0, r_tmp1);
5779
            tcg_temp_free(r_tmp1);
5780
            tcg_gen_movi_tl(t1, 0x1 << cc);
5781
            tcg_gen_and_tl(t0, t0, t1);
5782
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
5783
            tcg_gen_movi_tl(t0, 0);
5784
            tcg_gen_br(l2);
5785
            gen_set_label(l1);
5786
            tcg_gen_movi_tl(t0, 1);
5787
            gen_set_label(l2);
5788
        }
5789
        opn = "bc1tl";
5790
    likely:
5791
        ctx->hflags |= MIPS_HFLAG_BL;
5792
        tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, bcond));
5793
        break;
5794
    case OPC_BC1FANY2:
5795
        {
5796
            int l1 = gen_new_label();
5797
            int l2 = gen_new_label();
5798
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
5799

    
5800
            get_fp_cond(r_tmp1);
5801
            tcg_gen_ext_i32_tl(t0, r_tmp1);
5802
            tcg_temp_free(r_tmp1);
5803
            tcg_gen_not_tl(t0, t0);
5804
            tcg_gen_movi_tl(t1, 0x3 << cc);
5805
            tcg_gen_and_tl(t0, t0, t1);
5806
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
5807
            tcg_gen_movi_tl(t0, 0);
5808
            tcg_gen_br(l2);
5809
            gen_set_label(l1);
5810
            tcg_gen_movi_tl(t0, 1);
5811
            gen_set_label(l2);
5812
        }
5813
        opn = "bc1any2f";
5814
        goto not_likely;
5815
    case OPC_BC1TANY2:
5816
        {
5817
            int l1 = gen_new_label();
5818
            int l2 = gen_new_label();
5819
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
5820

    
5821
            get_fp_cond(r_tmp1);
5822
            tcg_gen_ext_i32_tl(t0, r_tmp1);
5823
            tcg_temp_free(r_tmp1);
5824
            tcg_gen_movi_tl(t1, 0x3 << cc);
5825
            tcg_gen_and_tl(t0, t0, t1);
5826
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
5827
            tcg_gen_movi_tl(t0, 0);
5828
            tcg_gen_br(l2);
5829
            gen_set_label(l1);
5830
            tcg_gen_movi_tl(t0, 1);
5831
            gen_set_label(l2);
5832
        }
5833
        opn = "bc1any2t";
5834
        goto not_likely;
5835
    case OPC_BC1FANY4:
5836
        {
5837
            int l1 = gen_new_label();
5838
            int l2 = gen_new_label();
5839
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
5840

    
5841
            get_fp_cond(r_tmp1);
5842
            tcg_gen_ext_i32_tl(t0, r_tmp1);
5843
            tcg_temp_free(r_tmp1);
5844
            tcg_gen_not_tl(t0, t0);
5845
            tcg_gen_movi_tl(t1, 0xf << cc);
5846
            tcg_gen_and_tl(t0, t0, t1);
5847
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
5848
            tcg_gen_movi_tl(t0, 0);
5849
            tcg_gen_br(l2);
5850
            gen_set_label(l1);
5851
            tcg_gen_movi_tl(t0, 1);
5852
            gen_set_label(l2);
5853
        }
5854
        opn = "bc1any4f";
5855
        goto not_likely;
5856
    case OPC_BC1TANY4:
5857
        {
5858
            int l1 = gen_new_label();
5859
            int l2 = gen_new_label();
5860
            TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
5861

    
5862
            get_fp_cond(r_tmp1);
5863
            tcg_gen_ext_i32_tl(t0, r_tmp1);
5864
            tcg_temp_free(r_tmp1);
5865
            tcg_gen_movi_tl(t1, 0xf << cc);
5866
            tcg_gen_and_tl(t0, t0, t1);
5867
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
5868
            tcg_gen_movi_tl(t0, 0);
5869
            tcg_gen_br(l2);
5870
            gen_set_label(l1);
5871
            tcg_gen_movi_tl(t0, 1);
5872
            gen_set_label(l2);
5873
        }
5874
        opn = "bc1any4t";
5875
    not_likely:
5876
        ctx->hflags |= MIPS_HFLAG_BC;
5877
        tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, bcond));
5878
        break;
5879
    default:
5880
        MIPS_INVAL(opn);
5881
        generate_exception (ctx, EXCP_RI);
5882
        goto out;
5883
    }
5884
    MIPS_DEBUG("%s: cond %02x target " TARGET_FMT_lx, opn,
5885
               ctx->hflags, btarget);
5886
    ctx->btarget = btarget;
5887

    
5888
 out:
5889
    tcg_temp_free(t0);
5890
    tcg_temp_free(t1);
5891
}
5892

    
5893
/* Coprocessor 1 (FPU) */
5894

    
5895
#define FOP(func, fmt) (((fmt) << 21) | (func))
5896

    
5897
static void gen_cp1 (DisasContext *ctx, uint32_t opc, int rt, int fs)
5898
{
5899
    const char *opn = "cp1 move";
5900
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
5901

    
5902
    switch (opc) {
5903
    case OPC_MFC1:
5904
        gen_load_fpr32(fpu32_T[0], fs);
5905
        tcg_gen_ext_i32_tl(t0, fpu32_T[0]);
5906
        gen_store_gpr(t0, rt);
5907
        opn = "mfc1";
5908
        break;
5909
    case OPC_MTC1:
5910
        gen_load_gpr(t0, rt);
5911
        tcg_gen_trunc_tl_i32(fpu32_T[0], t0);
5912
        gen_store_fpr32(fpu32_T[0], fs);
5913
        opn = "mtc1";
5914
        break;
5915
    case OPC_CFC1:
5916
        tcg_gen_helper_1_i(do_cfc1, t0, fs);
5917
        gen_store_gpr(t0, rt);
5918
        opn = "cfc1";
5919
        break;
5920
    case OPC_CTC1:
5921
        gen_load_gpr(t0, rt);
5922
        tcg_gen_helper_0_1i(do_ctc1, t0, fs);
5923
        opn = "ctc1";
5924
        break;
5925
    case OPC_DMFC1:
5926
        gen_load_fpr64(ctx, fpu64_T[0], fs);
5927
        tcg_gen_mov_tl(t0, fpu64_T[0]);
5928
        gen_store_gpr(t0, rt);
5929
        opn = "dmfc1";
5930
        break;
5931
    case OPC_DMTC1:
5932
        gen_load_gpr(t0, rt);
5933
        tcg_gen_mov_tl(fpu64_T[0], t0);
5934
        gen_store_fpr64(ctx, fpu64_T[0], fs);
5935
        opn = "dmtc1";
5936
        break;
5937
    case OPC_MFHC1:
5938
        gen_load_fpr32h(fpu32h_T[0], fs);
5939
        tcg_gen_ext_i32_tl(t0, fpu32h_T[0]);
5940
        gen_store_gpr(t0, rt);
5941
        opn = "mfhc1";
5942
        break;
5943
    case OPC_MTHC1:
5944
        gen_load_gpr(t0, rt);
5945
        tcg_gen_trunc_tl_i32(fpu32h_T[0], t0);
5946
        gen_store_fpr32h(fpu32h_T[0], fs);
5947
        opn = "mthc1";
5948
        break;
5949
    default:
5950
        MIPS_INVAL(opn);
5951
        generate_exception (ctx, EXCP_RI);
5952
        goto out;
5953
    }
5954
    MIPS_DEBUG("%s %s %s", opn, regnames[rt], fregnames[fs]);
5955

    
5956
 out:
5957
    tcg_temp_free(t0);
5958
}
5959

    
5960
static void gen_movci (DisasContext *ctx, int rd, int rs, int cc, int tf)
5961
{
5962
    int l1 = gen_new_label();
5963
    uint32_t ccbit;
5964
    TCGCond cond;
5965
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
5966
    TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
5967

    
5968
    if (cc)
5969
        ccbit = 1 << (24 + cc);
5970
    else
5971
        ccbit = 1 << 23;
5972
    if (tf)
5973
        cond = TCG_COND_EQ;
5974
    else
5975
        cond = TCG_COND_NE;
5976

    
5977
    gen_load_gpr(t0, rd);
5978
    gen_load_gpr(t1, rs);
5979
    {
5980
        TCGv r_ptr = tcg_temp_new(TCG_TYPE_PTR);
5981
        TCGv r_tmp = tcg_temp_local_new(TCG_TYPE_I32);
5982

    
5983
        tcg_gen_ld_ptr(r_ptr, cpu_env, offsetof(CPUState, fpu));
5984
        tcg_gen_ld_i32(r_tmp, r_ptr, offsetof(CPUMIPSFPUContext, fcr31));
5985
        tcg_temp_free(r_ptr);
5986
        tcg_gen_andi_i32(r_tmp, r_tmp, ccbit);
5987
        tcg_gen_brcondi_i32(cond, r_tmp, 0, l1);
5988
        tcg_temp_free(r_tmp);
5989
    }
5990
    tcg_gen_mov_tl(t0, t1);
5991
    tcg_temp_free(t1);
5992

    
5993
    gen_set_label(l1);
5994
    gen_store_gpr(t0, rd);
5995
    tcg_temp_free(t0);
5996
}
5997

    
5998
static inline void gen_movcf_s (int cc, int tf)
5999
{
6000
    uint32_t ccbit;
6001
    int cond;
6002
    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
6003
    int l1 = gen_new_label();
6004

    
6005
    if (cc)
6006
        ccbit = 1 << (24 + cc);
6007
    else
6008
        ccbit = 1 << 23;
6009

    
6010
    if (tf)
6011
        cond = TCG_COND_EQ;
6012
    else
6013
        cond = TCG_COND_NE;
6014

    
6015
    tcg_gen_ld_i32(r_tmp1, current_fpu, offsetof(CPUMIPSFPUContext, fcr31));
6016
    tcg_gen_andi_i32(r_tmp1, r_tmp1, ccbit);
6017
    tcg_gen_brcondi_i32(cond, r_tmp1, 0, l1);
6018
    tcg_gen_movi_i32(fpu32_T[2], fpu32_T[0]);
6019
    gen_set_label(l1);
6020
    tcg_temp_free(r_tmp1);
6021
}
6022

    
6023
static inline void gen_movcf_d (int cc, int tf)
6024
{
6025
    uint32_t ccbit;
6026
    int cond;
6027
    TCGv r_tmp1 = tcg_temp_new(TCG_TYPE_I32);
6028
    int l1 = gen_new_label();
6029

    
6030
    if (cc)
6031
        ccbit = 1 << (24 + cc);
6032
    else
6033
        ccbit = 1 << 23;
6034

    
6035
    if (tf)
6036
        cond = TCG_COND_EQ;
6037
    else
6038
        cond = TCG_COND_NE;
6039

    
6040
    tcg_gen_ld_i32(r_tmp1, current_fpu, offsetof(CPUMIPSFPUContext, fcr31));
6041
    tcg_gen_andi_i32(r_tmp1, r_tmp1, ccbit);
6042
    tcg_gen_brcondi_i32(cond, r_tmp1, 0, l1);
6043
    tcg_gen_movi_i64(fpu64_T[2], fpu64_T[0]);
6044
    gen_set_label(l1);
6045
    tcg_temp_free(r_tmp1);
6046
}
6047

    
6048
static inline void gen_movcf_ps (int cc, int tf)
6049
{
6050
    int cond;
6051
    TCGv r_tmp1 = tcg_temp_local_new(TCG_TYPE_I32);
6052
    TCGv r_tmp2 = tcg_temp_local_new(TCG_TYPE_I32);
6053
    int l1 = gen_new_label();
6054
    int l2 = gen_new_label();
6055

    
6056
    if (tf)
6057
        cond = TCG_COND_EQ;
6058
    else
6059
        cond = TCG_COND_NE;
6060

    
6061
    get_fp_cond(r_tmp1);
6062
    tcg_gen_shri_i32(r_tmp1, r_tmp1, cc);
6063
    tcg_gen_andi_i32(r_tmp2, r_tmp1, 0x1);
6064
    tcg_gen_brcondi_i32(cond, r_tmp2, 0, l1);
6065
    tcg_gen_movi_i32(fpu32_T[2], fpu32_T[0]);
6066
    gen_set_label(l1);
6067
    tcg_gen_andi_i32(r_tmp2, r_tmp1, 0x2);
6068
    tcg_gen_brcondi_i32(cond, r_tmp2, 0, l2);
6069
    tcg_gen_movi_i32(fpu32h_T[2], fpu32h_T[0]);
6070
    gen_set_label(l2);
6071
    tcg_temp_free(r_tmp1);
6072
    tcg_temp_free(r_tmp2);
6073
}
6074

    
6075

    
6076
static void gen_farith (DisasContext *ctx, uint32_t op1,
6077
                        int ft, int fs, int fd, int cc)
6078
{
6079
    const char *opn = "farith";
6080
    const char *condnames[] = {
6081
            "c.f",
6082
            "c.un",
6083
            "c.eq",
6084
            "c.ueq",
6085
            "c.olt",
6086
            "c.ult",
6087
            "c.ole",
6088
            "c.ule",
6089
            "c.sf",
6090
            "c.ngle",
6091
            "c.seq",
6092
            "c.ngl",
6093
            "c.lt",
6094
            "c.nge",
6095
            "c.le",
6096
            "c.ngt",
6097
    };
6098
    const char *condnames_abs[] = {
6099
            "cabs.f",
6100
            "cabs.un",
6101
            "cabs.eq",
6102
            "cabs.ueq",
6103
            "cabs.olt",
6104
            "cabs.ult",
6105
            "cabs.ole",
6106
            "cabs.ule",
6107
            "cabs.sf",
6108
            "cabs.ngle",
6109
            "cabs.seq",
6110
            "cabs.ngl",
6111
            "cabs.lt",
6112
            "cabs.nge",
6113
            "cabs.le",
6114
            "cabs.ngt",
6115
    };
6116
    enum { BINOP, CMPOP, OTHEROP } optype = OTHEROP;
6117
    uint32_t func = ctx->opcode & 0x3f;
6118

    
6119
    switch (ctx->opcode & FOP(0x3f, 0x1f)) {
6120
    case FOP(0, 16):
6121
        gen_load_fpr32(fpu32_T[0], fs);
6122
        gen_load_fpr32(fpu32_T[1], ft);
6123
        tcg_gen_helper_0_0(do_float_add_s);
6124
        gen_store_fpr32(fpu32_T[2], fd);
6125
        opn = "add.s";
6126
        optype = BINOP;
6127
        break;
6128
    case FOP(1, 16):
6129
        gen_load_fpr32(fpu32_T[0], fs);
6130
        gen_load_fpr32(fpu32_T[1], ft);
6131
        tcg_gen_helper_0_0(do_float_sub_s);
6132
        gen_store_fpr32(fpu32_T[2], fd);
6133
        opn = "sub.s";
6134
        optype = BINOP;
6135
        break;
6136
    case FOP(2, 16):
6137
        gen_load_fpr32(fpu32_T[0], fs);
6138
        gen_load_fpr32(fpu32_T[1], ft);
6139
        tcg_gen_helper_0_0(do_float_mul_s);
6140
        gen_store_fpr32(fpu32_T[2], fd);
6141
        opn = "mul.s";
6142
        optype = BINOP;
6143
        break;
6144
    case FOP(3, 16):
6145
        gen_load_fpr32(fpu32_T[0], fs);
6146
        gen_load_fpr32(fpu32_T[1], ft);
6147
        tcg_gen_helper_0_0(do_float_div_s);
6148
        gen_store_fpr32(fpu32_T[2], fd);
6149
        opn = "div.s";
6150
        optype = BINOP;
6151
        break;
6152
    case FOP(4, 16):
6153
        gen_load_fpr32(fpu32_T[0], fs);
6154
        tcg_gen_helper_0_0(do_float_sqrt_s);
6155
        gen_store_fpr32(fpu32_T[2], fd);
6156
        opn = "sqrt.s";
6157
        break;
6158
    case FOP(5, 16):
6159
        gen_load_fpr32(fpu32_T[0], fs);
6160
        tcg_gen_helper_0_0(do_float_abs_s);
6161
        gen_store_fpr32(fpu32_T[2], fd);
6162
        opn = "abs.s";
6163
        break;
6164
    case FOP(6, 16):
6165
        gen_load_fpr32(fpu32_T[0], fs);
6166
        gen_store_fpr32(fpu32_T[0], fd);
6167
        opn = "mov.s";
6168
        break;
6169
    case FOP(7, 16):
6170
        gen_load_fpr32(fpu32_T[0], fs);
6171
        tcg_gen_helper_0_0(do_float_chs_s);
6172
        gen_store_fpr32(fpu32_T[2], fd);
6173
        opn = "neg.s";
6174
        break;
6175
    case FOP(8, 16):
6176
        check_cp1_64bitmode(ctx);
6177
        gen_load_fpr32(fpu32_T[0], fs);
6178
        tcg_gen_helper_0_0(do_float_roundl_s);
6179
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6180
        opn = "round.l.s";
6181
        break;
6182
    case FOP(9, 16):
6183
        check_cp1_64bitmode(ctx);
6184
        gen_load_fpr32(fpu32_T[0], fs);
6185
        tcg_gen_helper_0_0(do_float_truncl_s);
6186
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6187
        opn = "trunc.l.s";
6188
        break;
6189
    case FOP(10, 16):
6190
        check_cp1_64bitmode(ctx);
6191
        gen_load_fpr32(fpu32_T[0], fs);
6192
        tcg_gen_helper_0_0(do_float_ceill_s);
6193
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6194
        opn = "ceil.l.s";
6195
        break;
6196
    case FOP(11, 16):
6197
        check_cp1_64bitmode(ctx);
6198
        gen_load_fpr32(fpu32_T[0], fs);
6199
        tcg_gen_helper_0_0(do_float_floorl_s);
6200
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6201
        opn = "floor.l.s";
6202
        break;
6203
    case FOP(12, 16):
6204
        gen_load_fpr32(fpu32_T[0], fs);
6205
        tcg_gen_helper_0_0(do_float_roundw_s);
6206
        gen_store_fpr32(fpu32_T[2], fd);
6207
        opn = "round.w.s";
6208
        break;
6209
    case FOP(13, 16):
6210
        gen_load_fpr32(fpu32_T[0], fs);
6211
        tcg_gen_helper_0_0(do_float_truncw_s);
6212
        gen_store_fpr32(fpu32_T[2], fd);
6213
        opn = "trunc.w.s";
6214
        break;
6215
    case FOP(14, 16):
6216
        gen_load_fpr32(fpu32_T[0], fs);
6217
        tcg_gen_helper_0_0(do_float_ceilw_s);
6218
        gen_store_fpr32(fpu32_T[2], fd);
6219
        opn = "ceil.w.s";
6220
        break;
6221
    case FOP(15, 16):
6222
        gen_load_fpr32(fpu32_T[0], fs);
6223
        tcg_gen_helper_0_0(do_float_floorw_s);
6224
        gen_store_fpr32(fpu32_T[2], fd);
6225
        opn = "floor.w.s";
6226
        break;
6227
    case FOP(17, 16):
6228
        gen_load_fpr32(fpu32_T[0], fs);
6229
        gen_load_fpr32(fpu32_T[2], fd);
6230
        gen_movcf_s((ft >> 2) & 0x7, ft & 0x1);
6231
        gen_store_fpr32(fpu32_T[2], fd);
6232
        opn = "movcf.s";
6233
        break;
6234
    case FOP(18, 16):
6235
        gen_load_fpr32(fpu32_T[0], fs);
6236
        gen_load_fpr32(fpu32_T[2], fd);
6237
        {
6238
            int l1 = gen_new_label();
6239
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
6240

    
6241
            gen_load_gpr(t0, ft);
6242
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
6243
            tcg_temp_free(t0);
6244
            tcg_gen_mov_i32(fpu32_T[2], fpu32_T[0]);
6245
            gen_set_label(l1);
6246
        }
6247
        gen_store_fpr32(fpu32_T[2], fd);
6248
        opn = "movz.s";
6249
        break;
6250
    case FOP(19, 16):
6251
        gen_load_fpr32(fpu32_T[0], fs);
6252
        gen_load_fpr32(fpu32_T[2], fd);
6253
        {
6254
            int l1 = gen_new_label();
6255
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
6256

    
6257
            gen_load_gpr(t0, ft);
6258
            tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);
6259
            tcg_temp_free(t0);
6260
            tcg_gen_mov_i32(fpu32_T[2], fpu32_T[0]);
6261
            gen_set_label(l1);
6262
        }
6263
        gen_store_fpr32(fpu32_T[2], fd);
6264
        opn = "movn.s";
6265
        break;
6266
    case FOP(21, 16):
6267
        check_cop1x(ctx);
6268
        gen_load_fpr32(fpu32_T[0], fs);
6269
        tcg_gen_helper_0_0(do_float_recip_s);
6270
        gen_store_fpr32(fpu32_T[2], fd);
6271
        opn = "recip.s";
6272
        break;
6273
    case FOP(22, 16):
6274
        check_cop1x(ctx);
6275
        gen_load_fpr32(fpu32_T[0], fs);
6276
        tcg_gen_helper_0_0(do_float_rsqrt_s);
6277
        gen_store_fpr32(fpu32_T[2], fd);
6278
        opn = "rsqrt.s";
6279
        break;
6280
    case FOP(28, 16):
6281
        check_cp1_64bitmode(ctx);
6282
        gen_load_fpr32(fpu32_T[0], fs);
6283
        gen_load_fpr32(fpu32_T[2], fd);
6284
        tcg_gen_helper_0_0(do_float_recip2_s);
6285
        gen_store_fpr32(fpu32_T[2], fd);
6286
        opn = "recip2.s";
6287
        break;
6288
    case FOP(29, 16):
6289
        check_cp1_64bitmode(ctx);
6290
        gen_load_fpr32(fpu32_T[0], fs);
6291
        tcg_gen_helper_0_0(do_float_recip1_s);
6292
        gen_store_fpr32(fpu32_T[2], fd);
6293
        opn = "recip1.s";
6294
        break;
6295
    case FOP(30, 16):
6296
        check_cp1_64bitmode(ctx);
6297
        gen_load_fpr32(fpu32_T[0], fs);
6298
        tcg_gen_helper_0_0(do_float_rsqrt1_s);
6299
        gen_store_fpr32(fpu32_T[2], fd);
6300
        opn = "rsqrt1.s";
6301
        break;
6302
    case FOP(31, 16):
6303
        check_cp1_64bitmode(ctx);
6304
        gen_load_fpr32(fpu32_T[0], fs);
6305
        gen_load_fpr32(fpu32_T[2], ft);
6306
        tcg_gen_helper_0_0(do_float_rsqrt2_s);
6307
        gen_store_fpr32(fpu32_T[2], fd);
6308
        opn = "rsqrt2.s";
6309
        break;
6310
    case FOP(33, 16):
6311
        check_cp1_registers(ctx, fd);
6312
        gen_load_fpr32(fpu32_T[0], fs);
6313
        tcg_gen_helper_0_0(do_float_cvtd_s);
6314
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6315
        opn = "cvt.d.s";
6316
        break;
6317
    case FOP(36, 16):
6318
        gen_load_fpr32(fpu32_T[0], fs);
6319
        tcg_gen_helper_0_0(do_float_cvtw_s);
6320
        gen_store_fpr32(fpu32_T[2], fd);
6321
        opn = "cvt.w.s";
6322
        break;
6323
    case FOP(37, 16):
6324
        check_cp1_64bitmode(ctx);
6325
        gen_load_fpr32(fpu32_T[0], fs);
6326
        tcg_gen_helper_0_0(do_float_cvtl_s);
6327
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6328
        opn = "cvt.l.s";
6329
        break;
6330
    case FOP(38, 16):
6331
        check_cp1_64bitmode(ctx);
6332
        gen_load_fpr32(fpu32_T[0], fs);
6333
        gen_load_fpr32(fpu32_T[1], ft);
6334
        tcg_gen_extu_i32_i64(fpu64_T[0], fpu32_T[0]);
6335
        tcg_gen_extu_i32_i64(fpu64_T[1], fpu32_T[1]);
6336
        tcg_gen_shli_i64(fpu64_T[1], fpu64_T[1], 32);
6337
        tcg_gen_or_i64(fpu64_T[2], fpu64_T[0], fpu64_T[1]);
6338
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6339
        opn = "cvt.ps.s";
6340
        break;
6341
    case FOP(48, 16):
6342
    case FOP(49, 16):
6343
    case FOP(50, 16):
6344
    case FOP(51, 16):
6345
    case FOP(52, 16):
6346
    case FOP(53, 16):
6347
    case FOP(54, 16):
6348
    case FOP(55, 16):
6349
    case FOP(56, 16):
6350
    case FOP(57, 16):
6351
    case FOP(58, 16):
6352
    case FOP(59, 16):
6353
    case FOP(60, 16):
6354
    case FOP(61, 16):
6355
    case FOP(62, 16):
6356
    case FOP(63, 16):
6357
        gen_load_fpr32(fpu32_T[0], fs);
6358
        gen_load_fpr32(fpu32_T[1], ft);
6359
        if (ctx->opcode & (1 << 6)) {
6360
            check_cop1x(ctx);
6361
            gen_cmpabs_s(func-48, cc);
6362
            opn = condnames_abs[func-48];
6363
        } else {
6364
            gen_cmp_s(func-48, cc);
6365
            opn = condnames[func-48];
6366
        }
6367
        break;
6368
    case FOP(0, 17):
6369
        check_cp1_registers(ctx, fs | ft | fd);
6370
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6371
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6372
        tcg_gen_helper_0_0(do_float_add_d);
6373
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6374
        opn = "add.d";
6375
        optype = BINOP;
6376
        break;
6377
    case FOP(1, 17):
6378
        check_cp1_registers(ctx, fs | ft | fd);
6379
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6380
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6381
        tcg_gen_helper_0_0(do_float_sub_d);
6382
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6383
        opn = "sub.d";
6384
        optype = BINOP;
6385
        break;
6386
    case FOP(2, 17):
6387
        check_cp1_registers(ctx, fs | ft | fd);
6388
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6389
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6390
        tcg_gen_helper_0_0(do_float_mul_d);
6391
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6392
        opn = "mul.d";
6393
        optype = BINOP;
6394
        break;
6395
    case FOP(3, 17):
6396
        check_cp1_registers(ctx, fs | ft | fd);
6397
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6398
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6399
        tcg_gen_helper_0_0(do_float_div_d);
6400
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6401
        opn = "div.d";
6402
        optype = BINOP;
6403
        break;
6404
    case FOP(4, 17):
6405
        check_cp1_registers(ctx, fs | fd);
6406
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6407
        tcg_gen_helper_0_0(do_float_sqrt_d);
6408
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6409
        opn = "sqrt.d";
6410
        break;
6411
    case FOP(5, 17):
6412
        check_cp1_registers(ctx, fs | fd);
6413
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6414
        tcg_gen_helper_0_0(do_float_abs_d);
6415
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6416
        opn = "abs.d";
6417
        break;
6418
    case FOP(6, 17):
6419
        check_cp1_registers(ctx, fs | fd);
6420
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6421
        gen_store_fpr64(ctx, fpu64_T[0], fd);
6422
        opn = "mov.d";
6423
        break;
6424
    case FOP(7, 17):
6425
        check_cp1_registers(ctx, fs | fd);
6426
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6427
        tcg_gen_helper_0_0(do_float_chs_d);
6428
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6429
        opn = "neg.d";
6430
        break;
6431
    case FOP(8, 17):
6432
        check_cp1_64bitmode(ctx);
6433
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6434
        tcg_gen_helper_0_0(do_float_roundl_d);
6435
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6436
        opn = "round.l.d";
6437
        break;
6438
    case FOP(9, 17):
6439
        check_cp1_64bitmode(ctx);
6440
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6441
        tcg_gen_helper_0_0(do_float_truncl_d);
6442
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6443
        opn = "trunc.l.d";
6444
        break;
6445
    case FOP(10, 17):
6446
        check_cp1_64bitmode(ctx);
6447
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6448
        tcg_gen_helper_0_0(do_float_ceill_d);
6449
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6450
        opn = "ceil.l.d";
6451
        break;
6452
    case FOP(11, 17):
6453
        check_cp1_64bitmode(ctx);
6454
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6455
        tcg_gen_helper_0_0(do_float_floorl_d);
6456
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6457
        opn = "floor.l.d";
6458
        break;
6459
    case FOP(12, 17):
6460
        check_cp1_registers(ctx, fs);
6461
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6462
        tcg_gen_helper_0_0(do_float_roundw_d);
6463
        gen_store_fpr32(fpu32_T[2], fd);
6464
        opn = "round.w.d";
6465
        break;
6466
    case FOP(13, 17):
6467
        check_cp1_registers(ctx, fs);
6468
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6469
        tcg_gen_helper_0_0(do_float_truncw_d);
6470
        gen_store_fpr32(fpu32_T[2], fd);
6471
        opn = "trunc.w.d";
6472
        break;
6473
    case FOP(14, 17):
6474
        check_cp1_registers(ctx, fs);
6475
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6476
        tcg_gen_helper_0_0(do_float_ceilw_d);
6477
        gen_store_fpr32(fpu32_T[2], fd);
6478
        opn = "ceil.w.d";
6479
        break;
6480
    case FOP(15, 17):
6481
        check_cp1_registers(ctx, fs);
6482
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6483
        tcg_gen_helper_0_0(do_float_floorw_d);
6484
        gen_store_fpr32(fpu32_T[2], fd);
6485
        opn = "floor.w.d";
6486
        break;
6487
    case FOP(17, 17):
6488
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6489
        gen_load_fpr64(ctx, fpu64_T[2], fd);
6490
        gen_movcf_d((ft >> 2) & 0x7, ft & 0x1);
6491
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6492
        opn = "movcf.d";
6493
        break;
6494
    case FOP(18, 17):
6495
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6496
        gen_load_fpr64(ctx, fpu64_T[2], fd);
6497
        {
6498
            int l1 = gen_new_label();
6499
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
6500

    
6501
            gen_load_gpr(t0, ft);
6502
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
6503
            tcg_temp_free(t0);
6504
            tcg_gen_mov_i64(fpu64_T[2], fpu64_T[0]);
6505
            gen_set_label(l1);
6506
        }
6507
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6508
        opn = "movz.d";
6509
        break;
6510
    case FOP(19, 17):
6511
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6512
        gen_load_fpr64(ctx, fpu64_T[2], fd);
6513
        {
6514
            int l1 = gen_new_label();
6515
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
6516

    
6517
            gen_load_gpr(t0, ft);
6518
            tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);
6519
            tcg_temp_free(t0);
6520
            tcg_gen_mov_i64(fpu64_T[2], fpu64_T[0]);
6521
            gen_set_label(l1);
6522
        }
6523
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6524
        opn = "movn.d";
6525
        break;
6526
    case FOP(21, 17):
6527
        check_cp1_64bitmode(ctx);
6528
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6529
        tcg_gen_helper_0_0(do_float_recip_d);
6530
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6531
        opn = "recip.d";
6532
        break;
6533
    case FOP(22, 17):
6534
        check_cp1_64bitmode(ctx);
6535
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6536
        tcg_gen_helper_0_0(do_float_rsqrt_d);
6537
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6538
        opn = "rsqrt.d";
6539
        break;
6540
    case FOP(28, 17):
6541
        check_cp1_64bitmode(ctx);
6542
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6543
        gen_load_fpr64(ctx, fpu64_T[2], ft);
6544
        tcg_gen_helper_0_0(do_float_recip2_d);
6545
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6546
        opn = "recip2.d";
6547
        break;
6548
    case FOP(29, 17):
6549
        check_cp1_64bitmode(ctx);
6550
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6551
        tcg_gen_helper_0_0(do_float_recip1_d);
6552
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6553
        opn = "recip1.d";
6554
        break;
6555
    case FOP(30, 17):
6556
        check_cp1_64bitmode(ctx);
6557
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6558
        tcg_gen_helper_0_0(do_float_rsqrt1_d);
6559
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6560
        opn = "rsqrt1.d";
6561
        break;
6562
    case FOP(31, 17):
6563
        check_cp1_64bitmode(ctx);
6564
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6565
        gen_load_fpr64(ctx, fpu64_T[2], ft);
6566
        tcg_gen_helper_0_0(do_float_rsqrt2_d);
6567
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6568
        opn = "rsqrt2.d";
6569
        break;
6570
    case FOP(48, 17):
6571
    case FOP(49, 17):
6572
    case FOP(50, 17):
6573
    case FOP(51, 17):
6574
    case FOP(52, 17):
6575
    case FOP(53, 17):
6576
    case FOP(54, 17):
6577
    case FOP(55, 17):
6578
    case FOP(56, 17):
6579
    case FOP(57, 17):
6580
    case FOP(58, 17):
6581
    case FOP(59, 17):
6582
    case FOP(60, 17):
6583
    case FOP(61, 17):
6584
    case FOP(62, 17):
6585
    case FOP(63, 17):
6586
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6587
        gen_load_fpr64(ctx, fpu64_T[1], ft);
6588
        if (ctx->opcode & (1 << 6)) {
6589
            check_cop1x(ctx);
6590
            check_cp1_registers(ctx, fs | ft);
6591
            gen_cmpabs_d(func-48, cc);
6592
            opn = condnames_abs[func-48];
6593
        } else {
6594
            check_cp1_registers(ctx, fs | ft);
6595
            gen_cmp_d(func-48, cc);
6596
            opn = condnames[func-48];
6597
        }
6598
        break;
6599
    case FOP(32, 17):
6600
        check_cp1_registers(ctx, fs);
6601
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6602
        tcg_gen_helper_0_0(do_float_cvts_d);
6603
        gen_store_fpr32(fpu32_T[2], fd);
6604
        opn = "cvt.s.d";
6605
        break;
6606
    case FOP(36, 17):
6607
        check_cp1_registers(ctx, fs);
6608
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6609
        tcg_gen_helper_0_0(do_float_cvtw_d);
6610
        gen_store_fpr32(fpu32_T[2], fd);
6611
        opn = "cvt.w.d";
6612
        break;
6613
    case FOP(37, 17):
6614
        check_cp1_64bitmode(ctx);
6615
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6616
        tcg_gen_helper_0_0(do_float_cvtl_d);
6617
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6618
        opn = "cvt.l.d";
6619
        break;
6620
    case FOP(32, 20):
6621
        gen_load_fpr32(fpu32_T[0], fs);
6622
        tcg_gen_helper_0_0(do_float_cvts_w);
6623
        gen_store_fpr32(fpu32_T[2], fd);
6624
        opn = "cvt.s.w";
6625
        break;
6626
    case FOP(33, 20):
6627
        check_cp1_registers(ctx, fd);
6628
        gen_load_fpr32(fpu32_T[0], fs);
6629
        tcg_gen_helper_0_0(do_float_cvtd_w);
6630
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6631
        opn = "cvt.d.w";
6632
        break;
6633
    case FOP(32, 21):
6634
        check_cp1_64bitmode(ctx);
6635
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6636
        tcg_gen_helper_0_0(do_float_cvts_l);
6637
        gen_store_fpr32(fpu32_T[2], fd);
6638
        opn = "cvt.s.l";
6639
        break;
6640
    case FOP(33, 21):
6641
        check_cp1_64bitmode(ctx);
6642
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6643
        tcg_gen_helper_0_0(do_float_cvtd_l);
6644
        gen_store_fpr64(ctx, fpu64_T[2], fd);
6645
        opn = "cvt.d.l";
6646
        break;
6647
    case FOP(38, 20):
6648
        check_cp1_64bitmode(ctx);
6649
        gen_load_fpr32(fpu32_T[0], fs);
6650
        gen_load_fpr32h(fpu32h_T[0], fs);
6651
        tcg_gen_helper_0_0(do_float_cvtps_pw);
6652
        gen_store_fpr32(fpu32_T[2], fd);
6653
        gen_store_fpr32h(fpu32h_T[2], fd);
6654
        opn = "cvt.ps.pw";
6655
        break;
6656
    case FOP(0, 22):
6657
        check_cp1_64bitmode(ctx);
6658
        gen_load_fpr32(fpu32_T[0], fs);
6659
        gen_load_fpr32h(fpu32h_T[0], fs);
6660
        gen_load_fpr32(fpu32_T[1], ft);
6661
        gen_load_fpr32h(fpu32h_T[1], ft);
6662
        tcg_gen_helper_0_0(do_float_add_ps);
6663
        gen_store_fpr32(fpu32_T[2], fd);
6664
        gen_store_fpr32h(fpu32h_T[2], fd);
6665
        opn = "add.ps";
6666
        break;
6667
    case FOP(1, 22):
6668
        check_cp1_64bitmode(ctx);
6669
        gen_load_fpr32(fpu32_T[0], fs);
6670
        gen_load_fpr32h(fpu32h_T[0], fs);
6671
        gen_load_fpr32(fpu32_T[1], ft);
6672
        gen_load_fpr32h(fpu32h_T[1], ft);
6673
        tcg_gen_helper_0_0(do_float_sub_ps);
6674
        gen_store_fpr32(fpu32_T[2], fd);
6675
        gen_store_fpr32h(fpu32h_T[2], fd);
6676
        opn = "sub.ps";
6677
        break;
6678
    case FOP(2, 22):
6679
        check_cp1_64bitmode(ctx);
6680
        gen_load_fpr32(fpu32_T[0], fs);
6681
        gen_load_fpr32h(fpu32h_T[0], fs);
6682
        gen_load_fpr32(fpu32_T[1], ft);
6683
        gen_load_fpr32h(fpu32h_T[1], ft);
6684
        tcg_gen_helper_0_0(do_float_mul_ps);
6685
        gen_store_fpr32(fpu32_T[2], fd);
6686
        gen_store_fpr32h(fpu32h_T[2], fd);
6687
        opn = "mul.ps";
6688
        break;
6689
    case FOP(5, 22):
6690
        check_cp1_64bitmode(ctx);
6691
        gen_load_fpr32(fpu32_T[0], fs);
6692
        gen_load_fpr32h(fpu32h_T[0], fs);
6693
        tcg_gen_helper_0_0(do_float_abs_ps);
6694
        gen_store_fpr32(fpu32_T[2], fd);
6695
        gen_store_fpr32h(fpu32h_T[2], fd);
6696
        opn = "abs.ps";
6697
        break;
6698
    case FOP(6, 22):
6699
        check_cp1_64bitmode(ctx);
6700
        gen_load_fpr32(fpu32_T[0], fs);
6701
        gen_load_fpr32h(fpu32h_T[0], fs);
6702
        gen_store_fpr32(fpu32_T[0], fd);
6703
        gen_store_fpr32h(fpu32h_T[0], fd);
6704
        opn = "mov.ps";
6705
        break;
6706
    case FOP(7, 22):
6707
        check_cp1_64bitmode(ctx);
6708
        gen_load_fpr32(fpu32_T[0], fs);
6709
        gen_load_fpr32h(fpu32h_T[0], fs);
6710
        tcg_gen_helper_0_0(do_float_chs_ps);
6711
        gen_store_fpr32(fpu32_T[2], fd);
6712
        gen_store_fpr32h(fpu32h_T[2], fd);
6713
        opn = "neg.ps";
6714
        break;
6715
    case FOP(17, 22):
6716
        check_cp1_64bitmode(ctx);
6717
        gen_load_fpr32(fpu32_T[0], fs);
6718
        gen_load_fpr32h(fpu32h_T[0], fs);
6719
        gen_load_fpr32(fpu32_T[2], fd);
6720
        gen_load_fpr32h(fpu32h_T[2], fd);
6721
        gen_movcf_ps((ft >> 2) & 0x7, ft & 0x1);
6722
        gen_store_fpr32(fpu32_T[2], fd);
6723
        gen_store_fpr32h(fpu32h_T[2], fd);
6724
        opn = "movcf.ps";
6725
        break;
6726
    case FOP(18, 22):
6727
        check_cp1_64bitmode(ctx);
6728
        gen_load_fpr32(fpu32_T[0], fs);
6729
        gen_load_fpr32h(fpu32h_T[0], fs);
6730
        gen_load_fpr32(fpu32_T[2], fd);
6731
        gen_load_fpr32h(fpu32h_T[2], fd);
6732
        {
6733
            int l1 = gen_new_label();
6734
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
6735

    
6736
            gen_load_gpr(t0, ft);
6737
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
6738
            tcg_temp_free(t0);
6739
            tcg_gen_mov_i32(fpu32_T[2], fpu32_T[0]);
6740
            tcg_gen_mov_i32(fpu32h_T[2], fpu32h_T[0]);
6741
            gen_set_label(l1);
6742
        }
6743
        gen_store_fpr32(fpu32_T[2], fd);
6744
        gen_store_fpr32h(fpu32h_T[2], fd);
6745
        opn = "movz.ps";
6746
        break;
6747
    case FOP(19, 22):
6748
        check_cp1_64bitmode(ctx);
6749
        gen_load_fpr32(fpu32_T[0], fs);
6750
        gen_load_fpr32h(fpu32h_T[0], fs);
6751
        gen_load_fpr32(fpu32_T[2], fd);
6752
        gen_load_fpr32h(fpu32h_T[2], fd);
6753
        {
6754
            int l1 = gen_new_label();
6755
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
6756

    
6757
            gen_load_gpr(t0, ft);
6758
            tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);
6759
            tcg_temp_free(t0);
6760
            tcg_gen_mov_i32(fpu32_T[2], fpu32_T[0]);
6761
            tcg_gen_mov_i32(fpu32h_T[2], fpu32h_T[0]);
6762
            gen_set_label(l1);
6763
        }
6764
        gen_store_fpr32(fpu32_T[2], fd);
6765
        gen_store_fpr32h(fpu32h_T[2], fd);
6766
        opn = "movn.ps";
6767
        break;
6768
    case FOP(24, 22):
6769
        check_cp1_64bitmode(ctx);
6770
        gen_load_fpr32(fpu32_T[0], ft);
6771
        gen_load_fpr32h(fpu32h_T[0], ft);
6772
        gen_load_fpr32(fpu32_T[1], fs);
6773
        gen_load_fpr32h(fpu32h_T[1], fs);
6774
        tcg_gen_helper_0_0(do_float_addr_ps);
6775
        gen_store_fpr32(fpu32_T[2], fd);
6776
        gen_store_fpr32h(fpu32h_T[2], fd);
6777
        opn = "addr.ps";
6778
        break;
6779
    case FOP(26, 22):
6780
        check_cp1_64bitmode(ctx);
6781
        gen_load_fpr32(fpu32_T[0], ft);
6782
        gen_load_fpr32h(fpu32h_T[0], ft);
6783
        gen_load_fpr32(fpu32_T[1], fs);
6784
        gen_load_fpr32h(fpu32h_T[1], fs);
6785
        tcg_gen_helper_0_0(do_float_mulr_ps);
6786
        gen_store_fpr32(fpu32_T[2], fd);
6787
        gen_store_fpr32h(fpu32h_T[2], fd);
6788
        opn = "mulr.ps";
6789
        break;
6790
    case FOP(28, 22):
6791
        check_cp1_64bitmode(ctx);
6792
        gen_load_fpr32(fpu32_T[0], fs);
6793
        gen_load_fpr32h(fpu32h_T[0], fs);
6794
        gen_load_fpr32(fpu32_T[2], fd);
6795
        gen_load_fpr32h(fpu32h_T[2], fd);
6796
        tcg_gen_helper_0_0(do_float_recip2_ps);
6797
        gen_store_fpr32(fpu32_T[2], fd);
6798
        gen_store_fpr32h(fpu32h_T[2], fd);
6799
        opn = "recip2.ps";
6800
        break;
6801
    case FOP(29, 22):
6802
        check_cp1_64bitmode(ctx);
6803
        gen_load_fpr32(fpu32_T[0], fs);
6804
        gen_load_fpr32h(fpu32h_T[0], fs);
6805
        tcg_gen_helper_0_0(do_float_recip1_ps);
6806
        gen_store_fpr32(fpu32_T[2], fd);
6807
        gen_store_fpr32h(fpu32h_T[2], fd);
6808
        opn = "recip1.ps";
6809
        break;
6810
    case FOP(30, 22):
6811
        check_cp1_64bitmode(ctx);
6812
        gen_load_fpr32(fpu32_T[0], fs);
6813
        gen_load_fpr32h(fpu32h_T[0], fs);
6814
        tcg_gen_helper_0_0(do_float_rsqrt1_ps);
6815
        gen_store_fpr32(fpu32_T[2], fd);
6816
        gen_store_fpr32h(fpu32h_T[2], fd);
6817
        opn = "rsqrt1.ps";
6818
        break;
6819
    case FOP(31, 22):
6820
        check_cp1_64bitmode(ctx);
6821
        gen_load_fpr32(fpu32_T[0], fs);
6822
        gen_load_fpr32h(fpu32h_T[0], fs);
6823
        gen_load_fpr32(fpu32_T[2], ft);
6824
        gen_load_fpr32h(fpu32h_T[2], ft);
6825
        tcg_gen_helper_0_0(do_float_rsqrt2_ps);
6826
        gen_store_fpr32(fpu32_T[2], fd);
6827
        gen_store_fpr32h(fpu32h_T[2], fd);
6828
        opn = "rsqrt2.ps";
6829
        break;
6830
    case FOP(32, 22):
6831
        check_cp1_64bitmode(ctx);
6832
        gen_load_fpr32h(fpu32h_T[0], fs);
6833
        tcg_gen_helper_0_0(do_float_cvts_pu);
6834
        gen_store_fpr32(fpu32_T[2], fd);
6835
        opn = "cvt.s.pu";
6836
        break;
6837
    case FOP(36, 22):
6838
        check_cp1_64bitmode(ctx);
6839
        gen_load_fpr32(fpu32_T[0], fs);
6840
        gen_load_fpr32h(fpu32h_T[0], fs);
6841
        tcg_gen_helper_0_0(do_float_cvtpw_ps);
6842
        gen_store_fpr32(fpu32_T[2], fd);
6843
        gen_store_fpr32h(fpu32h_T[2], fd);
6844
        opn = "cvt.pw.ps";
6845
        break;
6846
    case FOP(40, 22):
6847
        check_cp1_64bitmode(ctx);
6848
        gen_load_fpr32(fpu32_T[0], fs);
6849
        tcg_gen_helper_0_0(do_float_cvts_pl);
6850
        gen_store_fpr32(fpu32_T[2], fd);
6851
        opn = "cvt.s.pl";
6852
        break;
6853
    case FOP(44, 22):
6854
        check_cp1_64bitmode(ctx);
6855
        gen_load_fpr32(fpu32_T[0], fs);
6856
        gen_load_fpr32(fpu32_T[1], ft);
6857
        gen_store_fpr32h(fpu32_T[0], fd);
6858
        gen_store_fpr32(fpu32_T[1], fd);
6859
        opn = "pll.ps";
6860
        break;
6861
    case FOP(45, 22):
6862
        check_cp1_64bitmode(ctx);
6863
        gen_load_fpr32(fpu32_T[0], fs);
6864
        gen_load_fpr32h(fpu32h_T[1], ft);
6865
        gen_store_fpr32(fpu32h_T[1], fd);
6866
        gen_store_fpr32h(fpu32_T[0], fd);
6867
        opn = "plu.ps";
6868
        break;
6869
    case FOP(46, 22):
6870
        check_cp1_64bitmode(ctx);
6871
        gen_load_fpr32h(fpu32h_T[0], fs);
6872
        gen_load_fpr32(fpu32_T[1], ft);
6873
        gen_store_fpr32(fpu32_T[1], fd);
6874
        gen_store_fpr32h(fpu32h_T[0], fd);
6875
        opn = "pul.ps";
6876
        break;
6877
    case FOP(47, 22):
6878
        check_cp1_64bitmode(ctx);
6879
        gen_load_fpr32h(fpu32h_T[0], fs);
6880
        gen_load_fpr32h(fpu32h_T[1], ft);
6881
        gen_store_fpr32(fpu32h_T[1], fd);
6882
        gen_store_fpr32h(fpu32h_T[0], fd);
6883
        opn = "puu.ps";
6884
        break;
6885
    case FOP(48, 22):
6886
    case FOP(49, 22):
6887
    case FOP(50, 22):
6888
    case FOP(51, 22):
6889
    case FOP(52, 22):
6890
    case FOP(53, 22):
6891
    case FOP(54, 22):
6892
    case FOP(55, 22):
6893
    case FOP(56, 22):
6894
    case FOP(57, 22):
6895
    case FOP(58, 22):
6896
    case FOP(59, 22):
6897
    case FOP(60, 22):
6898
    case FOP(61, 22):
6899
    case FOP(62, 22):
6900
    case FOP(63, 22):
6901
        check_cp1_64bitmode(ctx);
6902
        gen_load_fpr32(fpu32_T[0], fs);
6903
        gen_load_fpr32h(fpu32h_T[0], fs);
6904
        gen_load_fpr32(fpu32_T[1], ft);
6905
        gen_load_fpr32h(fpu32h_T[1], ft);
6906
        if (ctx->opcode & (1 << 6)) {
6907
            gen_cmpabs_ps(func-48, cc);
6908
            opn = condnames_abs[func-48];
6909
        } else {
6910
            gen_cmp_ps(func-48, cc);
6911
            opn = condnames[func-48];
6912
        }
6913
        break;
6914
    default:
6915
        MIPS_INVAL(opn);
6916
        generate_exception (ctx, EXCP_RI);
6917
        return;
6918
    }
6919
    switch (optype) {
6920
    case BINOP:
6921
        MIPS_DEBUG("%s %s, %s, %s", opn, fregnames[fd], fregnames[fs], fregnames[ft]);
6922
        break;
6923
    case CMPOP:
6924
        MIPS_DEBUG("%s %s,%s", opn, fregnames[fs], fregnames[ft]);
6925
        break;
6926
    default:
6927
        MIPS_DEBUG("%s %s,%s", opn, fregnames[fd], fregnames[fs]);
6928
        break;
6929
    }
6930
}
6931

    
6932
/* Coprocessor 3 (FPU) */
6933
static void gen_flt3_ldst (DisasContext *ctx, uint32_t opc,
6934
                           int fd, int fs, int base, int index)
6935
{
6936
    const char *opn = "extended float load/store";
6937
    int store = 0;
6938
    TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
6939
    TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
6940

    
6941
    if (base == 0) {
6942
        gen_load_gpr(t0, index);
6943
    } else if (index == 0) {
6944
        gen_load_gpr(t0, base);
6945
    } else {
6946
        gen_load_gpr(t0, base);
6947
        gen_load_gpr(t1, index);
6948
        gen_op_addr_add(t0, t1);
6949
    }
6950
    /* Don't do NOP if destination is zero: we must perform the actual
6951
       memory access. */
6952
    switch (opc) {
6953
    case OPC_LWXC1:
6954
        check_cop1x(ctx);
6955
        tcg_gen_qemu_ld32s(fpu32_T[0], t0, ctx->mem_idx);
6956
        gen_store_fpr32(fpu32_T[0], fd);
6957
        opn = "lwxc1";
6958
        break;
6959
    case OPC_LDXC1:
6960
        check_cop1x(ctx);
6961
        check_cp1_registers(ctx, fd);
6962
        tcg_gen_qemu_ld64(fpu64_T[0], t0, ctx->mem_idx);
6963
        gen_store_fpr64(ctx, fpu64_T[0], fd);
6964
        opn = "ldxc1";
6965
        break;
6966
    case OPC_LUXC1:
6967
        check_cp1_64bitmode(ctx);
6968
        tcg_gen_andi_tl(t0, t0, ~0x7);
6969
        tcg_gen_qemu_ld64(fpu64_T[0], t0, ctx->mem_idx);
6970
        gen_store_fpr64(ctx, fpu64_T[0], fd);
6971
        opn = "luxc1";
6972
        break;
6973
    case OPC_SWXC1:
6974
        check_cop1x(ctx);
6975
        gen_load_fpr32(fpu32_T[0], fs);
6976
        tcg_gen_qemu_st32(fpu32_T[0], t0, ctx->mem_idx);
6977
        opn = "swxc1";
6978
        store = 1;
6979
        break;
6980
    case OPC_SDXC1:
6981
        check_cop1x(ctx);
6982
        check_cp1_registers(ctx, fs);
6983
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6984
        tcg_gen_qemu_st64(fpu64_T[0], t0, ctx->mem_idx);
6985
        opn = "sdxc1";
6986
        store = 1;
6987
        break;
6988
    case OPC_SUXC1:
6989
        check_cp1_64bitmode(ctx);
6990
        gen_load_fpr64(ctx, fpu64_T[0], fs);
6991
        tcg_gen_andi_tl(t0, t0, ~0x7);
6992
        tcg_gen_qemu_st64(fpu64_T[0], t0, ctx->mem_idx);
6993
        opn = "suxc1";
6994
        store = 1;
6995
        break;
6996
    default:
6997
        MIPS_INVAL(opn);
6998
        generate_exception(ctx, EXCP_RI);
6999
        tcg_temp_free(t0);
7000
        tcg_temp_free(t1);
7001
        return;
7002
    }
7003
    tcg_temp_free(t0);
7004
    tcg_temp_free(t1);
7005
    MIPS_DEBUG("%s %s, %s(%s)", opn, fregnames[store ? fs : fd],
7006
               regnames[index], regnames[base]);
7007
}
7008

    
7009
static void gen_flt3_arith (DisasContext *ctx, uint32_t opc,
7010
                            int fd, int fr, int fs, int ft)
7011
{
7012
    const char *opn = "flt3_arith";
7013

    
7014
    switch (opc) {
7015
    case OPC_ALNV_PS:
7016
        check_cp1_64bitmode(ctx);
7017
        {
7018
            TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
7019
            int l1 = gen_new_label();
7020
            int l2 = gen_new_label();
7021

    
7022
            gen_load_gpr(t0, fr);
7023
            tcg_gen_andi_tl(t0, t0, 0x7);
7024
            gen_load_fpr32(fpu32_T[0], fs);
7025
            gen_load_fpr32h(fpu32h_T[0], fs);
7026
            gen_load_fpr32(fpu32_T[1], ft);
7027
            gen_load_fpr32h(fpu32h_T[1], ft);
7028

    
7029
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
7030
            tcg_gen_mov_i32(fpu32_T[2], fpu32_T[0]);
7031
            tcg_gen_mov_i32(fpu32h_T[2], fpu32h_T[0]);
7032
            tcg_gen_br(l2);
7033
            gen_set_label(l1);
7034
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 4, l2);
7035
            tcg_temp_free(t0);
7036
#ifdef TARGET_WORDS_BIGENDIAN
7037
            tcg_gen_mov_i32(fpu32h_T[2], fpu32_T[0]);
7038
            tcg_gen_mov_i32(fpu32_T[2], fpu32h_T[1]);
7039
#else
7040
            tcg_gen_mov_i32(fpu32h_T[2], fpu32_T[1]);
7041
            tcg_gen_mov_i32(fpu32_T[2], fpu32h_T[0]);
7042
#endif
7043
            gen_set_label(l2);
7044
        }
7045
        gen_store_fpr32(fpu32_T[2], fd);
7046
        gen_store_fpr32h(fpu32h_T[2], fd);
7047
        opn = "alnv.ps";
7048
        break;
7049
    case OPC_MADD_S:
7050
        check_cop1x(ctx);
7051
        gen_load_fpr32(fpu32_T[0], fs);
7052
        gen_load_fpr32(fpu32_T[1], ft);
7053
        gen_load_fpr32(fpu32_T[2], fr);
7054
        tcg_gen_helper_0_0(do_float_muladd_s);
7055
        gen_store_fpr32(fpu32_T[2], fd);
7056
        opn = "madd.s";
7057
        break;
7058
    case OPC_MADD_D:
7059
        check_cop1x(ctx);
7060
        check_cp1_registers(ctx, fd | fs | ft | fr);
7061
        gen_load_fpr64(ctx, fpu64_T[0], fs);
7062
        gen_load_fpr64(ctx, fpu64_T[1], ft);
7063
        gen_load_fpr64(ctx, fpu64_T[2], fr);
7064
        tcg_gen_helper_0_0(do_float_muladd_d);
7065
        gen_store_fpr64(ctx, fpu64_T[2], fd);
7066
        opn = "madd.d";
7067
        break;
7068
    case OPC_MADD_PS:
7069
        check_cp1_64bitmode(ctx);
7070
        gen_load_fpr32(fpu32_T[0], fs);
7071
        gen_load_fpr32h(fpu32h_T[0], fs);
7072
        gen_load_fpr32(fpu32_T[1], ft);
7073
        gen_load_fpr32h(fpu32h_T[1], ft);
7074
        gen_load_fpr32(fpu32_T[2], fr);
7075
        gen_load_fpr32h(fpu32h_T[2], fr);
7076
        tcg_gen_helper_0_0(do_float_muladd_ps);
7077
        gen_store_fpr32(fpu32_T[2], fd);
7078
        gen_store_fpr32h(fpu32h_T[2], fd);
7079
        opn = "madd.ps";
7080
        break;
7081
    case OPC_MSUB_S:
7082
        check_cop1x(ctx);
7083
        gen_load_fpr32(fpu32_T[0], fs);
7084
        gen_load_fpr32(fpu32_T[1], ft);
7085
        gen_load_fpr32(fpu32_T[2], fr);
7086
        tcg_gen_helper_0_0(do_float_mulsub_s);
7087
        gen_store_fpr32(fpu32_T[2], fd);
7088
        opn = "msub.s";
7089
        break;
7090
    case OPC_MSUB_D:
7091
        check_cop1x(ctx);
7092
        check_cp1_registers(ctx, fd | fs | ft | fr);
7093
        gen_load_fpr64(ctx, fpu64_T[0], fs);
7094
        gen_load_fpr64(ctx, fpu64_T[1], ft);
7095
        gen_load_fpr64(ctx, fpu64_T[2], fr);
7096
        tcg_gen_helper_0_0(do_float_mulsub_d);
7097
        gen_store_fpr64(ctx, fpu64_T[2], fd);
7098
        opn = "msub.d";
7099
        break;
7100
    case OPC_MSUB_PS:
7101
        check_cp1_64bitmode(ctx);
7102
        gen_load_fpr32(fpu32_T[0], fs);
7103
        gen_load_fpr32h(fpu32h_T[0], fs);
7104
        gen_load_fpr32(fpu32_T[1], ft);
7105
        gen_load_fpr32h(fpu32h_T[1], ft);
7106
        gen_load_fpr32(fpu32_T[2], fr);
7107
        gen_load_fpr32h(fpu32h_T[2], fr);
7108
        tcg_gen_helper_0_0(do_float_mulsub_ps);
7109
        gen_store_fpr32(fpu32_T[2], fd);
7110
        gen_store_fpr32h(fpu32h_T[2], fd);
7111
        opn = "msub.ps";
7112
        break;
7113
    case OPC_NMADD_S:
7114
        check_cop1x(ctx);
7115
        gen_load_fpr32(fpu32_T[0], fs);
7116
        gen_load_fpr32(fpu32_T[1], ft);
7117
        gen_load_fpr32(fpu32_T[2], fr);
7118
        tcg_gen_helper_0_0(do_float_nmuladd_s);
7119
        gen_store_fpr32(fpu32_T[2], fd);
7120
        opn = "nmadd.s";
7121
        break;
7122
    case OPC_NMADD_D:
7123
        check_cop1x(ctx);
7124
        check_cp1_registers(ctx, fd | fs | ft | fr);
7125
        gen_load_fpr64(ctx, fpu64_T[0], fs);
7126
        gen_load_fpr64(ctx, fpu64_T[1], ft);
7127
        gen_load_fpr64(ctx, fpu64_T[2], fr);
7128
        tcg_gen_helper_0_0(do_float_nmuladd_d);
7129
        gen_store_fpr64(ctx, fpu64_T[2], fd);
7130
        opn = "nmadd.d";
7131
        break;
7132
    case OPC_NMADD_PS:
7133
        check_cp1_64bitmode(ctx);
7134
        gen_load_fpr32(fpu32_T[0], fs);
7135
        gen_load_fpr32h(fpu32h_T[0], fs);
7136
        gen_load_fpr32(fpu32_T[1], ft);
7137
        gen_load_fpr32h(fpu32h_T[1], ft);
7138
        gen_load_fpr32(fpu32_T[2], fr);
7139
        gen_load_fpr32h(fpu32h_T[2], fr);
7140
        tcg_gen_helper_0_0(do_float_nmuladd_ps);
7141
        gen_store_fpr32(fpu32_T[2], fd);
7142
        gen_store_fpr32h(fpu32h_T[2], fd);
7143
        opn = "nmadd.ps";
7144
        break;
7145
    case OPC_NMSUB_S:
7146
        check_cop1x(ctx);
7147
        gen_load_fpr32(fpu32_T[0], fs);
7148
        gen_load_fpr32(fpu32_T[1], ft);
7149
        gen_load_fpr32(fpu32_T[2], fr);
7150
        tcg_gen_helper_0_0(do_float_nmulsub_s);
7151
        gen_store_fpr32(fpu32_T[2], fd);
7152
        opn = "nmsub.s";
7153
        break;
7154
    case OPC_NMSUB_D:
7155
        check_cop1x(ctx);
7156
        check_cp1_registers(ctx, fd | fs | ft | fr);
7157
        gen_load_fpr64(ctx, fpu64_T[0], fs);
7158
        gen_load_fpr64(ctx, fpu64_T[1], ft);
7159
        gen_load_fpr64(ctx, fpu64_T[2], fr);
7160
        tcg_gen_helper_0_0(do_float_nmulsub_d);
7161
        gen_store_fpr64(ctx, fpu64_T[2], fd);
7162
        opn = "nmsub.d";
7163
        break;
7164
    case OPC_NMSUB_PS:
7165
        check_cp1_64bitmode(ctx);
7166
        gen_load_fpr32(fpu32_T[0], fs);
7167
        gen_load_fpr32h(fpu32h_T[0], fs);
7168
        gen_load_fpr32(fpu32_T[1], ft);
7169
        gen_load_fpr32h(fpu32h_T[1], ft);
7170
        gen_load_fpr32(fpu32_T[2], fr);
7171
        gen_load_fpr32h(fpu32h_T[2], fr);
7172
        tcg_gen_helper_0_0(do_float_nmulsub_ps);
7173
        gen_store_fpr32(fpu32_T[2], fd);
7174
        gen_store_fpr32h(fpu32h_T[2], fd);
7175
        opn = "nmsub.ps";
7176
        break;
7177
    default:
7178
        MIPS_INVAL(opn);
7179
        generate_exception (ctx, EXCP_RI);
7180
        return;
7181
    }
7182
    MIPS_DEBUG("%s %s, %s, %s, %s", opn, fregnames[fd], fregnames[fr],
7183
               fregnames[fs], fregnames[ft]);
7184
}
7185

    
7186
/* ISA extensions (ASEs) */
7187
/* MIPS16 extension to MIPS32 */
7188
/* SmartMIPS extension to MIPS32 */
7189

    
7190
#if defined(TARGET_MIPS64)
7191

    
7192
/* MDMX extension to MIPS64 */
7193

    
7194
#endif
7195

    
7196
static void decode_opc (CPUState *env, DisasContext *ctx)
7197
{
7198
    int32_t offset;
7199
    int rs, rt, rd, sa;
7200
    uint32_t op, op1, op2;
7201
    int16_t imm;
7202

    
7203
    /* make sure instructions are on a word boundary */
7204
    if (ctx->pc & 0x3) {
7205
        env->CP0_BadVAddr = ctx->pc;
7206
        generate_exception(ctx, EXCP_AdEL);
7207
        return;
7208
    }
7209

    
7210
    /* Handle blikely not taken case */
7211
    if ((ctx->hflags & MIPS_HFLAG_BMASK) == MIPS_HFLAG_BL) {
7212
        TCGv r_tmp = tcg_temp_local_new(TCG_TYPE_TL);
7213
        int l1 = gen_new_label();
7214

    
7215
        MIPS_DEBUG("blikely condition (" TARGET_FMT_lx ")", ctx->pc + 4);
7216
        tcg_gen_ld_tl(r_tmp, cpu_env, offsetof(CPUState, bcond));
7217
        tcg_gen_brcondi_tl(TCG_COND_NE, r_tmp, 0, l1);
7218
        tcg_temp_free(r_tmp);
7219
        {
7220
            TCGv r_tmp2 = tcg_temp_new(TCG_TYPE_I32);
7221

    
7222
            tcg_gen_movi_i32(r_tmp2, ctx->hflags & ~MIPS_HFLAG_BMASK);
7223
            tcg_gen_st_i32(r_tmp2, cpu_env, offsetof(CPUState, hflags));
7224
            tcg_temp_free(r_tmp2);
7225
        }
7226
        gen_goto_tb(ctx, 1, ctx->pc + 4);
7227
        gen_set_label(l1);
7228
    }
7229
    op = MASK_OP_MAJOR(ctx->opcode);
7230
    rs = (ctx->opcode >> 21) & 0x1f;
7231
    rt = (ctx->opcode >> 16) & 0x1f;
7232
    rd = (ctx->opcode >> 11) & 0x1f;
7233
    sa = (ctx->opcode >> 6) & 0x1f;
7234
    imm = (int16_t)ctx->opcode;
7235
    switch (op) {
7236
    case OPC_SPECIAL:
7237
        op1 = MASK_SPECIAL(ctx->opcode);
7238
        switch (op1) {
7239
        case OPC_SLL:          /* Arithmetic with immediate */
7240
        case OPC_SRL ... OPC_SRA:
7241
            gen_arith_imm(env, ctx, op1, rd, rt, sa);
7242
            break;
7243
        case OPC_MOVZ ... OPC_MOVN:
7244
            check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
7245
        case OPC_SLLV:         /* Arithmetic */
7246
        case OPC_SRLV ... OPC_SRAV:
7247
        case OPC_ADD ... OPC_NOR:
7248
        case OPC_SLT ... OPC_SLTU:
7249
            gen_arith(env, ctx, op1, rd, rs, rt);
7250
            break;
7251
        case OPC_MULT ... OPC_DIVU:
7252
            if (sa) {
7253
                check_insn(env, ctx, INSN_VR54XX);
7254
                op1 = MASK_MUL_VR54XX(ctx->opcode);
7255
                gen_mul_vr54xx(ctx, op1, rd, rs, rt);
7256
            } else
7257
                gen_muldiv(ctx, op1, rs, rt);
7258
            break;
7259
        case OPC_JR ... OPC_JALR:
7260
            gen_compute_branch(ctx, op1, rs, rd, sa);
7261
            return;
7262
        case OPC_TGE ... OPC_TEQ: /* Traps */
7263
        case OPC_TNE:
7264
            gen_trap(ctx, op1, rs, rt, -1);
7265
            break;
7266
        case OPC_MFHI:          /* Move from HI/LO */
7267
        case OPC_MFLO:
7268
            gen_HILO(ctx, op1, rd);
7269
            break;
7270
        case OPC_MTHI:
7271
        case OPC_MTLO:          /* Move to HI/LO */
7272
            gen_HILO(ctx, op1, rs);
7273
            break;
7274
        case OPC_PMON:          /* Pmon entry point, also R4010 selsl */
7275
#ifdef MIPS_STRICT_STANDARD
7276
            MIPS_INVAL("PMON / selsl");
7277
            generate_exception(ctx, EXCP_RI);
7278
#else
7279
            tcg_gen_helper_0_i(do_pmon, sa);
7280
#endif
7281
            break;
7282
        case OPC_SYSCALL:
7283
            generate_exception(ctx, EXCP_SYSCALL);
7284
            break;
7285
        case OPC_BREAK:
7286
            generate_exception(ctx, EXCP_BREAK);
7287
            break;
7288
        case OPC_SPIM:
7289
#ifdef MIPS_STRICT_STANDARD
7290
            MIPS_INVAL("SPIM");
7291
            generate_exception(ctx, EXCP_RI);
7292
#else
7293
           /* Implemented as RI exception for now. */
7294
            MIPS_INVAL("spim (unofficial)");
7295
            generate_exception(ctx, EXCP_RI);
7296
#endif
7297
            break;
7298
        case OPC_SYNC:
7299
            /* Treat as NOP. */
7300
            break;
7301

    
7302
        case OPC_MOVCI:
7303
            check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
7304
            if (env->CP0_Config1 & (1 << CP0C1_FP)) {
7305
                save_cpu_state(ctx, 1);
7306
                check_cp1_enabled(ctx);
7307
                gen_movci(ctx, rd, rs, (ctx->opcode >> 18) & 0x7,
7308
                          (ctx->opcode >> 16) & 1);
7309
            } else {
7310
                generate_exception_err(ctx, EXCP_CpU, 1);
7311
            }
7312
            break;
7313

    
7314
#if defined(TARGET_MIPS64)
7315
       /* MIPS64 specific opcodes */
7316
        case OPC_DSLL:
7317
        case OPC_DSRL ... OPC_DSRA:
7318
        case OPC_DSLL32:
7319
        case OPC_DSRL32 ... OPC_DSRA32:
7320
            check_insn(env, ctx, ISA_MIPS3);
7321
            check_mips_64(ctx);
7322
            gen_arith_imm(env, ctx, op1, rd, rt, sa);
7323
            break;
7324
        case OPC_DSLLV:
7325
        case OPC_DSRLV ... OPC_DSRAV:
7326
        case OPC_DADD ... OPC_DSUBU:
7327
            check_insn(env, ctx, ISA_MIPS3);
7328
            check_mips_64(ctx);
7329
            gen_arith(env, ctx, op1, rd, rs, rt);
7330
            break;
7331
        case OPC_DMULT ... OPC_DDIVU:
7332
            check_insn(env, ctx, ISA_MIPS3);
7333
            check_mips_64(ctx);
7334
            gen_muldiv(ctx, op1, rs, rt);
7335
            break;
7336
#endif
7337
        default:            /* Invalid */
7338
            MIPS_INVAL("special");
7339
            generate_exception(ctx, EXCP_RI);
7340
            break;
7341
        }
7342
        break;
7343
    case OPC_SPECIAL2:
7344
        op1 = MASK_SPECIAL2(ctx->opcode);
7345
        switch (op1) {
7346
        case OPC_MADD ... OPC_MADDU: /* Multiply and add/sub */
7347
        case OPC_MSUB ... OPC_MSUBU:
7348
            check_insn(env, ctx, ISA_MIPS32);
7349
            gen_muldiv(ctx, op1, rs, rt);
7350
            break;
7351
        case OPC_MUL:
7352
            gen_arith(env, ctx, op1, rd, rs, rt);
7353
            break;
7354
        case OPC_CLZ ... OPC_CLO:
7355
            check_insn(env, ctx, ISA_MIPS32);
7356
            gen_cl(ctx, op1, rd, rs);
7357
            break;
7358
        case OPC_SDBBP:
7359
            /* XXX: not clear which exception should be raised
7360
             *      when in debug mode...
7361
             */
7362
            check_insn(env, ctx, ISA_MIPS32);
7363
            if (!(ctx->hflags & MIPS_HFLAG_DM)) {
7364
                generate_exception(ctx, EXCP_DBp);
7365
            } else {
7366
                generate_exception(ctx, EXCP_DBp);
7367
            }
7368
            /* Treat as NOP. */
7369
            break;
7370
#if defined(TARGET_MIPS64)
7371
        case OPC_DCLZ ... OPC_DCLO:
7372
            check_insn(env, ctx, ISA_MIPS64);
7373
            check_mips_64(ctx);
7374
            gen_cl(ctx, op1, rd, rs);
7375
            break;
7376
#endif
7377
        default:            /* Invalid */
7378
            MIPS_INVAL("special2");
7379
            generate_exception(ctx, EXCP_RI);
7380
            break;
7381
        }
7382
        break;
7383
    case OPC_SPECIAL3:
7384
        op1 = MASK_SPECIAL3(ctx->opcode);
7385
        switch (op1) {
7386
        case OPC_EXT:
7387
        case OPC_INS:
7388
            check_insn(env, ctx, ISA_MIPS32R2);
7389
            gen_bitops(ctx, op1, rt, rs, sa, rd);
7390
            break;
7391
        case OPC_BSHFL:
7392
            check_insn(env, ctx, ISA_MIPS32R2);
7393
            op2 = MASK_BSHFL(ctx->opcode);
7394
            {
7395
                TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
7396
                TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
7397

    
7398
                switch (op2) {
7399
                case OPC_WSBH:
7400
                    gen_load_gpr(t1, rt);
7401
                    tcg_gen_helper_1_1(do_wsbh, t0, t1);
7402
                    gen_store_gpr(t0, rd);
7403
                    break;
7404
                case OPC_SEB:
7405
                    gen_load_gpr(t1, rt);
7406
                    tcg_gen_ext8s_tl(t0, t1);
7407
                    gen_store_gpr(t0, rd);
7408
                    break;
7409
                case OPC_SEH:
7410
                    gen_load_gpr(t1, rt);
7411
                    tcg_gen_ext16s_tl(t0, t1);
7412
                    gen_store_gpr(t0, rd);
7413
                    break;
7414
                default:            /* Invalid */
7415
                    MIPS_INVAL("bshfl");
7416
                    generate_exception(ctx, EXCP_RI);
7417
                    break;
7418
                }
7419
                tcg_temp_free(t0);
7420
                tcg_temp_free(t1);
7421
            }
7422
            break;
7423
        case OPC_RDHWR:
7424
            check_insn(env, ctx, ISA_MIPS32R2);
7425
            {
7426
                TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
7427

    
7428
                switch (rd) {
7429
                case 0:
7430
                    save_cpu_state(ctx, 1);
7431
                    tcg_gen_helper_1_0(do_rdhwr_cpunum, t0);
7432
                    break;
7433
                case 1:
7434
                    save_cpu_state(ctx, 1);
7435
                    tcg_gen_helper_1_0(do_rdhwr_synci_step, t0);
7436
                    break;
7437
                case 2:
7438
                    save_cpu_state(ctx, 1);
7439
                    tcg_gen_helper_1_0(do_rdhwr_cc, t0);
7440
                    break;
7441
                case 3:
7442
                    save_cpu_state(ctx, 1);
7443
                    tcg_gen_helper_1_0(do_rdhwr_ccres, t0);
7444
                    break;
7445
                case 29:
7446
#if defined (CONFIG_USER_ONLY)
7447
                    tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, tls_value));
7448
                    break;
7449
#else
7450
                    /* XXX: Some CPUs implement this in hardware. Not supported yet. */
7451
#endif
7452
                default:            /* Invalid */
7453
                    MIPS_INVAL("rdhwr");
7454
                    generate_exception(ctx, EXCP_RI);
7455
                    break;
7456
                }
7457
                gen_store_gpr(t0, rt);
7458
                tcg_temp_free(t0);
7459
            }
7460
            break;
7461
        case OPC_FORK:
7462
            check_insn(env, ctx, ASE_MT);
7463
            {
7464
                TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
7465
                TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
7466

    
7467
                gen_load_gpr(t0, rt);
7468
                gen_load_gpr(t1, rs);
7469
                tcg_gen_helper_0_2(do_fork, t0, t1);
7470
                tcg_temp_free(t0);
7471
                tcg_temp_free(t1);
7472
            }
7473
            break;
7474
        case OPC_YIELD:
7475
            check_insn(env, ctx, ASE_MT);
7476
            {
7477
                TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
7478

    
7479
                gen_load_gpr(t0, rs);
7480
                tcg_gen_helper_1_1(do_yield, t0, t0);
7481
                gen_store_gpr(t0, rd);
7482
                tcg_temp_free(t0);
7483
            }
7484
            break;
7485
#if defined(TARGET_MIPS64)
7486
        case OPC_DEXTM ... OPC_DEXT:
7487
        case OPC_DINSM ... OPC_DINS:
7488
            check_insn(env, ctx, ISA_MIPS64R2);
7489
            check_mips_64(ctx);
7490
            gen_bitops(ctx, op1, rt, rs, sa, rd);
7491
            break;
7492
        case OPC_DBSHFL:
7493
            check_insn(env, ctx, ISA_MIPS64R2);
7494
            check_mips_64(ctx);
7495
            op2 = MASK_DBSHFL(ctx->opcode);
7496
            {
7497
                TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
7498
                TCGv t1 = tcg_temp_local_new(TCG_TYPE_TL);
7499

    
7500
                switch (op2) {
7501
                case OPC_DSBH:
7502
                    gen_load_gpr(t1, rt);
7503
                    tcg_gen_helper_1_1(do_dsbh, t0, t1);
7504
                    break;
7505
                case OPC_DSHD:
7506
                    gen_load_gpr(t1, rt);
7507
                    tcg_gen_helper_1_1(do_dshd, t0, t1);
7508
                    break;
7509
                default:            /* Invalid */
7510
                    MIPS_INVAL("dbshfl");
7511
                    generate_exception(ctx, EXCP_RI);
7512
                    break;
7513
                }
7514
                gen_store_gpr(t0, rd);
7515
                tcg_temp_free(t0);
7516
                tcg_temp_free(t1);
7517
            }
7518
            break;
7519
#endif
7520
        default:            /* Invalid */
7521
            MIPS_INVAL("special3");
7522
            generate_exception(ctx, EXCP_RI);
7523
            break;
7524
        }
7525
        break;
7526
    case OPC_REGIMM:
7527
        op1 = MASK_REGIMM(ctx->opcode);
7528
        switch (op1) {
7529
        case OPC_BLTZ ... OPC_BGEZL: /* REGIMM branches */
7530
        case OPC_BLTZAL ... OPC_BGEZALL:
7531
            gen_compute_branch(ctx, op1, rs, -1, imm << 2);
7532
            return;
7533
        case OPC_TGEI ... OPC_TEQI: /* REGIMM traps */
7534
        case OPC_TNEI:
7535
            gen_trap(ctx, op1, rs, -1, imm);
7536
            break;
7537
        case OPC_SYNCI:
7538
            check_insn(env, ctx, ISA_MIPS32R2);
7539
            /* Treat as NOP. */
7540
            break;
7541
        default:            /* Invalid */
7542
            MIPS_INVAL("regimm");
7543
            generate_exception(ctx, EXCP_RI);
7544
            break;
7545
        }
7546
        break;
7547
    case OPC_CP0:
7548
        check_cp0_enabled(ctx);
7549
        op1 = MASK_CP0(ctx->opcode);
7550
        switch (op1) {
7551
        case OPC_MFC0:
7552
        case OPC_MTC0:
7553
        case OPC_MFTR:
7554
        case OPC_MTTR:
7555
#if defined(TARGET_MIPS64)
7556
        case OPC_DMFC0:
7557
        case OPC_DMTC0:
7558
#endif
7559
#ifndef CONFIG_USER_ONLY
7560
            gen_cp0(env, ctx, op1, rt, rd);
7561
#endif
7562
            break;
7563
        case OPC_C0_FIRST ... OPC_C0_LAST:
7564
#ifndef CONFIG_USER_ONLY
7565
            gen_cp0(env, ctx, MASK_C0(ctx->opcode), rt, rd);
7566
#endif
7567
            break;
7568
        case OPC_MFMC0:
7569
            op2 = MASK_MFMC0(ctx->opcode);
7570
            {
7571
                TCGv t0 = tcg_temp_local_new(TCG_TYPE_TL);
7572

    
7573
                switch (op2) {
7574
                case OPC_DMT:
7575
                    check_insn(env, ctx, ASE_MT);
7576
                    tcg_gen_helper_1_1(do_dmt, t0, t0);
7577
                    break;
7578
                case OPC_EMT:
7579
                    check_insn(env, ctx, ASE_MT);
7580
                    tcg_gen_helper_1_1(do_emt, t0, t0);
7581
                     break;
7582
                case OPC_DVPE:
7583
                    check_insn(env, ctx, ASE_MT);
7584
                    tcg_gen_helper_1_1(do_dvpe, t0, t0);
7585
                    break;
7586
                case OPC_EVPE:
7587
                    check_insn(env, ctx, ASE_MT);
7588
                    tcg_gen_helper_1_1(do_evpe, t0, t0);
7589
                    break;
7590
                case OPC_DI:
7591
                    check_insn(env, ctx, ISA_MIPS32R2);
7592
                    save_cpu_state(ctx, 1);
7593
                    tcg_gen_helper_1_0(do_di, t0);
7594
                    /* Stop translation as we may have switched the execution mode */
7595
                    ctx->bstate = BS_STOP;
7596
                    break;
7597
                case OPC_EI:
7598
                    check_insn(env, ctx, ISA_MIPS32R2);
7599
                    save_cpu_state(ctx, 1);
7600
                    tcg_gen_helper_1_0(do_ei, t0);
7601
                    /* Stop translation as we may have switched the execution mode */
7602
                    ctx->bstate = BS_STOP;
7603
                    break;
7604
                default:            /* Invalid */
7605
                    MIPS_INVAL("mfmc0");
7606
                    generate_exception(ctx, EXCP_RI);
7607
                    break;
7608
                }
7609
                gen_store_gpr(t0, rt);
7610
                tcg_temp_free(t0);
7611
            }
7612
            break;
7613
        case OPC_RDPGPR:
7614
            check_insn(env, ctx, ISA_MIPS32R2);
7615
            gen_load_srsgpr(rt, rd);
7616
            break;
7617
        case OPC_WRPGPR:
7618
            check_insn(env, ctx, ISA_MIPS32R2);
7619
            gen_store_srsgpr(rt, rd);
7620
            break;
7621
        default:
7622
            MIPS_INVAL("cp0");
7623
            generate_exception(ctx, EXCP_RI);
7624
            break;
7625
        }
7626
        break;
7627
    case OPC_ADDI ... OPC_LUI: /* Arithmetic with immediate opcode */
7628
         gen_arith_imm(env, ctx, op, rt, rs, imm);
7629
         break;
7630
    case OPC_J ... OPC_JAL: /* Jump */
7631
         offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
7632
         gen_compute_branch(ctx, op, rs, rt, offset);
7633
         return;
7634
    case OPC_BEQ ... OPC_BGTZ: /* Branch */
7635
    case OPC_BEQL ... OPC_BGTZL:
7636
         gen_compute_branch(ctx, op, rs, rt, imm << 2);
7637
         return;
7638
    case OPC_LB ... OPC_LWR: /* Load and stores */
7639
    case OPC_SB ... OPC_SW:
7640
    case OPC_SWR:
7641
    case OPC_LL:
7642
    case OPC_SC:
7643
         gen_ldst(ctx, op, rt, rs, imm);
7644
         break;
7645
    case OPC_CACHE:
7646
        check_insn(env, ctx, ISA_MIPS3 | ISA_MIPS32);
7647
        /* Treat as NOP. */
7648
        break;
7649
    case OPC_PREF:
7650
        check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
7651
        /* Treat as NOP. */
7652
        break;
7653

    
7654
    /* Floating point (COP1). */
7655
    case OPC_LWC1:
7656
    case OPC_LDC1:
7657
    case OPC_SWC1:
7658
    case OPC_SDC1:
7659
        if (env->CP0_Config1 & (1 << CP0C1_FP)) {
7660
            save_cpu_state(ctx, 1);
7661
            check_cp1_enabled(ctx);
7662
            gen_flt_ldst(ctx, op, rt, rs, imm);
7663
        } else {
7664
            generate_exception_err(ctx, EXCP_CpU, 1);
7665
        }
7666
        break;
7667

    
7668
    case OPC_CP1:
7669
        if (env->CP0_Config1 & (1 << CP0C1_FP)) {
7670
            save_cpu_state(ctx, 1);
7671
            check_cp1_enabled(ctx);
7672
            op1 = MASK_CP1(ctx->opcode);
7673
            switch (op1) {
7674
            case OPC_MFHC1:
7675
            case OPC_MTHC1:
7676
                check_insn(env, ctx, ISA_MIPS32R2);
7677
            case OPC_MFC1:
7678
            case OPC_CFC1:
7679
            case OPC_MTC1:
7680
            case OPC_CTC1:
7681
                gen_cp1(ctx, op1, rt, rd);
7682
                break;
7683
#if defined(TARGET_MIPS64)
7684
            case OPC_DMFC1:
7685
            case OPC_DMTC1:
7686
                check_insn(env, ctx, ISA_MIPS3);
7687
                gen_cp1(ctx, op1, rt, rd);
7688
                break;
7689
#endif
7690
            case OPC_BC1ANY2:
7691
            case OPC_BC1ANY4:
7692
                check_cop1x(ctx);
7693
                check_insn(env, ctx, ASE_MIPS3D);
7694
                /* fall through */
7695
            case OPC_BC1:
7696
                gen_compute_branch1(env, ctx, MASK_BC1(ctx->opcode),
7697
                                    (rt >> 2) & 0x7, imm << 2);
7698
                return;
7699
            case OPC_S_FMT:
7700
            case OPC_D_FMT:
7701
            case OPC_W_FMT:
7702
            case OPC_L_FMT:
7703
            case OPC_PS_FMT:
7704
                gen_farith(ctx, MASK_CP1_FUNC(ctx->opcode), rt, rd, sa,
7705
                           (imm >> 8) & 0x7);
7706
                break;
7707
            default:
7708
                MIPS_INVAL("cp1");
7709
                generate_exception (ctx, EXCP_RI);
7710
                break;
7711
            }
7712
        } else {
7713
            generate_exception_err(ctx, EXCP_CpU, 1);
7714
        }
7715
        break;
7716

    
7717
    /* COP2.  */
7718
    case OPC_LWC2:
7719
    case OPC_LDC2:
7720
    case OPC_SWC2:
7721
    case OPC_SDC2:
7722
    case OPC_CP2:
7723
        /* COP2: Not implemented. */
7724
        generate_exception_err(ctx, EXCP_CpU, 2);
7725
        break;
7726

    
7727
    case OPC_CP3:
7728
        if (env->CP0_Config1 & (1 << CP0C1_FP)) {
7729
            save_cpu_state(ctx, 1);
7730
            check_cp1_enabled(ctx);
7731
            op1 = MASK_CP3(ctx->opcode);
7732
            switch (op1) {
7733
            case OPC_LWXC1:
7734
            case OPC_LDXC1:
7735
            case OPC_LUXC1:
7736
            case OPC_SWXC1:
7737
            case OPC_SDXC1:
7738
            case OPC_SUXC1:
7739
                gen_flt3_ldst(ctx, op1, sa, rd, rs, rt);
7740
                break;
7741
            case OPC_PREFX:
7742
                /* Treat as NOP. */
7743
                break;
7744
            case OPC_ALNV_PS:
7745
            case OPC_MADD_S:
7746
            case OPC_MADD_D:
7747
            case OPC_MADD_PS:
7748
            case OPC_MSUB_S:
7749
            case OPC_MSUB_D:
7750
            case OPC_MSUB_PS:
7751
            case OPC_NMADD_S:
7752
            case OPC_NMADD_D:
7753
            case OPC_NMADD_PS:
7754
            case OPC_NMSUB_S:
7755
            case OPC_NMSUB_D:
7756
            case OPC_NMSUB_PS:
7757
                gen_flt3_arith(ctx, op1, sa, rs, rd, rt);
7758
                break;
7759
            default:
7760
                MIPS_INVAL("cp3");
7761
                generate_exception (ctx, EXCP_RI);
7762
                break;
7763
            }
7764
        } else {
7765
            generate_exception_err(ctx, EXCP_CpU, 1);
7766
        }
7767
        break;
7768

    
7769
#if defined(TARGET_MIPS64)
7770
    /* MIPS64 opcodes */
7771
    case OPC_LWU:
7772
    case OPC_LDL ... OPC_LDR:
7773
    case OPC_SDL ... OPC_SDR:
7774
    case OPC_LLD:
7775
    case OPC_LD:
7776
    case OPC_SCD:
7777
    case OPC_SD:
7778
        check_insn(env, ctx, ISA_MIPS3);
7779
        check_mips_64(ctx);
7780
        gen_ldst(ctx, op, rt, rs, imm);
7781
        break;
7782
    case OPC_DADDI ... OPC_DADDIU:
7783
        check_insn(env, ctx, ISA_MIPS3);
7784
        check_mips_64(ctx);
7785
        gen_arith_imm(env, ctx, op, rt, rs, imm);
7786
        break;
7787
#endif
7788
    case OPC_JALX:
7789
        check_insn(env, ctx, ASE_MIPS16);
7790
        /* MIPS16: Not implemented. */
7791
    case OPC_MDMX:
7792
        check_insn(env, ctx, ASE_MDMX);
7793
        /* MDMX: Not implemented. */
7794
    default:            /* Invalid */
7795
        MIPS_INVAL("major opcode");
7796
        generate_exception(ctx, EXCP_RI);
7797
        break;
7798
    }
7799
    if (ctx->hflags & MIPS_HFLAG_BMASK) {
7800
        int hflags = ctx->hflags & MIPS_HFLAG_BMASK;
7801
        /* Branches completion */
7802
        ctx->hflags &= ~MIPS_HFLAG_BMASK;
7803
        ctx->bstate = BS_BRANCH;
7804
        save_cpu_state(ctx, 0);
7805
        /* FIXME: Need to clear can_do_io.  */
7806
        switch (hflags) {
7807
        case MIPS_HFLAG_B:
7808
            /* unconditional branch */
7809
            MIPS_DEBUG("unconditional branch");
7810
            gen_goto_tb(ctx, 0, ctx->btarget);
7811
            break;
7812
        case MIPS_HFLAG_BL:
7813
            /* blikely taken case */
7814
            MIPS_DEBUG("blikely branch taken");
7815
            gen_goto_tb(ctx, 0, ctx->btarget);
7816
            break;
7817
        case MIPS_HFLAG_BC:
7818
            /* Conditional branch */
7819
            MIPS_DEBUG("conditional branch");
7820
            {
7821
                TCGv r_tmp = tcg_temp_local_new(TCG_TYPE_TL);
7822
                int l1 = gen_new_label();
7823

    
7824
                tcg_gen_ld_tl(r_tmp, cpu_env, offsetof(CPUState, bcond));
7825
                tcg_gen_brcondi_tl(TCG_COND_NE, r_tmp, 0, l1);
7826
                tcg_temp_free(r_tmp);
7827
                gen_goto_tb(ctx, 1, ctx->pc + 4);
7828
                gen_set_label(l1);
7829
                gen_goto_tb(ctx, 0, ctx->btarget);
7830
            }
7831
            break;
7832
        case MIPS_HFLAG_BR:
7833
            /* unconditional branch to register */
7834
            MIPS_DEBUG("branch to register");
7835
            gen_breg_pc();
7836
            tcg_gen_exit_tb(0);
7837
            break;
7838
        default:
7839
            MIPS_DEBUG("unknown branch");
7840
            break;
7841
        }
7842
    }
7843
}
7844

    
7845
static always_inline int
7846
gen_intermediate_code_internal (CPUState *env, TranslationBlock *tb,
7847
                                int search_pc)
7848
{
7849
    DisasContext ctx;
7850
    target_ulong pc_start;
7851
    uint16_t *gen_opc_end;
7852
    int j, lj = -1;
7853
    int num_insns;
7854
    int max_insns;
7855

    
7856
    if (search_pc && loglevel)
7857
        fprintf (logfile, "search pc %d\n", search_pc);
7858

    
7859
    pc_start = tb->pc;
7860
    /* Leave some spare opc slots for branch handling. */
7861
    gen_opc_end = gen_opc_buf + OPC_MAX_SIZE - 16;
7862
    ctx.pc = pc_start;
7863
    ctx.saved_pc = -1;
7864
    ctx.tb = tb;
7865
    ctx.bstate = BS_NONE;
7866
    /* Restore delay slot state from the tb context.  */
7867
    ctx.hflags = (uint32_t)tb->flags; /* FIXME: maybe use 64 bits here? */
7868
    restore_cpu_state(env, &ctx);
7869
#if defined(CONFIG_USER_ONLY)
7870
    ctx.mem_idx = MIPS_HFLAG_UM;
7871
#else
7872
    ctx.mem_idx = ctx.hflags & MIPS_HFLAG_KSU;
7873
#endif
7874
    num_insns = 0;
7875
    max_insns = tb->cflags & CF_COUNT_MASK;
7876
    if (max_insns == 0)
7877
        max_insns = CF_COUNT_MASK;
7878
#ifdef DEBUG_DISAS
7879
    if (loglevel & CPU_LOG_TB_CPU) {
7880
        fprintf(logfile, "------------------------------------------------\n");
7881
        /* FIXME: This may print out stale hflags from env... */
7882
        cpu_dump_state(env, logfile, fprintf, 0);
7883
    }
7884
#endif
7885
#ifdef MIPS_DEBUG_DISAS
7886
    if (loglevel & CPU_LOG_TB_IN_ASM)
7887
        fprintf(logfile, "\ntb %p idx %d hflags %04x\n",
7888
                tb, ctx.mem_idx, ctx.hflags);
7889
#endif
7890
    gen_icount_start();
7891
    while (ctx.bstate == BS_NONE) {
7892
        if (env->nb_breakpoints > 0) {
7893
            for(j = 0; j < env->nb_breakpoints; j++) {
7894
                if (env->breakpoints[j] == ctx.pc) {
7895
                    save_cpu_state(&ctx, 1);
7896
                    ctx.bstate = BS_BRANCH;
7897
                    tcg_gen_helper_0_i(do_raise_exception, EXCP_DEBUG);
7898
                    /* Include the breakpoint location or the tb won't
7899
                     * be flushed when it must be.  */
7900
                    ctx.pc += 4;
7901
                    goto done_generating;
7902
                }
7903
            }
7904
        }
7905

    
7906
        if (search_pc) {
7907
            j = gen_opc_ptr - gen_opc_buf;
7908
            if (lj < j) {
7909
                lj++;
7910
                while (lj < j)
7911
                    gen_opc_instr_start[lj++] = 0;
7912
            }
7913
            gen_opc_pc[lj] = ctx.pc;
7914
            gen_opc_hflags[lj] = ctx.hflags & MIPS_HFLAG_BMASK;
7915
            gen_opc_instr_start[lj] = 1;
7916
            gen_opc_icount[lj] = num_insns;
7917
        }
7918
        if (num_insns + 1 == max_insns && (tb->cflags & CF_LAST_IO))
7919
            gen_io_start();
7920
        ctx.opcode = ldl_code(ctx.pc);
7921
        decode_opc(env, &ctx);
7922
        ctx.pc += 4;
7923
        num_insns++;
7924

    
7925
        if (env->singlestep_enabled)
7926
            break;
7927

    
7928
        if ((ctx.pc & (TARGET_PAGE_SIZE - 1)) == 0)
7929
            break;
7930

    
7931
        if (gen_opc_ptr >= gen_opc_end)
7932
            break;
7933

    
7934
        if (gen_opc_ptr >= gen_opc_end)
7935
            break;
7936

    
7937
        if (num_insns >= max_insns)
7938
            break;
7939
#if defined (MIPS_SINGLE_STEP)
7940
        break;
7941
#endif
7942
    }
7943
    if (tb->cflags & CF_LAST_IO)
7944
        gen_io_end();
7945
    if (env->singlestep_enabled) {
7946
        save_cpu_state(&ctx, ctx.bstate == BS_NONE);
7947
        tcg_gen_helper_0_i(do_raise_exception, EXCP_DEBUG);
7948
    } else {
7949
        switch (ctx.bstate) {
7950
        case BS_STOP:
7951
            tcg_gen_helper_0_0(do_interrupt_restart);
7952
            gen_goto_tb(&ctx, 0, ctx.pc);
7953
            break;
7954
        case BS_NONE:
7955
            save_cpu_state(&ctx, 0);
7956
            gen_goto_tb(&ctx, 0, ctx.pc);
7957
            break;
7958
        case BS_EXCP:
7959
            tcg_gen_helper_0_0(do_interrupt_restart);
7960
            tcg_gen_exit_tb(0);
7961
            break;
7962
        case BS_BRANCH:
7963
        default:
7964
            break;
7965
        }
7966
    }
7967
done_generating:
7968
    gen_icount_end(tb, num_insns);
7969
    *gen_opc_ptr = INDEX_op_end;
7970
    if (search_pc) {
7971
        j = gen_opc_ptr - gen_opc_buf;
7972
        lj++;
7973
        while (lj <= j)
7974
            gen_opc_instr_start[lj++] = 0;
7975
    } else {
7976
        tb->size = ctx.pc - pc_start;
7977
        tb->icount = num_insns;
7978
    }
7979
#ifdef DEBUG_DISAS
7980
#if defined MIPS_DEBUG_DISAS
7981
    if (loglevel & CPU_LOG_TB_IN_ASM)
7982
        fprintf(logfile, "\n");
7983
#endif
7984
    if (loglevel & CPU_LOG_TB_IN_ASM) {
7985
        fprintf(logfile, "IN: %s\n", lookup_symbol(pc_start));
7986
        target_disas(logfile, pc_start, ctx.pc - pc_start, 0);
7987
        fprintf(logfile, "\n");
7988
    }
7989
    if (loglevel & CPU_LOG_TB_CPU) {
7990
        fprintf(logfile, "---------------- %d %08x\n", ctx.bstate, ctx.hflags);
7991
    }
7992
#endif
7993

    
7994
    return 0;
7995
}
7996

    
7997
int gen_intermediate_code (CPUState *env, struct TranslationBlock *tb)
7998
{
7999
    return gen_intermediate_code_internal(env, tb, 0);
8000
}
8001

    
8002
int gen_intermediate_code_pc (CPUState *env, struct TranslationBlock *tb)
8003
{
8004
    return gen_intermediate_code_internal(env, tb, 1);
8005
}
8006

    
8007
void fpu_dump_state(CPUState *env, FILE *f,
8008
                    int (*fpu_fprintf)(FILE *f, const char *fmt, ...),
8009
                    int flags)
8010
{
8011
    int i;
8012
    int is_fpu64 = !!(env->hflags & MIPS_HFLAG_F64);
8013

    
8014
#define printfpr(fp)                                                        \
8015
    do {                                                                    \
8016
        if (is_fpu64)                                                       \
8017
            fpu_fprintf(f, "w:%08x d:%016lx fd:%13g fs:%13g psu: %13g\n",   \
8018
                        (fp)->w[FP_ENDIAN_IDX], (fp)->d, (fp)->fd,          \
8019
                        (fp)->fs[FP_ENDIAN_IDX], (fp)->fs[!FP_ENDIAN_IDX]); \
8020
        else {                                                              \
8021
            fpr_t tmp;                                                      \
8022
            tmp.w[FP_ENDIAN_IDX] = (fp)->w[FP_ENDIAN_IDX];                  \
8023
            tmp.w[!FP_ENDIAN_IDX] = ((fp) + 1)->w[FP_ENDIAN_IDX];           \
8024
            fpu_fprintf(f, "w:%08x d:%016lx fd:%13g fs:%13g psu:%13g\n",    \
8025
                        tmp.w[FP_ENDIAN_IDX], tmp.d, tmp.fd,                \
8026
                        tmp.fs[FP_ENDIAN_IDX], tmp.fs[!FP_ENDIAN_IDX]);     \
8027
        }                                                                   \
8028
    } while(0)
8029

    
8030

    
8031
    fpu_fprintf(f, "CP1 FCR0 0x%08x  FCR31 0x%08x  SR.FR %d  fp_status 0x%08x(0x%02x)\n",
8032
                env->fpu->fcr0, env->fpu->fcr31, is_fpu64, env->fpu->fp_status,
8033
                get_float_exception_flags(&env->fpu->fp_status));
8034
    fpu_fprintf(f, "FT0: "); printfpr(&env->ft0);
8035
    fpu_fprintf(f, "FT1: "); printfpr(&env->ft1);
8036
    fpu_fprintf(f, "FT2: "); printfpr(&env->ft2);
8037
    for (i = 0; i < 32; (is_fpu64) ? i++ : (i += 2)) {
8038
        fpu_fprintf(f, "%3s: ", fregnames[i]);
8039
        printfpr(&env->fpu->fpr[i]);
8040
    }
8041

    
8042
#undef printfpr
8043
}
8044

    
8045
void dump_fpu (CPUState *env)
8046
{
8047
    if (loglevel) {
8048
        fprintf(logfile,
8049
                "pc=0x" TARGET_FMT_lx " HI=0x" TARGET_FMT_lx
8050
                " LO=0x" TARGET_FMT_lx " ds %04x " TARGET_FMT_lx
8051
                " %04x\n",
8052
                env->active_tc.PC, env->active_tc.HI[0],
8053
                env->active_tc.LO[0], env->hflags, env->btarget,
8054
                env->bcond);
8055
       fpu_dump_state(env, logfile, fprintf, 0);
8056
    }
8057
}
8058

    
8059
#if defined(TARGET_MIPS64) && defined(MIPS_DEBUG_SIGN_EXTENSIONS)
8060
/* Debug help: The architecture requires 32bit code to maintain proper
8061
   sign-extened values on 64bit machines.  */
8062

    
8063
#define SIGN_EXT_P(val) ((((val) & ~0x7fffffff) == 0) || (((val) & ~0x7fffffff) == ~0x7fffffff))
8064

    
8065
void cpu_mips_check_sign_extensions (CPUState *env, FILE *f,
8066
                     int (*cpu_fprintf)(FILE *f, const char *fmt, ...),
8067
                     int flags)
8068
{
8069
    int i;
8070

    
8071
    if (!SIGN_EXT_P(env->active_tc.PC))
8072
        cpu_fprintf(f, "BROKEN: pc=0x" TARGET_FMT_lx "\n", env->active_tc.PC);
8073
    if (!SIGN_EXT_P(env->active_tc.HI[0]))
8074
        cpu_fprintf(f, "BROKEN: HI=0x" TARGET_FMT_lx "\n", env->active_tc.HI[0]);
8075
    if (!SIGN_EXT_P(env->active_tc.LO[0]))
8076
        cpu_fprintf(f, "BROKEN: LO=0x" TARGET_FMT_lx "\n", env->active_tc.LO[0]);
8077
    if (!SIGN_EXT_P(env->btarget))
8078
        cpu_fprintf(f, "BROKEN: btarget=0x" TARGET_FMT_lx "\n", env->btarget);
8079

    
8080
    for (i = 0; i < 32; i++) {
8081
        if (!SIGN_EXT_P(env->active_tc.gpr[i]))
8082
            cpu_fprintf(f, "BROKEN: %s=0x" TARGET_FMT_lx "\n", regnames[i], env->active_tc.gpr[i]);
8083
    }
8084

    
8085
    if (!SIGN_EXT_P(env->CP0_EPC))
8086
        cpu_fprintf(f, "BROKEN: EPC=0x" TARGET_FMT_lx "\n", env->CP0_EPC);
8087
    if (!SIGN_EXT_P(env->CP0_LLAddr))
8088
        cpu_fprintf(f, "BROKEN: LLAddr=0x" TARGET_FMT_lx "\n", env->CP0_LLAddr);
8089
}
8090
#endif
8091

    
8092
void cpu_dump_state (CPUState *env, FILE *f,
8093
                     int (*cpu_fprintf)(FILE *f, const char *fmt, ...),
8094
                     int flags)
8095
{
8096
    int i;
8097

    
8098
    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",
8099
                env->active_tc.PC, env->active_tc.HI, env->active_tc.LO, env->hflags, env->btarget, env->bcond);
8100
    for (i = 0; i < 32; i++) {
8101
        if ((i & 3) == 0)
8102
            cpu_fprintf(f, "GPR%02d:", i);
8103
        cpu_fprintf(f, " %s " TARGET_FMT_lx, regnames[i], env->active_tc.gpr[i]);
8104
        if ((i & 3) == 3)
8105
            cpu_fprintf(f, "\n");
8106
    }
8107

    
8108
    cpu_fprintf(f, "CP0 Status  0x%08x Cause   0x%08x EPC    0x" TARGET_FMT_lx "\n",
8109
                env->CP0_Status, env->CP0_Cause, env->CP0_EPC);
8110
    cpu_fprintf(f, "    Config0 0x%08x Config1 0x%08x LLAddr 0x" TARGET_FMT_lx "\n",
8111
                env->CP0_Config0, env->CP0_Config1, env->CP0_LLAddr);
8112
    if (env->hflags & MIPS_HFLAG_FPU)
8113
        fpu_dump_state(env, f, cpu_fprintf, flags);
8114
#if defined(TARGET_MIPS64) && defined(MIPS_DEBUG_SIGN_EXTENSIONS)
8115
    cpu_mips_check_sign_extensions(env, f, cpu_fprintf, flags);
8116
#endif
8117
}
8118

    
8119
static void mips_tcg_init(void)
8120
{
8121
    static int inited;
8122

    
8123
    /* Initialize various static tables. */
8124
    if (inited)
8125
        return;
8126

    
8127
    cpu_env = tcg_global_reg_new(TCG_TYPE_PTR, TCG_AREG0, "env");
8128
    current_fpu = tcg_global_mem_new(TCG_TYPE_PTR,
8129
                                     TCG_AREG0,
8130
                                     offsetof(CPUState, fpu),
8131
                                     "current_fpu");
8132

    
8133
    /* register helpers */
8134
#undef DEF_HELPER
8135
#define DEF_HELPER(ret, name, params) tcg_register_helper(name, #name);
8136
#include "helper.h"
8137

    
8138
    fpu32_T[0] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft0.w[FP_ENDIAN_IDX]), "WT0");
8139
    fpu32_T[1] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft1.w[FP_ENDIAN_IDX]), "WT1");
8140
    fpu32_T[2] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft2.w[FP_ENDIAN_IDX]), "WT2");
8141
    fpu64_T[0] = tcg_global_mem_new(TCG_TYPE_I64, TCG_AREG0, offsetof(CPUState, ft0.d), "DT0");
8142
    fpu64_T[1] = tcg_global_mem_new(TCG_TYPE_I64, TCG_AREG0, offsetof(CPUState, ft1.d), "DT1");
8143
    fpu64_T[2] = tcg_global_mem_new(TCG_TYPE_I64, TCG_AREG0, offsetof(CPUState, ft2.d), "DT2");
8144
    fpu32h_T[0] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft0.w[!FP_ENDIAN_IDX]), "WTH0");
8145
    fpu32h_T[1] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft1.w[!FP_ENDIAN_IDX]), "WTH1");
8146
    fpu32h_T[2] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0, offsetof(CPUState, ft2.w[!FP_ENDIAN_IDX]), "WTH2");
8147

    
8148
    inited = 1;
8149
}
8150

    
8151
#include "translate_init.c"
8152

    
8153
CPUMIPSState *cpu_mips_init (const char *cpu_model)
8154
{
8155
    CPUMIPSState *env;
8156
    const mips_def_t *def;
8157

    
8158
    def = cpu_mips_find_by_name(cpu_model);
8159
    if (!def)
8160
        return NULL;
8161
    env = qemu_mallocz(sizeof(CPUMIPSState));
8162
    if (!env)
8163
        return NULL;
8164
    env->cpu_model = def;
8165

    
8166
    cpu_exec_init(env);
8167
    env->cpu_model_str = cpu_model;
8168
    mips_tcg_init();
8169
    cpu_reset(env);
8170
    return env;
8171
}
8172

    
8173
void cpu_reset (CPUMIPSState *env)
8174
{
8175
    memset(env, 0, offsetof(CPUMIPSState, breakpoints));
8176

    
8177
    tlb_flush(env, 1);
8178

    
8179
    /* Minimal init */
8180
#if !defined(CONFIG_USER_ONLY)
8181
    if (env->hflags & MIPS_HFLAG_BMASK) {
8182
        /* If the exception was raised from a delay slot,
8183
         * come back to the jump.  */
8184
        env->CP0_ErrorEPC = env->active_tc.PC - 4;
8185
    } else {
8186
        env->CP0_ErrorEPC = env->active_tc.PC;
8187
    }
8188
    env->active_tc.PC = (int32_t)0xBFC00000;
8189
    env->CP0_Wired = 0;
8190
    /* SMP not implemented */
8191
    env->CP0_EBase = 0x80000000;
8192
    env->CP0_Status = (1 << CP0St_BEV) | (1 << CP0St_ERL);
8193
    /* vectored interrupts not implemented, timer on int 7,
8194
       no performance counters. */
8195
    env->CP0_IntCtl = 0xe0000000;
8196
    {
8197
        int i;
8198

    
8199
        for (i = 0; i < 7; i++) {
8200
            env->CP0_WatchLo[i] = 0;
8201
            env->CP0_WatchHi[i] = 0x80000000;
8202
        }
8203
        env->CP0_WatchLo[7] = 0;
8204
        env->CP0_WatchHi[7] = 0;
8205
    }
8206
    /* Count register increments in debug mode, EJTAG version 1 */
8207
    env->CP0_Debug = (1 << CP0DB_CNT) | (0x1 << CP0DB_VER);
8208
#endif
8209
    env->exception_index = EXCP_NONE;
8210
#if defined(CONFIG_USER_ONLY)
8211
    env->hflags = MIPS_HFLAG_UM;
8212
    env->user_mode_only = 1;
8213
#else
8214
    env->hflags = MIPS_HFLAG_CP0;
8215
#endif
8216
    cpu_mips_register(env, env->cpu_model);
8217
}
8218

    
8219
void gen_pc_load(CPUState *env, TranslationBlock *tb,
8220
                unsigned long searched_pc, int pc_pos, void *puc)
8221
{
8222
    env->active_tc.PC = gen_opc_pc[pc_pos];
8223
    env->hflags &= ~MIPS_HFLAG_BMASK;
8224
    env->hflags |= gen_opc_hflags[pc_pos];
8225
}