Statistics
| Branch: | Revision:

root / target-mips / translate.c @ edcdd562

History | View | Annotate | Download (360.9 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
 *  Copyright (c) 2009 CodeSourcery (MIPS16 and microMIPS support)
8
 *
9
 * This library is free software; you can redistribute it and/or
10
 * modify it under the terms of the GNU Lesser General Public
11
 * License as published by the Free Software Foundation; either
12
 * version 2 of the License, or (at your option) any later version.
13
 *
14
 * This library is distributed in the hope that it will be useful,
15
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17
 * Lesser General Public License for more details.
18
 *
19
 * You should have received a copy of the GNU Lesser General Public
20
 * License along with this library; if not, see <http://www.gnu.org/licenses/>.
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 "tcg-op.h"
33
#include "qemu-common.h"
34

    
35
#include "helper.h"
36
#define GEN_HELPER 1
37
#include "helper.h"
38

    
39
//#define MIPS_DEBUG_DISAS
40
//#define MIPS_DEBUG_SIGN_EXTENSIONS
41

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

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

    
126
/* MIPS special opcodes */
127
#define MASK_SPECIAL(op)   MASK_OP_MAJOR(op) | (op & 0x3F)
128

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

    
199
    OPC_MOVCI    = 0x01 | OPC_SPECIAL,
200

    
201
    /* Special */
202
    OPC_PMON     = 0x05 | OPC_SPECIAL, /* unofficial */
203
    OPC_SYSCALL  = 0x0C | OPC_SPECIAL,
204
    OPC_BREAK    = 0x0D | OPC_SPECIAL,
205
    OPC_SPIM     = 0x0E | OPC_SPECIAL, /* unofficial */
206
    OPC_SYNC     = 0x0F | OPC_SPECIAL,
207

    
208
    OPC_SPECIAL15_RESERVED = 0x15 | OPC_SPECIAL,
209
    OPC_SPECIAL28_RESERVED = 0x28 | OPC_SPECIAL,
210
    OPC_SPECIAL29_RESERVED = 0x29 | OPC_SPECIAL,
211
    OPC_SPECIAL35_RESERVED = 0x35 | OPC_SPECIAL,
212
    OPC_SPECIAL37_RESERVED = 0x37 | OPC_SPECIAL,
213
    OPC_SPECIAL39_RESERVED = 0x39 | OPC_SPECIAL,
214
    OPC_SPECIAL3D_RESERVED = 0x3D | OPC_SPECIAL,
215
};
216

    
217
/* Multiplication variants of the vr54xx. */
218
#define MASK_MUL_VR54XX(op)   MASK_SPECIAL(op) | (op & (0x1F << 6))
219

    
220
enum {
221
    OPC_VR54XX_MULS    = (0x03 << 6) | OPC_MULT,
222
    OPC_VR54XX_MULSU   = (0x03 << 6) | OPC_MULTU,
223
    OPC_VR54XX_MACC    = (0x05 << 6) | OPC_MULT,
224
    OPC_VR54XX_MACCU   = (0x05 << 6) | OPC_MULTU,
225
    OPC_VR54XX_MSAC    = (0x07 << 6) | OPC_MULT,
226
    OPC_VR54XX_MSACU   = (0x07 << 6) | OPC_MULTU,
227
    OPC_VR54XX_MULHI   = (0x09 << 6) | OPC_MULT,
228
    OPC_VR54XX_MULHIU  = (0x09 << 6) | OPC_MULTU,
229
    OPC_VR54XX_MULSHI  = (0x0B << 6) | OPC_MULT,
230
    OPC_VR54XX_MULSHIU = (0x0B << 6) | OPC_MULTU,
231
    OPC_VR54XX_MACCHI  = (0x0D << 6) | OPC_MULT,
232
    OPC_VR54XX_MACCHIU = (0x0D << 6) | OPC_MULTU,
233
    OPC_VR54XX_MSACHI  = (0x0F << 6) | OPC_MULT,
234
    OPC_VR54XX_MSACHIU = (0x0F << 6) | OPC_MULTU,
235
};
236

    
237
/* REGIMM (rt field) opcodes */
238
#define MASK_REGIMM(op)    MASK_OP_MAJOR(op) | (op & (0x1F << 16))
239

    
240
enum {
241
    OPC_BLTZ     = (0x00 << 16) | OPC_REGIMM,
242
    OPC_BLTZL    = (0x02 << 16) | OPC_REGIMM,
243
    OPC_BGEZ     = (0x01 << 16) | OPC_REGIMM,
244
    OPC_BGEZL    = (0x03 << 16) | OPC_REGIMM,
245
    OPC_BLTZAL   = (0x10 << 16) | OPC_REGIMM,
246
    OPC_BLTZALS  = OPC_BLTZAL | 0x5, /* microMIPS */
247
    OPC_BLTZALL  = (0x12 << 16) | OPC_REGIMM,
248
    OPC_BGEZAL   = (0x11 << 16) | OPC_REGIMM,
249
    OPC_BGEZALS  = OPC_BGEZAL | 0x5, /* microMIPS */
250
    OPC_BGEZALL  = (0x13 << 16) | OPC_REGIMM,
251
    OPC_TGEI     = (0x08 << 16) | OPC_REGIMM,
252
    OPC_TGEIU    = (0x09 << 16) | OPC_REGIMM,
253
    OPC_TLTI     = (0x0A << 16) | OPC_REGIMM,
254
    OPC_TLTIU    = (0x0B << 16) | OPC_REGIMM,
255
    OPC_TEQI     = (0x0C << 16) | OPC_REGIMM,
256
    OPC_TNEI     = (0x0E << 16) | OPC_REGIMM,
257
    OPC_SYNCI    = (0x1F << 16) | OPC_REGIMM,
258
};
259

    
260
/* Special2 opcodes */
261
#define MASK_SPECIAL2(op)  MASK_OP_MAJOR(op) | (op & 0x3F)
262

    
263
enum {
264
    /* Multiply & xxx operations */
265
    OPC_MADD     = 0x00 | OPC_SPECIAL2,
266
    OPC_MADDU    = 0x01 | OPC_SPECIAL2,
267
    OPC_MUL      = 0x02 | OPC_SPECIAL2,
268
    OPC_MSUB     = 0x04 | OPC_SPECIAL2,
269
    OPC_MSUBU    = 0x05 | OPC_SPECIAL2,
270
    /* Loongson 2F */
271
    OPC_MULT_G_2F   = 0x10 | OPC_SPECIAL2,
272
    OPC_DMULT_G_2F  = 0x11 | OPC_SPECIAL2,
273
    OPC_MULTU_G_2F  = 0x12 | OPC_SPECIAL2,
274
    OPC_DMULTU_G_2F = 0x13 | OPC_SPECIAL2,
275
    OPC_DIV_G_2F    = 0x14 | OPC_SPECIAL2,
276
    OPC_DDIV_G_2F   = 0x15 | OPC_SPECIAL2,
277
    OPC_DIVU_G_2F   = 0x16 | OPC_SPECIAL2,
278
    OPC_DDIVU_G_2F  = 0x17 | OPC_SPECIAL2,
279
    OPC_MOD_G_2F    = 0x1c | OPC_SPECIAL2,
280
    OPC_DMOD_G_2F   = 0x1d | OPC_SPECIAL2,
281
    OPC_MODU_G_2F   = 0x1e | OPC_SPECIAL2,
282
    OPC_DMODU_G_2F  = 0x1f | OPC_SPECIAL2,
283
    /* Misc */
284
    OPC_CLZ      = 0x20 | OPC_SPECIAL2,
285
    OPC_CLO      = 0x21 | OPC_SPECIAL2,
286
    OPC_DCLZ     = 0x24 | OPC_SPECIAL2,
287
    OPC_DCLO     = 0x25 | OPC_SPECIAL2,
288
    /* Special */
289
    OPC_SDBBP    = 0x3F | OPC_SPECIAL2,
290
};
291

    
292
/* Special3 opcodes */
293
#define MASK_SPECIAL3(op)  MASK_OP_MAJOR(op) | (op & 0x3F)
294

    
295
enum {
296
    OPC_EXT      = 0x00 | OPC_SPECIAL3,
297
    OPC_DEXTM    = 0x01 | OPC_SPECIAL3,
298
    OPC_DEXTU    = 0x02 | OPC_SPECIAL3,
299
    OPC_DEXT     = 0x03 | OPC_SPECIAL3,
300
    OPC_INS      = 0x04 | OPC_SPECIAL3,
301
    OPC_DINSM    = 0x05 | OPC_SPECIAL3,
302
    OPC_DINSU    = 0x06 | OPC_SPECIAL3,
303
    OPC_DINS     = 0x07 | OPC_SPECIAL3,
304
    OPC_FORK     = 0x08 | OPC_SPECIAL3,
305
    OPC_YIELD    = 0x09 | OPC_SPECIAL3,
306
    OPC_BSHFL    = 0x20 | OPC_SPECIAL3,
307
    OPC_DBSHFL   = 0x24 | OPC_SPECIAL3,
308
    OPC_RDHWR    = 0x3B | OPC_SPECIAL3,
309

    
310
    /* Loongson 2E */
311
    OPC_MULT_G_2E   = 0x18 | OPC_SPECIAL3,
312
    OPC_MULTU_G_2E  = 0x19 | OPC_SPECIAL3,
313
    OPC_DIV_G_2E    = 0x1A | OPC_SPECIAL3,
314
    OPC_DIVU_G_2E   = 0x1B | OPC_SPECIAL3,
315
    OPC_DMULT_G_2E  = 0x1C | OPC_SPECIAL3,
316
    OPC_DMULTU_G_2E = 0x1D | OPC_SPECIAL3,
317
    OPC_DDIV_G_2E   = 0x1E | OPC_SPECIAL3,
318
    OPC_DDIVU_G_2E  = 0x1F | OPC_SPECIAL3,
319
    OPC_MOD_G_2E    = 0x22 | OPC_SPECIAL3,
320
    OPC_MODU_G_2E   = 0x23 | OPC_SPECIAL3,
321
    OPC_DMOD_G_2E   = 0x26 | OPC_SPECIAL3,
322
    OPC_DMODU_G_2E  = 0x27 | OPC_SPECIAL3,
323
};
324

    
325
/* BSHFL opcodes */
326
#define MASK_BSHFL(op)     MASK_SPECIAL3(op) | (op & (0x1F << 6))
327

    
328
enum {
329
    OPC_WSBH     = (0x02 << 6) | OPC_BSHFL,
330
    OPC_SEB      = (0x10 << 6) | OPC_BSHFL,
331
    OPC_SEH      = (0x18 << 6) | OPC_BSHFL,
332
};
333

    
334
/* DBSHFL opcodes */
335
#define MASK_DBSHFL(op)    MASK_SPECIAL3(op) | (op & (0x1F << 6))
336

    
337
enum {
338
    OPC_DSBH     = (0x02 << 6) | OPC_DBSHFL,
339
    OPC_DSHD     = (0x05 << 6) | OPC_DBSHFL,
340
};
341

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

    
345
enum {
346
    OPC_MFC0     = (0x00 << 21) | OPC_CP0,
347
    OPC_DMFC0    = (0x01 << 21) | OPC_CP0,
348
    OPC_MTC0     = (0x04 << 21) | OPC_CP0,
349
    OPC_DMTC0    = (0x05 << 21) | OPC_CP0,
350
    OPC_MFTR     = (0x08 << 21) | OPC_CP0,
351
    OPC_RDPGPR   = (0x0A << 21) | OPC_CP0,
352
    OPC_MFMC0    = (0x0B << 21) | OPC_CP0,
353
    OPC_MTTR     = (0x0C << 21) | OPC_CP0,
354
    OPC_WRPGPR   = (0x0E << 21) | OPC_CP0,
355
    OPC_C0       = (0x10 << 21) | OPC_CP0,
356
    OPC_C0_FIRST = (0x10 << 21) | OPC_CP0,
357
    OPC_C0_LAST  = (0x1F << 21) | OPC_CP0,
358
};
359

    
360
/* MFMC0 opcodes */
361
#define MASK_MFMC0(op)     MASK_CP0(op) | (op & 0xFFFF)
362

    
363
enum {
364
    OPC_DMT      = 0x01 | (0 << 5) | (0x0F << 6) | (0x01 << 11) | OPC_MFMC0,
365
    OPC_EMT      = 0x01 | (1 << 5) | (0x0F << 6) | (0x01 << 11) | OPC_MFMC0,
366
    OPC_DVPE     = 0x01 | (0 << 5) | OPC_MFMC0,
367
    OPC_EVPE     = 0x01 | (1 << 5) | OPC_MFMC0,
368
    OPC_DI       = (0 << 5) | (0x0C << 11) | OPC_MFMC0,
369
    OPC_EI       = (1 << 5) | (0x0C << 11) | OPC_MFMC0,
370
};
371

    
372
/* Coprocessor 0 (with rs == C0) */
373
#define MASK_C0(op)        MASK_CP0(op) | (op & 0x3F)
374

    
375
enum {
376
    OPC_TLBR     = 0x01 | OPC_C0,
377
    OPC_TLBWI    = 0x02 | OPC_C0,
378
    OPC_TLBWR    = 0x06 | OPC_C0,
379
    OPC_TLBP     = 0x08 | OPC_C0,
380
    OPC_RFE      = 0x10 | OPC_C0,
381
    OPC_ERET     = 0x18 | OPC_C0,
382
    OPC_DERET    = 0x1F | OPC_C0,
383
    OPC_WAIT     = 0x20 | OPC_C0,
384
};
385

    
386
/* Coprocessor 1 (rs field) */
387
#define MASK_CP1(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
388

    
389
/* Values for the fmt field in FP instructions */
390
enum {
391
    /* 0 - 15 are reserved */
392
    FMT_S = 16,          /* single fp */
393
    FMT_D = 17,          /* double fp */
394
    FMT_E = 18,          /* extended fp */
395
    FMT_Q = 19,          /* quad fp */
396
    FMT_W = 20,          /* 32-bit fixed */
397
    FMT_L = 21,          /* 64-bit fixed */
398
    FMT_PS = 22,         /* paired single fp */
399
    /* 23 - 31 are reserved */
400
};
401

    
402
enum {
403
    OPC_MFC1     = (0x00 << 21) | OPC_CP1,
404
    OPC_DMFC1    = (0x01 << 21) | OPC_CP1,
405
    OPC_CFC1     = (0x02 << 21) | OPC_CP1,
406
    OPC_MFHC1    = (0x03 << 21) | OPC_CP1,
407
    OPC_MTC1     = (0x04 << 21) | OPC_CP1,
408
    OPC_DMTC1    = (0x05 << 21) | OPC_CP1,
409
    OPC_CTC1     = (0x06 << 21) | OPC_CP1,
410
    OPC_MTHC1    = (0x07 << 21) | OPC_CP1,
411
    OPC_BC1      = (0x08 << 21) | OPC_CP1, /* bc */
412
    OPC_BC1ANY2  = (0x09 << 21) | OPC_CP1,
413
    OPC_BC1ANY4  = (0x0A << 21) | OPC_CP1,
414
    OPC_S_FMT    = (FMT_S << 21) | OPC_CP1,
415
    OPC_D_FMT    = (FMT_D << 21) | OPC_CP1,
416
    OPC_E_FMT    = (FMT_E << 21) | OPC_CP1,
417
    OPC_Q_FMT    = (FMT_Q << 21) | OPC_CP1,
418
    OPC_W_FMT    = (FMT_W << 21) | OPC_CP1,
419
    OPC_L_FMT    = (FMT_L << 21) | OPC_CP1,
420
    OPC_PS_FMT   = (FMT_PS << 21) | OPC_CP1,
421
};
422

    
423
#define MASK_CP1_FUNC(op)       MASK_CP1(op) | (op & 0x3F)
424
#define MASK_BC1(op)            MASK_CP1(op) | (op & (0x3 << 16))
425

    
426
enum {
427
    OPC_BC1F     = (0x00 << 16) | OPC_BC1,
428
    OPC_BC1T     = (0x01 << 16) | OPC_BC1,
429
    OPC_BC1FL    = (0x02 << 16) | OPC_BC1,
430
    OPC_BC1TL    = (0x03 << 16) | OPC_BC1,
431
};
432

    
433
enum {
434
    OPC_BC1FANY2     = (0x00 << 16) | OPC_BC1ANY2,
435
    OPC_BC1TANY2     = (0x01 << 16) | OPC_BC1ANY2,
436
};
437

    
438
enum {
439
    OPC_BC1FANY4     = (0x00 << 16) | OPC_BC1ANY4,
440
    OPC_BC1TANY4     = (0x01 << 16) | OPC_BC1ANY4,
441
};
442

    
443
#define MASK_CP2(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
444

    
445
enum {
446
    OPC_MFC2    = (0x00 << 21) | OPC_CP2,
447
    OPC_DMFC2   = (0x01 << 21) | OPC_CP2,
448
    OPC_CFC2    = (0x02 << 21) | OPC_CP2,
449
    OPC_MFHC2   = (0x03 << 21) | OPC_CP2,
450
    OPC_MTC2    = (0x04 << 21) | OPC_CP2,
451
    OPC_DMTC2   = (0x05 << 21) | OPC_CP2,
452
    OPC_CTC2    = (0x06 << 21) | OPC_CP2,
453
    OPC_MTHC2   = (0x07 << 21) | OPC_CP2,
454
    OPC_BC2     = (0x08 << 21) | OPC_CP2,
455
};
456

    
457
#define MASK_CP3(op)       MASK_OP_MAJOR(op) | (op & 0x3F)
458

    
459
enum {
460
    OPC_LWXC1   = 0x00 | OPC_CP3,
461
    OPC_LDXC1   = 0x01 | OPC_CP3,
462
    OPC_LUXC1   = 0x05 | OPC_CP3,
463
    OPC_SWXC1   = 0x08 | OPC_CP3,
464
    OPC_SDXC1   = 0x09 | OPC_CP3,
465
    OPC_SUXC1   = 0x0D | OPC_CP3,
466
    OPC_PREFX   = 0x0F | OPC_CP3,
467
    OPC_ALNV_PS = 0x1E | OPC_CP3,
468
    OPC_MADD_S  = 0x20 | OPC_CP3,
469
    OPC_MADD_D  = 0x21 | OPC_CP3,
470
    OPC_MADD_PS = 0x26 | OPC_CP3,
471
    OPC_MSUB_S  = 0x28 | OPC_CP3,
472
    OPC_MSUB_D  = 0x29 | OPC_CP3,
473
    OPC_MSUB_PS = 0x2E | OPC_CP3,
474
    OPC_NMADD_S = 0x30 | OPC_CP3,
475
    OPC_NMADD_D = 0x31 | OPC_CP3,
476
    OPC_NMADD_PS= 0x36 | OPC_CP3,
477
    OPC_NMSUB_S = 0x38 | OPC_CP3,
478
    OPC_NMSUB_D = 0x39 | OPC_CP3,
479
    OPC_NMSUB_PS= 0x3E | OPC_CP3,
480
};
481

    
482
/* global register indices */
483
static TCGv_ptr cpu_env;
484
static TCGv cpu_gpr[32], cpu_PC;
485
static TCGv cpu_HI[MIPS_DSP_ACC], cpu_LO[MIPS_DSP_ACC], cpu_ACX[MIPS_DSP_ACC];
486
static TCGv cpu_dspctrl, btarget, bcond;
487
static TCGv_i32 hflags;
488
static TCGv_i32 fpu_fcr0, fpu_fcr31;
489

    
490
static uint32_t gen_opc_hflags[OPC_BUF_SIZE];
491

    
492
#include "gen-icount.h"
493

    
494
#define gen_helper_0i(name, arg) do {                             \
495
    TCGv_i32 helper_tmp = tcg_const_i32(arg);                     \
496
    gen_helper_##name(helper_tmp);                                \
497
    tcg_temp_free_i32(helper_tmp);                                \
498
    } while(0)
499

    
500
#define gen_helper_1i(name, arg1, arg2) do {                      \
501
    TCGv_i32 helper_tmp = tcg_const_i32(arg2);                    \
502
    gen_helper_##name(arg1, helper_tmp);                          \
503
    tcg_temp_free_i32(helper_tmp);                                \
504
    } while(0)
505

    
506
#define gen_helper_2i(name, arg1, arg2, arg3) do {                \
507
    TCGv_i32 helper_tmp = tcg_const_i32(arg3);                    \
508
    gen_helper_##name(arg1, arg2, helper_tmp);                    \
509
    tcg_temp_free_i32(helper_tmp);                                \
510
    } while(0)
511

    
512
#define gen_helper_3i(name, arg1, arg2, arg3, arg4) do {          \
513
    TCGv_i32 helper_tmp = tcg_const_i32(arg4);                    \
514
    gen_helper_##name(arg1, arg2, arg3, helper_tmp);              \
515
    tcg_temp_free_i32(helper_tmp);                                \
516
    } while(0)
517

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

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

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

    
544
static const char *regnames_HI[] =
545
    { "HI0", "HI1", "HI2", "HI3", };
546

    
547
static const char *regnames_LO[] =
548
    { "LO0", "LO1", "LO2", "LO3", };
549

    
550
static const char *regnames_ACX[] =
551
    { "ACX0", "ACX1", "ACX2", "ACX3", };
552

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

    
559
#ifdef MIPS_DEBUG_DISAS
560
#define MIPS_DEBUG(fmt, ...)                         \
561
        qemu_log_mask(CPU_LOG_TB_IN_ASM,                \
562
                       TARGET_FMT_lx ": %08x " fmt "\n", \
563
                       ctx->pc, ctx->opcode , ## __VA_ARGS__)
564
#define LOG_DISAS(...) qemu_log_mask(CPU_LOG_TB_IN_ASM, ## __VA_ARGS__)
565
#else
566
#define MIPS_DEBUG(fmt, ...) do { } while(0)
567
#define LOG_DISAS(...) do { } while (0)
568
#endif
569

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

    
576
/* General purpose registers moves. */
577
static inline void gen_load_gpr (TCGv t, int reg)
578
{
579
    if (reg == 0)
580
        tcg_gen_movi_tl(t, 0);
581
    else
582
        tcg_gen_mov_tl(t, cpu_gpr[reg]);
583
}
584

    
585
static inline void gen_store_gpr (TCGv t, int reg)
586
{
587
    if (reg != 0)
588
        tcg_gen_mov_tl(cpu_gpr[reg], t);
589
}
590

    
591
/* Moves to/from ACX register.  */
592
static inline void gen_load_ACX (TCGv t, int reg)
593
{
594
    tcg_gen_mov_tl(t, cpu_ACX[reg]);
595
}
596

    
597
static inline void gen_store_ACX (TCGv t, int reg)
598
{
599
    tcg_gen_mov_tl(cpu_ACX[reg], t);
600
}
601

    
602
/* Moves to/from shadow registers. */
603
static inline void gen_load_srsgpr (int from, int to)
604
{
605
    TCGv t0 = tcg_temp_new();
606

    
607
    if (from == 0)
608
        tcg_gen_movi_tl(t0, 0);
609
    else {
610
        TCGv_i32 t2 = tcg_temp_new_i32();
611
        TCGv_ptr addr = tcg_temp_new_ptr();
612

    
613
        tcg_gen_ld_i32(t2, cpu_env, offsetof(CPUState, CP0_SRSCtl));
614
        tcg_gen_shri_i32(t2, t2, CP0SRSCtl_PSS);
615
        tcg_gen_andi_i32(t2, t2, 0xf);
616
        tcg_gen_muli_i32(t2, t2, sizeof(target_ulong) * 32);
617
        tcg_gen_ext_i32_ptr(addr, t2);
618
        tcg_gen_add_ptr(addr, cpu_env, addr);
619

    
620
        tcg_gen_ld_tl(t0, addr, sizeof(target_ulong) * from);
621
        tcg_temp_free_ptr(addr);
622
        tcg_temp_free_i32(t2);
623
    }
624
    gen_store_gpr(t0, to);
625
    tcg_temp_free(t0);
626
}
627

    
628
static inline void gen_store_srsgpr (int from, int to)
629
{
630
    if (to != 0) {
631
        TCGv t0 = tcg_temp_new();
632
        TCGv_i32 t2 = tcg_temp_new_i32();
633
        TCGv_ptr addr = tcg_temp_new_ptr();
634

    
635
        gen_load_gpr(t0, from);
636
        tcg_gen_ld_i32(t2, cpu_env, offsetof(CPUState, CP0_SRSCtl));
637
        tcg_gen_shri_i32(t2, t2, CP0SRSCtl_PSS);
638
        tcg_gen_andi_i32(t2, t2, 0xf);
639
        tcg_gen_muli_i32(t2, t2, sizeof(target_ulong) * 32);
640
        tcg_gen_ext_i32_ptr(addr, t2);
641
        tcg_gen_add_ptr(addr, cpu_env, addr);
642

    
643
        tcg_gen_st_tl(t0, addr, sizeof(target_ulong) * to);
644
        tcg_temp_free_ptr(addr);
645
        tcg_temp_free_i32(t2);
646
        tcg_temp_free(t0);
647
    }
648
}
649

    
650
/* Floating point register moves. */
651
static inline void gen_load_fpr32 (TCGv_i32 t, int reg)
652
{
653
    tcg_gen_ld_i32(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].w[FP_ENDIAN_IDX]));
654
}
655

    
656
static inline void gen_store_fpr32 (TCGv_i32 t, int reg)
657
{
658
    tcg_gen_st_i32(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].w[FP_ENDIAN_IDX]));
659
}
660

    
661
static inline void gen_load_fpr32h (TCGv_i32 t, int reg)
662
{
663
    tcg_gen_ld_i32(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].w[!FP_ENDIAN_IDX]));
664
}
665

    
666
static inline void gen_store_fpr32h (TCGv_i32 t, int reg)
667
{
668
    tcg_gen_st_i32(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].w[!FP_ENDIAN_IDX]));
669
}
670

    
671
static inline void gen_load_fpr64 (DisasContext *ctx, TCGv_i64 t, int reg)
672
{
673
    if (ctx->hflags & MIPS_HFLAG_F64) {
674
        tcg_gen_ld_i64(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].d));
675
    } else {
676
        TCGv_i32 t0 = tcg_temp_new_i32();
677
        TCGv_i32 t1 = tcg_temp_new_i32();
678
        gen_load_fpr32(t0, reg & ~1);
679
        gen_load_fpr32(t1, reg | 1);
680
        tcg_gen_concat_i32_i64(t, t0, t1);
681
        tcg_temp_free_i32(t0);
682
        tcg_temp_free_i32(t1);
683
    }
684
}
685

    
686
static inline void gen_store_fpr64 (DisasContext *ctx, TCGv_i64 t, int reg)
687
{
688
    if (ctx->hflags & MIPS_HFLAG_F64) {
689
        tcg_gen_st_i64(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].d));
690
    } else {
691
        TCGv_i64 t0 = tcg_temp_new_i64();
692
        TCGv_i32 t1 = tcg_temp_new_i32();
693
        tcg_gen_trunc_i64_i32(t1, t);
694
        gen_store_fpr32(t1, reg & ~1);
695
        tcg_gen_shri_i64(t0, t, 32);
696
        tcg_gen_trunc_i64_i32(t1, t0);
697
        gen_store_fpr32(t1, reg | 1);
698
        tcg_temp_free_i32(t1);
699
        tcg_temp_free_i64(t0);
700
    }
701
}
702

    
703
static inline int get_fp_bit (int cc)
704
{
705
    if (cc)
706
        return 24 + cc;
707
    else
708
        return 23;
709
}
710

    
711
/* Tests */
712
static inline void gen_save_pc(target_ulong pc)
713
{
714
    tcg_gen_movi_tl(cpu_PC, pc);
715
}
716

    
717
static inline void save_cpu_state (DisasContext *ctx, int do_save_pc)
718
{
719
    LOG_DISAS("hflags %08x saved %08x\n", ctx->hflags, ctx->saved_hflags);
720
    if (do_save_pc && ctx->pc != ctx->saved_pc) {
721
        gen_save_pc(ctx->pc);
722
        ctx->saved_pc = ctx->pc;
723
    }
724
    if (ctx->hflags != ctx->saved_hflags) {
725
        tcg_gen_movi_i32(hflags, ctx->hflags);
726
        ctx->saved_hflags = ctx->hflags;
727
        switch (ctx->hflags & MIPS_HFLAG_BMASK_BASE) {
728
        case MIPS_HFLAG_BR:
729
            break;
730
        case MIPS_HFLAG_BC:
731
        case MIPS_HFLAG_BL:
732
        case MIPS_HFLAG_B:
733
            tcg_gen_movi_tl(btarget, ctx->btarget);
734
            break;
735
        }
736
    }
737
}
738

    
739
static inline void restore_cpu_state (CPUState *env, DisasContext *ctx)
740
{
741
    ctx->saved_hflags = ctx->hflags;
742
    switch (ctx->hflags & MIPS_HFLAG_BMASK_BASE) {
743
    case MIPS_HFLAG_BR:
744
        break;
745
    case MIPS_HFLAG_BC:
746
    case MIPS_HFLAG_BL:
747
    case MIPS_HFLAG_B:
748
        ctx->btarget = env->btarget;
749
        break;
750
    }
751
}
752

    
753
static inline void
754
generate_exception_err (DisasContext *ctx, int excp, int err)
755
{
756
    TCGv_i32 texcp = tcg_const_i32(excp);
757
    TCGv_i32 terr = tcg_const_i32(err);
758
    save_cpu_state(ctx, 1);
759
    gen_helper_raise_exception_err(texcp, terr);
760
    tcg_temp_free_i32(terr);
761
    tcg_temp_free_i32(texcp);
762
}
763

    
764
static inline void
765
generate_exception (DisasContext *ctx, int excp)
766
{
767
    save_cpu_state(ctx, 1);
768
    gen_helper_0i(raise_exception, excp);
769
}
770

    
771
/* Addresses computation */
772
static inline void gen_op_addr_add (DisasContext *ctx, TCGv ret, TCGv arg0, TCGv arg1)
773
{
774
    tcg_gen_add_tl(ret, arg0, arg1);
775

    
776
#if defined(TARGET_MIPS64)
777
    /* For compatibility with 32-bit code, data reference in user mode
778
       with Status_UX = 0 should be casted to 32-bit and sign extended.
779
       See the MIPS64 PRA manual, section 4.10. */
780
    if (((ctx->hflags & MIPS_HFLAG_KSU) == MIPS_HFLAG_UM) &&
781
        !(ctx->hflags & MIPS_HFLAG_UX)) {
782
        tcg_gen_ext32s_i64(ret, ret);
783
    }
784
#endif
785
}
786

    
787
static inline void check_cp0_enabled(DisasContext *ctx)
788
{
789
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_CP0)))
790
        generate_exception_err(ctx, EXCP_CpU, 0);
791
}
792

    
793
static inline void check_cp1_enabled(DisasContext *ctx)
794
{
795
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_FPU)))
796
        generate_exception_err(ctx, EXCP_CpU, 1);
797
}
798

    
799
/* Verify that the processor is running with COP1X instructions enabled.
800
   This is associated with the nabla symbol in the MIPS32 and MIPS64
801
   opcode tables.  */
802

    
803
static inline void check_cop1x(DisasContext *ctx)
804
{
805
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_COP1X)))
806
        generate_exception(ctx, EXCP_RI);
807
}
808

    
809
/* Verify that the processor is running with 64-bit floating-point
810
   operations enabled.  */
811

    
812
static inline void check_cp1_64bitmode(DisasContext *ctx)
813
{
814
    if (unlikely(~ctx->hflags & (MIPS_HFLAG_F64 | MIPS_HFLAG_COP1X)))
815
        generate_exception(ctx, EXCP_RI);
816
}
817

    
818
/*
819
 * Verify if floating point register is valid; an operation is not defined
820
 * if bit 0 of any register specification is set and the FR bit in the
821
 * Status register equals zero, since the register numbers specify an
822
 * even-odd pair of adjacent coprocessor general registers. When the FR bit
823
 * in the Status register equals one, both even and odd register numbers
824
 * are valid. This limitation exists only for 64 bit wide (d,l,ps) registers.
825
 *
826
 * Multiple 64 bit wide registers can be checked by calling
827
 * gen_op_cp1_registers(freg1 | freg2 | ... | fregN);
828
 */
829
static inline void check_cp1_registers(DisasContext *ctx, int regs)
830
{
831
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_F64) && (regs & 1)))
832
        generate_exception(ctx, EXCP_RI);
833
}
834

    
835
/* This code generates a "reserved instruction" exception if the
836
   CPU does not support the instruction set corresponding to flags. */
837
static inline void check_insn(CPUState *env, DisasContext *ctx, int flags)
838
{
839
    if (unlikely(!(env->insn_flags & flags)))
840
        generate_exception(ctx, EXCP_RI);
841
}
842

    
843
/* This code generates a "reserved instruction" exception if 64-bit
844
   instructions are not enabled. */
845
static inline void check_mips_64(DisasContext *ctx)
846
{
847
    if (unlikely(!(ctx->hflags & MIPS_HFLAG_64)))
848
        generate_exception(ctx, EXCP_RI);
849
}
850

    
851
/* Define small wrappers for gen_load_fpr* so that we have a uniform
852
   calling interface for 32 and 64-bit FPRs.  No sense in changing
853
   all callers for gen_load_fpr32 when we need the CTX parameter for
854
   this one use.  */
855
#define gen_ldcmp_fpr32(ctx, x, y) gen_load_fpr32(x, y)
856
#define gen_ldcmp_fpr64(ctx, x, y) gen_load_fpr64(ctx, x, y)
857
#define FOP_CONDS(type, abs, fmt, ifmt, bits)                                 \
858
static inline void gen_cmp ## type ## _ ## fmt(DisasContext *ctx, int n,      \
859
                                               int ft, int fs, int cc)        \
860
{                                                                             \
861
    TCGv_i##bits fp0 = tcg_temp_new_i##bits ();                               \
862
    TCGv_i##bits fp1 = tcg_temp_new_i##bits ();                               \
863
    switch (ifmt) {                                                           \
864
    case FMT_PS:                                                              \
865
        check_cp1_64bitmode(ctx);                                             \
866
        break;                                                                \
867
    case FMT_D:                                                               \
868
        if (abs) {                                                            \
869
            check_cop1x(ctx);                                                 \
870
        }                                                                     \
871
        check_cp1_registers(ctx, fs | ft);                                    \
872
        break;                                                                \
873
    case FMT_S:                                                               \
874
        if (abs) {                                                            \
875
            check_cop1x(ctx);                                                 \
876
        }                                                                     \
877
        break;                                                                \
878
    }                                                                         \
879
    gen_ldcmp_fpr##bits (ctx, fp0, fs);                                       \
880
    gen_ldcmp_fpr##bits (ctx, fp1, ft);                                       \
881
    switch (n) {                                                              \
882
    case  0: gen_helper_2i(cmp ## type ## _ ## fmt ## _f, fp0, fp1, cc);    break;\
883
    case  1: gen_helper_2i(cmp ## type ## _ ## fmt ## _un, fp0, fp1, cc);   break;\
884
    case  2: gen_helper_2i(cmp ## type ## _ ## fmt ## _eq, fp0, fp1, cc);   break;\
885
    case  3: gen_helper_2i(cmp ## type ## _ ## fmt ## _ueq, fp0, fp1, cc);  break;\
886
    case  4: gen_helper_2i(cmp ## type ## _ ## fmt ## _olt, fp0, fp1, cc);  break;\
887
    case  5: gen_helper_2i(cmp ## type ## _ ## fmt ## _ult, fp0, fp1, cc);  break;\
888
    case  6: gen_helper_2i(cmp ## type ## _ ## fmt ## _ole, fp0, fp1, cc);  break;\
889
    case  7: gen_helper_2i(cmp ## type ## _ ## fmt ## _ule, fp0, fp1, cc);  break;\
890
    case  8: gen_helper_2i(cmp ## type ## _ ## fmt ## _sf, fp0, fp1, cc);   break;\
891
    case  9: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngle, fp0, fp1, cc); break;\
892
    case 10: gen_helper_2i(cmp ## type ## _ ## fmt ## _seq, fp0, fp1, cc);  break;\
893
    case 11: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngl, fp0, fp1, cc);  break;\
894
    case 12: gen_helper_2i(cmp ## type ## _ ## fmt ## _lt, fp0, fp1, cc);   break;\
895
    case 13: gen_helper_2i(cmp ## type ## _ ## fmt ## _nge, fp0, fp1, cc);  break;\
896
    case 14: gen_helper_2i(cmp ## type ## _ ## fmt ## _le, fp0, fp1, cc);   break;\
897
    case 15: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngt, fp0, fp1, cc);  break;\
898
    default: abort();                                                         \
899
    }                                                                         \
900
    tcg_temp_free_i##bits (fp0);                                              \
901
    tcg_temp_free_i##bits (fp1);                                              \
902
}
903

    
904
FOP_CONDS(, 0, d, FMT_D, 64)
905
FOP_CONDS(abs, 1, d, FMT_D, 64)
906
FOP_CONDS(, 0, s, FMT_S, 32)
907
FOP_CONDS(abs, 1, s, FMT_S, 32)
908
FOP_CONDS(, 0, ps, FMT_PS, 64)
909
FOP_CONDS(abs, 1, ps, FMT_PS, 64)
910
#undef FOP_CONDS
911
#undef gen_ldcmp_fpr32
912
#undef gen_ldcmp_fpr64
913

    
914
/* load/store instructions. */
915
#define OP_LD(insn,fname)                                                 \
916
static inline void op_ld_##insn(TCGv ret, TCGv arg1, DisasContext *ctx)   \
917
{                                                                         \
918
    tcg_gen_qemu_##fname(ret, arg1, ctx->mem_idx);                        \
919
}
920
OP_LD(lb,ld8s);
921
OP_LD(lbu,ld8u);
922
OP_LD(lh,ld16s);
923
OP_LD(lhu,ld16u);
924
OP_LD(lw,ld32s);
925
#if defined(TARGET_MIPS64)
926
OP_LD(lwu,ld32u);
927
OP_LD(ld,ld64);
928
#endif
929
#undef OP_LD
930

    
931
#define OP_ST(insn,fname)                                                  \
932
static inline void op_st_##insn(TCGv arg1, TCGv arg2, DisasContext *ctx)   \
933
{                                                                          \
934
    tcg_gen_qemu_##fname(arg1, arg2, ctx->mem_idx);                        \
935
}
936
OP_ST(sb,st8);
937
OP_ST(sh,st16);
938
OP_ST(sw,st32);
939
#if defined(TARGET_MIPS64)
940
OP_ST(sd,st64);
941
#endif
942
#undef OP_ST
943

    
944
#ifdef CONFIG_USER_ONLY
945
#define OP_LD_ATOMIC(insn,fname)                                           \
946
static inline void op_ld_##insn(TCGv ret, TCGv arg1, DisasContext *ctx)    \
947
{                                                                          \
948
    TCGv t0 = tcg_temp_new();                                              \
949
    tcg_gen_mov_tl(t0, arg1);                                              \
950
    tcg_gen_qemu_##fname(ret, arg1, ctx->mem_idx);                         \
951
    tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, lladdr));                \
952
    tcg_gen_st_tl(ret, cpu_env, offsetof(CPUState, llval));                \
953
    tcg_temp_free(t0);                                                     \
954
}
955
#else
956
#define OP_LD_ATOMIC(insn,fname)                                           \
957
static inline void op_ld_##insn(TCGv ret, TCGv arg1, DisasContext *ctx)    \
958
{                                                                          \
959
    gen_helper_2i(insn, ret, arg1, ctx->mem_idx);                          \
960
}
961
#endif
962
OP_LD_ATOMIC(ll,ld32s);
963
#if defined(TARGET_MIPS64)
964
OP_LD_ATOMIC(lld,ld64);
965
#endif
966
#undef OP_LD_ATOMIC
967

    
968
#ifdef CONFIG_USER_ONLY
969
#define OP_ST_ATOMIC(insn,fname,ldname,almask)                               \
970
static inline void op_st_##insn(TCGv arg1, TCGv arg2, int rt, DisasContext *ctx) \
971
{                                                                            \
972
    TCGv t0 = tcg_temp_new();                                                \
973
    int l1 = gen_new_label();                                                \
974
    int l2 = gen_new_label();                                                \
975
                                                                             \
976
    tcg_gen_andi_tl(t0, arg2, almask);                                       \
977
    tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);                              \
978
    tcg_gen_st_tl(arg2, cpu_env, offsetof(CPUState, CP0_BadVAddr));          \
979
    generate_exception(ctx, EXCP_AdES);                                      \
980
    gen_set_label(l1);                                                       \
981
    tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, lladdr));                  \
982
    tcg_gen_brcond_tl(TCG_COND_NE, arg2, t0, l2);                            \
983
    tcg_gen_movi_tl(t0, rt | ((almask << 3) & 0x20));                        \
984
    tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, llreg));                   \
985
    tcg_gen_st_tl(arg1, cpu_env, offsetof(CPUState, llnewval));              \
986
    gen_helper_0i(raise_exception, EXCP_SC);                                 \
987
    gen_set_label(l2);                                                       \
988
    tcg_gen_movi_tl(t0, 0);                                                  \
989
    gen_store_gpr(t0, rt);                                                   \
990
    tcg_temp_free(t0);                                                       \
991
}
992
#else
993
#define OP_ST_ATOMIC(insn,fname,ldname,almask)                               \
994
static inline void op_st_##insn(TCGv arg1, TCGv arg2, int rt, DisasContext *ctx) \
995
{                                                                            \
996
    TCGv t0 = tcg_temp_new();                                                \
997
    gen_helper_3i(insn, t0, arg1, arg2, ctx->mem_idx);                       \
998
    gen_store_gpr(t0, rt);                                                   \
999
    tcg_temp_free(t0);                                                       \
1000
}
1001
#endif
1002
OP_ST_ATOMIC(sc,st32,ld32s,0x3);
1003
#if defined(TARGET_MIPS64)
1004
OP_ST_ATOMIC(scd,st64,ld64,0x7);
1005
#endif
1006
#undef OP_ST_ATOMIC
1007

    
1008
static void gen_base_offset_addr (DisasContext *ctx, TCGv addr,
1009
                                  int base, int16_t offset)
1010
{
1011
    if (base == 0) {
1012
        tcg_gen_movi_tl(addr, offset);
1013
    } else if (offset == 0) {
1014
        gen_load_gpr(addr, base);
1015
    } else {
1016
        tcg_gen_movi_tl(addr, offset);
1017
        gen_op_addr_add(ctx, addr, cpu_gpr[base], addr);
1018
    }
1019
}
1020

    
1021
static target_ulong pc_relative_pc (DisasContext *ctx)
1022
{
1023
    target_ulong pc = ctx->pc;
1024

    
1025
    if (ctx->hflags & MIPS_HFLAG_BMASK) {
1026
        int branch_bytes = ctx->hflags & MIPS_HFLAG_BDS16 ? 2 : 4;
1027

    
1028
        pc -= branch_bytes;
1029
    }
1030

    
1031
    pc &= ~(target_ulong)3;
1032
    return pc;
1033
}
1034

    
1035
/* Load */
1036
static void gen_ld (CPUState *env, DisasContext *ctx, uint32_t opc,
1037
                    int rt, int base, int16_t offset)
1038
{
1039
    const char *opn = "ld";
1040
    TCGv t0, t1;
1041

    
1042
    if (rt == 0 && env->insn_flags & (INSN_LOONGSON2E | INSN_LOONGSON2F)) {
1043
        /* Loongson CPU uses a load to zero register for prefetch.
1044
           We emulate it as a NOP. On other CPU we must perform the
1045
           actual memory access. */
1046
        MIPS_DEBUG("NOP");
1047
        return;
1048
    }
1049

    
1050
    t0 = tcg_temp_new();
1051
    t1 = tcg_temp_new();
1052
    gen_base_offset_addr(ctx, t0, base, offset);
1053

    
1054
    switch (opc) {
1055
#if defined(TARGET_MIPS64)
1056
    case OPC_LWU:
1057
        save_cpu_state(ctx, 0);
1058
        op_ld_lwu(t0, t0, ctx);
1059
        gen_store_gpr(t0, rt);
1060
        opn = "lwu";
1061
        break;
1062
    case OPC_LD:
1063
        save_cpu_state(ctx, 0);
1064
        op_ld_ld(t0, t0, ctx);
1065
        gen_store_gpr(t0, rt);
1066
        opn = "ld";
1067
        break;
1068
    case OPC_LLD:
1069
        save_cpu_state(ctx, 0);
1070
        op_ld_lld(t0, t0, ctx);
1071
        gen_store_gpr(t0, rt);
1072
        opn = "lld";
1073
        break;
1074
    case OPC_LDL:
1075
        save_cpu_state(ctx, 1);
1076
        gen_load_gpr(t1, rt);
1077
        gen_helper_3i(ldl, t1, t1, t0, ctx->mem_idx);
1078
        gen_store_gpr(t1, rt);
1079
        opn = "ldl";
1080
        break;
1081
    case OPC_LDR:
1082
        save_cpu_state(ctx, 1);
1083
        gen_load_gpr(t1, rt);
1084
        gen_helper_3i(ldr, t1, t1, t0, ctx->mem_idx);
1085
        gen_store_gpr(t1, rt);
1086
        opn = "ldr";
1087
        break;
1088
    case OPC_LDPC:
1089
        save_cpu_state(ctx, 1);
1090
        tcg_gen_movi_tl(t1, pc_relative_pc(ctx));
1091
        gen_op_addr_add(ctx, t0, t0, t1);
1092
        op_ld_ld(t0, t0, ctx);
1093
        gen_store_gpr(t0, rt);
1094
        opn = "ldpc";
1095
        break;
1096
#endif
1097
    case OPC_LWPC:
1098
        save_cpu_state(ctx, 1);
1099
        tcg_gen_movi_tl(t1, pc_relative_pc(ctx));
1100
        gen_op_addr_add(ctx, t0, t0, t1);
1101
        op_ld_lw(t0, t0, ctx);
1102
        gen_store_gpr(t0, rt);
1103
        opn = "lwpc";
1104
        break;
1105
    case OPC_LW:
1106
        save_cpu_state(ctx, 0);
1107
        op_ld_lw(t0, t0, ctx);
1108
        gen_store_gpr(t0, rt);
1109
        opn = "lw";
1110
        break;
1111
    case OPC_LH:
1112
        save_cpu_state(ctx, 0);
1113
        op_ld_lh(t0, t0, ctx);
1114
        gen_store_gpr(t0, rt);
1115
        opn = "lh";
1116
        break;
1117
    case OPC_LHU:
1118
        save_cpu_state(ctx, 0);
1119
        op_ld_lhu(t0, t0, ctx);
1120
        gen_store_gpr(t0, rt);
1121
        opn = "lhu";
1122
        break;
1123
    case OPC_LB:
1124
        save_cpu_state(ctx, 0);
1125
        op_ld_lb(t0, t0, ctx);
1126
        gen_store_gpr(t0, rt);
1127
        opn = "lb";
1128
        break;
1129
    case OPC_LBU:
1130
        save_cpu_state(ctx, 0);
1131
        op_ld_lbu(t0, t0, ctx);
1132
        gen_store_gpr(t0, rt);
1133
        opn = "lbu";
1134
        break;
1135
    case OPC_LWL:
1136
        save_cpu_state(ctx, 1);
1137
        gen_load_gpr(t1, rt);
1138
        gen_helper_3i(lwl, t1, t1, t0, ctx->mem_idx);
1139
        gen_store_gpr(t1, rt);
1140
        opn = "lwl";
1141
        break;
1142
    case OPC_LWR:
1143
        save_cpu_state(ctx, 1);
1144
        gen_load_gpr(t1, rt);
1145
        gen_helper_3i(lwr, t1, t1, t0, ctx->mem_idx);
1146
        gen_store_gpr(t1, rt);
1147
        opn = "lwr";
1148
        break;
1149
    case OPC_LL:
1150
        save_cpu_state(ctx, 1);
1151
        op_ld_ll(t0, t0, ctx);
1152
        gen_store_gpr(t0, rt);
1153
        opn = "ll";
1154
        break;
1155
    }
1156
    (void)opn; /* avoid a compiler warning */
1157
    MIPS_DEBUG("%s %s, %d(%s)", opn, regnames[rt], offset, regnames[base]);
1158
    tcg_temp_free(t0);
1159
    tcg_temp_free(t1);
1160
}
1161

    
1162
/* Store */
1163
static void gen_st (DisasContext *ctx, uint32_t opc, int rt,
1164
                    int base, int16_t offset)
1165
{
1166
    const char *opn = "st";
1167
    TCGv t0 = tcg_temp_new();
1168
    TCGv t1 = tcg_temp_new();
1169

    
1170
    gen_base_offset_addr(ctx, t0, base, offset);
1171
    gen_load_gpr(t1, rt);
1172
    switch (opc) {
1173
#if defined(TARGET_MIPS64)
1174
    case OPC_SD:
1175
        save_cpu_state(ctx, 0);
1176
        op_st_sd(t1, t0, ctx);
1177
        opn = "sd";
1178
        break;
1179
    case OPC_SDL:
1180
        save_cpu_state(ctx, 1);
1181
        gen_helper_2i(sdl, t1, t0, ctx->mem_idx);
1182
        opn = "sdl";
1183
        break;
1184
    case OPC_SDR:
1185
        save_cpu_state(ctx, 1);
1186
        gen_helper_2i(sdr, t1, t0, ctx->mem_idx);
1187
        opn = "sdr";
1188
        break;
1189
#endif
1190
    case OPC_SW:
1191
        save_cpu_state(ctx, 0);
1192
        op_st_sw(t1, t0, ctx);
1193
        opn = "sw";
1194
        break;
1195
    case OPC_SH:
1196
        save_cpu_state(ctx, 0);
1197
        op_st_sh(t1, t0, ctx);
1198
        opn = "sh";
1199
        break;
1200
    case OPC_SB:
1201
        save_cpu_state(ctx, 0);
1202
        op_st_sb(t1, t0, ctx);
1203
        opn = "sb";
1204
        break;
1205
    case OPC_SWL:
1206
        save_cpu_state(ctx, 1);
1207
        gen_helper_2i(swl, t1, t0, ctx->mem_idx);
1208
        opn = "swl";
1209
        break;
1210
    case OPC_SWR:
1211
        save_cpu_state(ctx, 1);
1212
        gen_helper_2i(swr, t1, t0, ctx->mem_idx);
1213
        opn = "swr";
1214
        break;
1215
    }
1216
    (void)opn; /* avoid a compiler warning */
1217
    MIPS_DEBUG("%s %s, %d(%s)", opn, regnames[rt], offset, regnames[base]);
1218
    tcg_temp_free(t0);
1219
    tcg_temp_free(t1);
1220
}
1221

    
1222

    
1223
/* Store conditional */
1224
static void gen_st_cond (DisasContext *ctx, uint32_t opc, int rt,
1225
                         int base, int16_t offset)
1226
{
1227
    const char *opn = "st_cond";
1228
    TCGv t0, t1;
1229

    
1230
    t0 = tcg_temp_local_new();
1231

    
1232
    gen_base_offset_addr(ctx, t0, base, offset);
1233
    /* Don't do NOP if destination is zero: we must perform the actual
1234
       memory access. */
1235

    
1236
    t1 = tcg_temp_local_new();
1237
    gen_load_gpr(t1, rt);
1238
    switch (opc) {
1239
#if defined(TARGET_MIPS64)
1240
    case OPC_SCD:
1241
        save_cpu_state(ctx, 0);
1242
        op_st_scd(t1, t0, rt, ctx);
1243
        opn = "scd";
1244
        break;
1245
#endif
1246
    case OPC_SC:
1247
        save_cpu_state(ctx, 1);
1248
        op_st_sc(t1, t0, rt, ctx);
1249
        opn = "sc";
1250
        break;
1251
    }
1252
    (void)opn; /* avoid a compiler warning */
1253
    MIPS_DEBUG("%s %s, %d(%s)", opn, regnames[rt], offset, regnames[base]);
1254
    tcg_temp_free(t1);
1255
    tcg_temp_free(t0);
1256
}
1257

    
1258
/* Load and store */
1259
static void gen_flt_ldst (DisasContext *ctx, uint32_t opc, int ft,
1260
                          int base, int16_t offset)
1261
{
1262
    const char *opn = "flt_ldst";
1263
    TCGv t0 = tcg_temp_new();
1264

    
1265
    gen_base_offset_addr(ctx, t0, base, offset);
1266
    /* Don't do NOP if destination is zero: we must perform the actual
1267
       memory access. */
1268
    switch (opc) {
1269
    case OPC_LWC1:
1270
        {
1271
            TCGv_i32 fp0 = tcg_temp_new_i32();
1272

    
1273
            tcg_gen_qemu_ld32s(t0, t0, ctx->mem_idx);
1274
            tcg_gen_trunc_tl_i32(fp0, t0);
1275
            gen_store_fpr32(fp0, ft);
1276
            tcg_temp_free_i32(fp0);
1277
        }
1278
        opn = "lwc1";
1279
        break;
1280
    case OPC_SWC1:
1281
        {
1282
            TCGv_i32 fp0 = tcg_temp_new_i32();
1283
            TCGv t1 = tcg_temp_new();
1284

    
1285
            gen_load_fpr32(fp0, ft);
1286
            tcg_gen_extu_i32_tl(t1, fp0);
1287
            tcg_gen_qemu_st32(t1, t0, ctx->mem_idx);
1288
            tcg_temp_free(t1);
1289
            tcg_temp_free_i32(fp0);
1290
        }
1291
        opn = "swc1";
1292
        break;
1293
    case OPC_LDC1:
1294
        {
1295
            TCGv_i64 fp0 = tcg_temp_new_i64();
1296

    
1297
            tcg_gen_qemu_ld64(fp0, t0, ctx->mem_idx);
1298
            gen_store_fpr64(ctx, fp0, ft);
1299
            tcg_temp_free_i64(fp0);
1300
        }
1301
        opn = "ldc1";
1302
        break;
1303
    case OPC_SDC1:
1304
        {
1305
            TCGv_i64 fp0 = tcg_temp_new_i64();
1306

    
1307
            gen_load_fpr64(ctx, fp0, ft);
1308
            tcg_gen_qemu_st64(fp0, t0, ctx->mem_idx);
1309
            tcg_temp_free_i64(fp0);
1310
        }
1311
        opn = "sdc1";
1312
        break;
1313
    default:
1314
        MIPS_INVAL(opn);
1315
        generate_exception(ctx, EXCP_RI);
1316
        goto out;
1317
    }
1318
    (void)opn; /* avoid a compiler warning */
1319
    MIPS_DEBUG("%s %s, %d(%s)", opn, fregnames[ft], offset, regnames[base]);
1320
 out:
1321
    tcg_temp_free(t0);
1322
}
1323

    
1324
static void gen_cop1_ldst(CPUState *env, DisasContext *ctx,
1325
                          uint32_t op, int rt, int rs, int16_t imm)
1326
{
1327
    if (env->CP0_Config1 & (1 << CP0C1_FP)) {
1328
        check_cp1_enabled(ctx);
1329
        gen_flt_ldst(ctx, op, rt, rs, imm);
1330
    } else {
1331
        generate_exception_err(ctx, EXCP_CpU, 1);
1332
    }
1333
}
1334

    
1335
/* Arithmetic with immediate operand */
1336
static void gen_arith_imm (CPUState *env, DisasContext *ctx, uint32_t opc,
1337
                           int rt, int rs, int16_t imm)
1338
{
1339
    target_ulong uimm = (target_long)imm; /* Sign extend to 32/64 bits */
1340
    const char *opn = "imm arith";
1341

    
1342
    if (rt == 0 && opc != OPC_ADDI && opc != OPC_DADDI) {
1343
        /* If no destination, treat it as a NOP.
1344
           For addi, we must generate the overflow exception when needed. */
1345
        MIPS_DEBUG("NOP");
1346
        return;
1347
    }
1348
    switch (opc) {
1349
    case OPC_ADDI:
1350
        {
1351
            TCGv t0 = tcg_temp_local_new();
1352
            TCGv t1 = tcg_temp_new();
1353
            TCGv t2 = tcg_temp_new();
1354
            int l1 = gen_new_label();
1355

    
1356
            gen_load_gpr(t1, rs);
1357
            tcg_gen_addi_tl(t0, t1, uimm);
1358
            tcg_gen_ext32s_tl(t0, t0);
1359

    
1360
            tcg_gen_xori_tl(t1, t1, ~uimm);
1361
            tcg_gen_xori_tl(t2, t0, uimm);
1362
            tcg_gen_and_tl(t1, t1, t2);
1363
            tcg_temp_free(t2);
1364
            tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1365
            tcg_temp_free(t1);
1366
            /* operands of same sign, result different sign */
1367
            generate_exception(ctx, EXCP_OVERFLOW);
1368
            gen_set_label(l1);
1369
            tcg_gen_ext32s_tl(t0, t0);
1370
            gen_store_gpr(t0, rt);
1371
            tcg_temp_free(t0);
1372
        }
1373
        opn = "addi";
1374
        break;
1375
    case OPC_ADDIU:
1376
        if (rs != 0) {
1377
            tcg_gen_addi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1378
            tcg_gen_ext32s_tl(cpu_gpr[rt], cpu_gpr[rt]);
1379
        } else {
1380
            tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1381
        }
1382
        opn = "addiu";
1383
        break;
1384
#if defined(TARGET_MIPS64)
1385
    case OPC_DADDI:
1386
        {
1387
            TCGv t0 = tcg_temp_local_new();
1388
            TCGv t1 = tcg_temp_new();
1389
            TCGv t2 = tcg_temp_new();
1390
            int l1 = gen_new_label();
1391

    
1392
            gen_load_gpr(t1, rs);
1393
            tcg_gen_addi_tl(t0, t1, uimm);
1394

    
1395
            tcg_gen_xori_tl(t1, t1, ~uimm);
1396
            tcg_gen_xori_tl(t2, t0, uimm);
1397
            tcg_gen_and_tl(t1, t1, t2);
1398
            tcg_temp_free(t2);
1399
            tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1400
            tcg_temp_free(t1);
1401
            /* operands of same sign, result different sign */
1402
            generate_exception(ctx, EXCP_OVERFLOW);
1403
            gen_set_label(l1);
1404
            gen_store_gpr(t0, rt);
1405
            tcg_temp_free(t0);
1406
        }
1407
        opn = "daddi";
1408
        break;
1409
    case OPC_DADDIU:
1410
        if (rs != 0) {
1411
            tcg_gen_addi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1412
        } else {
1413
            tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1414
        }
1415
        opn = "daddiu";
1416
        break;
1417
#endif
1418
    }
1419
    (void)opn; /* avoid a compiler warning */
1420
    MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1421
}
1422

    
1423
/* Logic with immediate operand */
1424
static void gen_logic_imm (CPUState *env, uint32_t opc, int rt, int rs, int16_t imm)
1425
{
1426
    target_ulong uimm;
1427
    const char *opn = "imm logic";
1428

    
1429
    if (rt == 0) {
1430
        /* If no destination, treat it as a NOP. */
1431
        MIPS_DEBUG("NOP");
1432
        return;
1433
    }
1434
    uimm = (uint16_t)imm;
1435
    switch (opc) {
1436
    case OPC_ANDI:
1437
        if (likely(rs != 0))
1438
            tcg_gen_andi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1439
        else
1440
            tcg_gen_movi_tl(cpu_gpr[rt], 0);
1441
        opn = "andi";
1442
        break;
1443
    case OPC_ORI:
1444
        if (rs != 0)
1445
            tcg_gen_ori_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1446
        else
1447
            tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1448
        opn = "ori";
1449
        break;
1450
    case OPC_XORI:
1451
        if (likely(rs != 0))
1452
            tcg_gen_xori_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1453
        else
1454
            tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1455
        opn = "xori";
1456
        break;
1457
    case OPC_LUI:
1458
        tcg_gen_movi_tl(cpu_gpr[rt], imm << 16);
1459
        opn = "lui";
1460
        break;
1461
    }
1462
    (void)opn; /* avoid a compiler warning */
1463
    MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1464
}
1465

    
1466
/* Set on less than with immediate operand */
1467
static void gen_slt_imm (CPUState *env, uint32_t opc, int rt, int rs, int16_t imm)
1468
{
1469
    target_ulong uimm = (target_long)imm; /* Sign extend to 32/64 bits */
1470
    const char *opn = "imm arith";
1471
    TCGv t0;
1472

    
1473
    if (rt == 0) {
1474
        /* If no destination, treat it as a NOP. */
1475
        MIPS_DEBUG("NOP");
1476
        return;
1477
    }
1478
    t0 = tcg_temp_new();
1479
    gen_load_gpr(t0, rs);
1480
    switch (opc) {
1481
    case OPC_SLTI:
1482
        tcg_gen_setcondi_tl(TCG_COND_LT, cpu_gpr[rt], t0, uimm);
1483
        opn = "slti";
1484
        break;
1485
    case OPC_SLTIU:
1486
        tcg_gen_setcondi_tl(TCG_COND_LTU, cpu_gpr[rt], t0, uimm);
1487
        opn = "sltiu";
1488
        break;
1489
    }
1490
    (void)opn; /* avoid a compiler warning */
1491
    MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1492
    tcg_temp_free(t0);
1493
}
1494

    
1495
/* Shifts with immediate operand */
1496
static void gen_shift_imm(CPUState *env, DisasContext *ctx, uint32_t opc,
1497
                          int rt, int rs, int16_t imm)
1498
{
1499
    target_ulong uimm = ((uint16_t)imm) & 0x1f;
1500
    const char *opn = "imm shift";
1501
    TCGv t0;
1502

    
1503
    if (rt == 0) {
1504
        /* If no destination, treat it as a NOP. */
1505
        MIPS_DEBUG("NOP");
1506
        return;
1507
    }
1508

    
1509
    t0 = tcg_temp_new();
1510
    gen_load_gpr(t0, rs);
1511
    switch (opc) {
1512
    case OPC_SLL:
1513
        tcg_gen_shli_tl(t0, t0, uimm);
1514
        tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
1515
        opn = "sll";
1516
        break;
1517
    case OPC_SRA:
1518
        tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm);
1519
        opn = "sra";
1520
        break;
1521
    case OPC_SRL:
1522
        if (uimm != 0) {
1523
            tcg_gen_ext32u_tl(t0, t0);
1524
            tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm);
1525
        } else {
1526
            tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
1527
        }
1528
        opn = "srl";
1529
        break;
1530
    case OPC_ROTR:
1531
        if (uimm != 0) {
1532
            TCGv_i32 t1 = tcg_temp_new_i32();
1533

    
1534
            tcg_gen_trunc_tl_i32(t1, t0);
1535
            tcg_gen_rotri_i32(t1, t1, uimm);
1536
            tcg_gen_ext_i32_tl(cpu_gpr[rt], t1);
1537
            tcg_temp_free_i32(t1);
1538
        } else {
1539
            tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
1540
        }
1541
        opn = "rotr";
1542
        break;
1543
#if defined(TARGET_MIPS64)
1544
    case OPC_DSLL:
1545
        tcg_gen_shli_tl(cpu_gpr[rt], t0, uimm);
1546
        opn = "dsll";
1547
        break;
1548
    case OPC_DSRA:
1549
        tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm);
1550
        opn = "dsra";
1551
        break;
1552
    case OPC_DSRL:
1553
        tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm);
1554
        opn = "dsrl";
1555
        break;
1556
    case OPC_DROTR:
1557
        if (uimm != 0) {
1558
            tcg_gen_rotri_tl(cpu_gpr[rt], t0, uimm);
1559
        } else {
1560
            tcg_gen_mov_tl(cpu_gpr[rt], t0);
1561
        }
1562
        opn = "drotr";
1563
        break;
1564
    case OPC_DSLL32:
1565
        tcg_gen_shli_tl(cpu_gpr[rt], t0, uimm + 32);
1566
        opn = "dsll32";
1567
        break;
1568
    case OPC_DSRA32:
1569
        tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm + 32);
1570
        opn = "dsra32";
1571
        break;
1572
    case OPC_DSRL32:
1573
        tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm + 32);
1574
        opn = "dsrl32";
1575
        break;
1576
    case OPC_DROTR32:
1577
        tcg_gen_rotri_tl(cpu_gpr[rt], t0, uimm + 32);
1578
        opn = "drotr32";
1579
        break;
1580
#endif
1581
    }
1582
    (void)opn; /* avoid a compiler warning */
1583
    MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1584
    tcg_temp_free(t0);
1585
}
1586

    
1587
/* Arithmetic */
1588
static void gen_arith (CPUState *env, DisasContext *ctx, uint32_t opc,
1589
                       int rd, int rs, int rt)
1590
{
1591
    const char *opn = "arith";
1592

    
1593
    if (rd == 0 && opc != OPC_ADD && opc != OPC_SUB
1594
       && opc != OPC_DADD && opc != OPC_DSUB) {
1595
        /* If no destination, treat it as a NOP.
1596
           For add & sub, we must generate the overflow exception when needed. */
1597
        MIPS_DEBUG("NOP");
1598
        return;
1599
    }
1600

    
1601
    switch (opc) {
1602
    case OPC_ADD:
1603
        {
1604
            TCGv t0 = tcg_temp_local_new();
1605
            TCGv t1 = tcg_temp_new();
1606
            TCGv t2 = tcg_temp_new();
1607
            int l1 = gen_new_label();
1608

    
1609
            gen_load_gpr(t1, rs);
1610
            gen_load_gpr(t2, rt);
1611
            tcg_gen_add_tl(t0, t1, t2);
1612
            tcg_gen_ext32s_tl(t0, t0);
1613
            tcg_gen_xor_tl(t1, t1, t2);
1614
            tcg_gen_xor_tl(t2, t0, t2);
1615
            tcg_gen_andc_tl(t1, t2, t1);
1616
            tcg_temp_free(t2);
1617
            tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1618
            tcg_temp_free(t1);
1619
            /* operands of same sign, result different sign */
1620
            generate_exception(ctx, EXCP_OVERFLOW);
1621
            gen_set_label(l1);
1622
            gen_store_gpr(t0, rd);
1623
            tcg_temp_free(t0);
1624
        }
1625
        opn = "add";
1626
        break;
1627
    case OPC_ADDU:
1628
        if (rs != 0 && rt != 0) {
1629
            tcg_gen_add_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1630
            tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1631
        } else if (rs == 0 && rt != 0) {
1632
            tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1633
        } else if (rs != 0 && rt == 0) {
1634
            tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1635
        } else {
1636
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
1637
        }
1638
        opn = "addu";
1639
        break;
1640
    case OPC_SUB:
1641
        {
1642
            TCGv t0 = tcg_temp_local_new();
1643
            TCGv t1 = tcg_temp_new();
1644
            TCGv t2 = tcg_temp_new();
1645
            int l1 = gen_new_label();
1646

    
1647
            gen_load_gpr(t1, rs);
1648
            gen_load_gpr(t2, rt);
1649
            tcg_gen_sub_tl(t0, t1, t2);
1650
            tcg_gen_ext32s_tl(t0, t0);
1651
            tcg_gen_xor_tl(t2, t1, t2);
1652
            tcg_gen_xor_tl(t1, t0, t1);
1653
            tcg_gen_and_tl(t1, t1, t2);
1654
            tcg_temp_free(t2);
1655
            tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1656
            tcg_temp_free(t1);
1657
            /* operands of different sign, first operand and result different sign */
1658
            generate_exception(ctx, EXCP_OVERFLOW);
1659
            gen_set_label(l1);
1660
            gen_store_gpr(t0, rd);
1661
            tcg_temp_free(t0);
1662
        }
1663
        opn = "sub";
1664
        break;
1665
    case OPC_SUBU:
1666
        if (rs != 0 && rt != 0) {
1667
            tcg_gen_sub_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1668
            tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1669
        } else if (rs == 0 && rt != 0) {
1670
            tcg_gen_neg_tl(cpu_gpr[rd], cpu_gpr[rt]);
1671
            tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1672
        } else if (rs != 0 && rt == 0) {
1673
            tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1674
        } else {
1675
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
1676
        }
1677
        opn = "subu";
1678
        break;
1679
#if defined(TARGET_MIPS64)
1680
    case OPC_DADD:
1681
        {
1682
            TCGv t0 = tcg_temp_local_new();
1683
            TCGv t1 = tcg_temp_new();
1684
            TCGv t2 = tcg_temp_new();
1685
            int l1 = gen_new_label();
1686

    
1687
            gen_load_gpr(t1, rs);
1688
            gen_load_gpr(t2, rt);
1689
            tcg_gen_add_tl(t0, t1, t2);
1690
            tcg_gen_xor_tl(t1, t1, t2);
1691
            tcg_gen_xor_tl(t2, t0, t2);
1692
            tcg_gen_andc_tl(t1, t2, t1);
1693
            tcg_temp_free(t2);
1694
            tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1695
            tcg_temp_free(t1);
1696
            /* operands of same sign, result different sign */
1697
            generate_exception(ctx, EXCP_OVERFLOW);
1698
            gen_set_label(l1);
1699
            gen_store_gpr(t0, rd);
1700
            tcg_temp_free(t0);
1701
        }
1702
        opn = "dadd";
1703
        break;
1704
    case OPC_DADDU:
1705
        if (rs != 0 && rt != 0) {
1706
            tcg_gen_add_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1707
        } else if (rs == 0 && rt != 0) {
1708
            tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1709
        } else if (rs != 0 && rt == 0) {
1710
            tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1711
        } else {
1712
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
1713
        }
1714
        opn = "daddu";
1715
        break;
1716
    case OPC_DSUB:
1717
        {
1718
            TCGv t0 = tcg_temp_local_new();
1719
            TCGv t1 = tcg_temp_new();
1720
            TCGv t2 = tcg_temp_new();
1721
            int l1 = gen_new_label();
1722

    
1723
            gen_load_gpr(t1, rs);
1724
            gen_load_gpr(t2, rt);
1725
            tcg_gen_sub_tl(t0, t1, t2);
1726
            tcg_gen_xor_tl(t2, t1, t2);
1727
            tcg_gen_xor_tl(t1, t0, t1);
1728
            tcg_gen_and_tl(t1, t1, t2);
1729
            tcg_temp_free(t2);
1730
            tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1731
            tcg_temp_free(t1);
1732
            /* operands of different sign, first operand and result different sign */
1733
            generate_exception(ctx, EXCP_OVERFLOW);
1734
            gen_set_label(l1);
1735
            gen_store_gpr(t0, rd);
1736
            tcg_temp_free(t0);
1737
        }
1738
        opn = "dsub";
1739
        break;
1740
    case OPC_DSUBU:
1741
        if (rs != 0 && rt != 0) {
1742
            tcg_gen_sub_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1743
        } else if (rs == 0 && rt != 0) {
1744
            tcg_gen_neg_tl(cpu_gpr[rd], cpu_gpr[rt]);
1745
        } else if (rs != 0 && rt == 0) {
1746
            tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1747
        } else {
1748
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
1749
        }
1750
        opn = "dsubu";
1751
        break;
1752
#endif
1753
    case OPC_MUL:
1754
        if (likely(rs != 0 && rt != 0)) {
1755
            tcg_gen_mul_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1756
            tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1757
        } else {
1758
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
1759
        }
1760
        opn = "mul";
1761
        break;
1762
    }
1763
    (void)opn; /* avoid a compiler warning */
1764
    MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1765
}
1766

    
1767
/* Conditional move */
1768
static void gen_cond_move (CPUState *env, uint32_t opc, int rd, int rs, int rt)
1769
{
1770
    const char *opn = "cond move";
1771
    int l1;
1772

    
1773
    if (rd == 0) {
1774
        /* If no destination, treat it as a NOP.
1775
           For add & sub, we must generate the overflow exception when needed. */
1776
        MIPS_DEBUG("NOP");
1777
        return;
1778
    }
1779

    
1780
    l1 = gen_new_label();
1781
    switch (opc) {
1782
    case OPC_MOVN:
1783
        if (likely(rt != 0))
1784
            tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[rt], 0, l1);
1785
        else
1786
            tcg_gen_br(l1);
1787
        opn = "movn";
1788
        break;
1789
    case OPC_MOVZ:
1790
        if (likely(rt != 0))
1791
            tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[rt], 0, l1);
1792
        opn = "movz";
1793
        break;
1794
    }
1795
    if (rs != 0)
1796
        tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1797
    else
1798
        tcg_gen_movi_tl(cpu_gpr[rd], 0);
1799
    gen_set_label(l1);
1800

    
1801
    (void)opn; /* avoid a compiler warning */
1802
    MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1803
}
1804

    
1805
/* Logic */
1806
static void gen_logic (CPUState *env, uint32_t opc, int rd, int rs, int rt)
1807
{
1808
    const char *opn = "logic";
1809

    
1810
    if (rd == 0) {
1811
        /* If no destination, treat it as a NOP. */
1812
        MIPS_DEBUG("NOP");
1813
        return;
1814
    }
1815

    
1816
    switch (opc) {
1817
    case OPC_AND:
1818
        if (likely(rs != 0 && rt != 0)) {
1819
            tcg_gen_and_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1820
        } else {
1821
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
1822
        }
1823
        opn = "and";
1824
        break;
1825
    case OPC_NOR:
1826
        if (rs != 0 && rt != 0) {
1827
            tcg_gen_nor_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1828
        } else if (rs == 0 && rt != 0) {
1829
            tcg_gen_not_tl(cpu_gpr[rd], cpu_gpr[rt]);
1830
        } else if (rs != 0 && rt == 0) {
1831
            tcg_gen_not_tl(cpu_gpr[rd], cpu_gpr[rs]);
1832
        } else {
1833
            tcg_gen_movi_tl(cpu_gpr[rd], ~((target_ulong)0));
1834
        }
1835
        opn = "nor";
1836
        break;
1837
    case OPC_OR:
1838
        if (likely(rs != 0 && rt != 0)) {
1839
            tcg_gen_or_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1840
        } else if (rs == 0 && rt != 0) {
1841
            tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1842
        } else if (rs != 0 && rt == 0) {
1843
            tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1844
        } else {
1845
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
1846
        }
1847
        opn = "or";
1848
        break;
1849
    case OPC_XOR:
1850
        if (likely(rs != 0 && rt != 0)) {
1851
            tcg_gen_xor_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1852
        } else if (rs == 0 && rt != 0) {
1853
            tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1854
        } else if (rs != 0 && rt == 0) {
1855
            tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1856
        } else {
1857
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
1858
        }
1859
        opn = "xor";
1860
        break;
1861
    }
1862
    (void)opn; /* avoid a compiler warning */
1863
    MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1864
}
1865

    
1866
/* Set on lower than */
1867
static void gen_slt (CPUState *env, uint32_t opc, int rd, int rs, int rt)
1868
{
1869
    const char *opn = "slt";
1870
    TCGv t0, t1;
1871

    
1872
    if (rd == 0) {
1873
        /* If no destination, treat it as a NOP. */
1874
        MIPS_DEBUG("NOP");
1875
        return;
1876
    }
1877

    
1878
    t0 = tcg_temp_new();
1879
    t1 = tcg_temp_new();
1880
    gen_load_gpr(t0, rs);
1881
    gen_load_gpr(t1, rt);
1882
    switch (opc) {
1883
    case OPC_SLT:
1884
        tcg_gen_setcond_tl(TCG_COND_LT, cpu_gpr[rd], t0, t1);
1885
        opn = "slt";
1886
        break;
1887
    case OPC_SLTU:
1888
        tcg_gen_setcond_tl(TCG_COND_LTU, cpu_gpr[rd], t0, t1);
1889
        opn = "sltu";
1890
        break;
1891
    }
1892
    (void)opn; /* avoid a compiler warning */
1893
    MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1894
    tcg_temp_free(t0);
1895
    tcg_temp_free(t1);
1896
}
1897

    
1898
/* Shifts */
1899
static void gen_shift (CPUState *env, DisasContext *ctx, uint32_t opc,
1900
                       int rd, int rs, int rt)
1901
{
1902
    const char *opn = "shifts";
1903
    TCGv t0, t1;
1904

    
1905
    if (rd == 0) {
1906
        /* If no destination, treat it as a NOP.
1907
           For add & sub, we must generate the overflow exception when needed. */
1908
        MIPS_DEBUG("NOP");
1909
        return;
1910
    }
1911

    
1912
    t0 = tcg_temp_new();
1913
    t1 = tcg_temp_new();
1914
    gen_load_gpr(t0, rs);
1915
    gen_load_gpr(t1, rt);
1916
    switch (opc) {
1917
    case OPC_SLLV:
1918
        tcg_gen_andi_tl(t0, t0, 0x1f);
1919
        tcg_gen_shl_tl(t0, t1, t0);
1920
        tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
1921
        opn = "sllv";
1922
        break;
1923
    case OPC_SRAV:
1924
        tcg_gen_andi_tl(t0, t0, 0x1f);
1925
        tcg_gen_sar_tl(cpu_gpr[rd], t1, t0);
1926
        opn = "srav";
1927
        break;
1928
    case OPC_SRLV:
1929
        tcg_gen_ext32u_tl(t1, t1);
1930
        tcg_gen_andi_tl(t0, t0, 0x1f);
1931
        tcg_gen_shr_tl(t0, t1, t0);
1932
        tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
1933
        opn = "srlv";
1934
        break;
1935
    case OPC_ROTRV:
1936
        {
1937
            TCGv_i32 t2 = tcg_temp_new_i32();
1938
            TCGv_i32 t3 = tcg_temp_new_i32();
1939

    
1940
            tcg_gen_trunc_tl_i32(t2, t0);
1941
            tcg_gen_trunc_tl_i32(t3, t1);
1942
            tcg_gen_andi_i32(t2, t2, 0x1f);
1943
            tcg_gen_rotr_i32(t2, t3, t2);
1944
            tcg_gen_ext_i32_tl(cpu_gpr[rd], t2);
1945
            tcg_temp_free_i32(t2);
1946
            tcg_temp_free_i32(t3);
1947
            opn = "rotrv";
1948
        }
1949
        break;
1950
#if defined(TARGET_MIPS64)
1951
    case OPC_DSLLV:
1952
        tcg_gen_andi_tl(t0, t0, 0x3f);
1953
        tcg_gen_shl_tl(cpu_gpr[rd], t1, t0);
1954
        opn = "dsllv";
1955
        break;
1956
    case OPC_DSRAV:
1957
        tcg_gen_andi_tl(t0, t0, 0x3f);
1958
        tcg_gen_sar_tl(cpu_gpr[rd], t1, t0);
1959
        opn = "dsrav";
1960
        break;
1961
    case OPC_DSRLV:
1962
        tcg_gen_andi_tl(t0, t0, 0x3f);
1963
        tcg_gen_shr_tl(cpu_gpr[rd], t1, t0);
1964
        opn = "dsrlv";
1965
        break;
1966
    case OPC_DROTRV:
1967
        tcg_gen_andi_tl(t0, t0, 0x3f);
1968
        tcg_gen_rotr_tl(cpu_gpr[rd], t1, t0);
1969
        opn = "drotrv";
1970
        break;
1971
#endif
1972
    }
1973
    (void)opn; /* avoid a compiler warning */
1974
    MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1975
    tcg_temp_free(t0);
1976
    tcg_temp_free(t1);
1977
}
1978

    
1979
/* Arithmetic on HI/LO registers */
1980
static void gen_HILO (DisasContext *ctx, uint32_t opc, int reg)
1981
{
1982
    const char *opn = "hilo";
1983

    
1984
    if (reg == 0 && (opc == OPC_MFHI || opc == OPC_MFLO)) {
1985
        /* Treat as NOP. */
1986
        MIPS_DEBUG("NOP");
1987
        return;
1988
    }
1989
    switch (opc) {
1990
    case OPC_MFHI:
1991
        tcg_gen_mov_tl(cpu_gpr[reg], cpu_HI[0]);
1992
        opn = "mfhi";
1993
        break;
1994
    case OPC_MFLO:
1995
        tcg_gen_mov_tl(cpu_gpr[reg], cpu_LO[0]);
1996
        opn = "mflo";
1997
        break;
1998
    case OPC_MTHI:
1999
        if (reg != 0)
2000
            tcg_gen_mov_tl(cpu_HI[0], cpu_gpr[reg]);
2001
        else
2002
            tcg_gen_movi_tl(cpu_HI[0], 0);
2003
        opn = "mthi";
2004
        break;
2005
    case OPC_MTLO:
2006
        if (reg != 0)
2007
            tcg_gen_mov_tl(cpu_LO[0], cpu_gpr[reg]);
2008
        else
2009
            tcg_gen_movi_tl(cpu_LO[0], 0);
2010
        opn = "mtlo";
2011
        break;
2012
    }
2013
    (void)opn; /* avoid a compiler warning */
2014
    MIPS_DEBUG("%s %s", opn, regnames[reg]);
2015
}
2016

    
2017
static void gen_muldiv (DisasContext *ctx, uint32_t opc,
2018
                        int rs, int rt)
2019
{
2020
    const char *opn = "mul/div";
2021
    TCGv t0, t1;
2022

    
2023
    switch (opc) {
2024
    case OPC_DIV:
2025
    case OPC_DIVU:
2026
#if defined(TARGET_MIPS64)
2027
    case OPC_DDIV:
2028
    case OPC_DDIVU:
2029
#endif
2030
        t0 = tcg_temp_local_new();
2031
        t1 = tcg_temp_local_new();
2032
        break;
2033
    default:
2034
        t0 = tcg_temp_new();
2035
        t1 = tcg_temp_new();
2036
        break;
2037
    }
2038

    
2039
    gen_load_gpr(t0, rs);
2040
    gen_load_gpr(t1, rt);
2041
    switch (opc) {
2042
    case OPC_DIV:
2043
        {
2044
            int l1 = gen_new_label();
2045
            int l2 = gen_new_label();
2046

    
2047
            tcg_gen_ext32s_tl(t0, t0);
2048
            tcg_gen_ext32s_tl(t1, t1);
2049
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2050
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, INT_MIN, l2);
2051
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1, l2);
2052

    
2053
            tcg_gen_mov_tl(cpu_LO[0], t0);
2054
            tcg_gen_movi_tl(cpu_HI[0], 0);
2055
            tcg_gen_br(l1);
2056
            gen_set_label(l2);
2057
            tcg_gen_div_tl(cpu_LO[0], t0, t1);
2058
            tcg_gen_rem_tl(cpu_HI[0], t0, t1);
2059
            tcg_gen_ext32s_tl(cpu_LO[0], cpu_LO[0]);
2060
            tcg_gen_ext32s_tl(cpu_HI[0], cpu_HI[0]);
2061
            gen_set_label(l1);
2062
        }
2063
        opn = "div";
2064
        break;
2065
    case OPC_DIVU:
2066
        {
2067
            int l1 = gen_new_label();
2068

    
2069
            tcg_gen_ext32u_tl(t0, t0);
2070
            tcg_gen_ext32u_tl(t1, t1);
2071
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2072
            tcg_gen_divu_tl(cpu_LO[0], t0, t1);
2073
            tcg_gen_remu_tl(cpu_HI[0], t0, t1);
2074
            tcg_gen_ext32s_tl(cpu_LO[0], cpu_LO[0]);
2075
            tcg_gen_ext32s_tl(cpu_HI[0], cpu_HI[0]);
2076
            gen_set_label(l1);
2077
        }
2078
        opn = "divu";
2079
        break;
2080
    case OPC_MULT:
2081
        {
2082
            TCGv_i64 t2 = tcg_temp_new_i64();
2083
            TCGv_i64 t3 = tcg_temp_new_i64();
2084

    
2085
            tcg_gen_ext_tl_i64(t2, t0);
2086
            tcg_gen_ext_tl_i64(t3, t1);
2087
            tcg_gen_mul_i64(t2, t2, t3);
2088
            tcg_temp_free_i64(t3);
2089
            tcg_gen_trunc_i64_tl(t0, t2);
2090
            tcg_gen_shri_i64(t2, t2, 32);
2091
            tcg_gen_trunc_i64_tl(t1, t2);
2092
            tcg_temp_free_i64(t2);
2093
            tcg_gen_ext32s_tl(cpu_LO[0], t0);
2094
            tcg_gen_ext32s_tl(cpu_HI[0], t1);
2095
        }
2096
        opn = "mult";
2097
        break;
2098
    case OPC_MULTU:
2099
        {
2100
            TCGv_i64 t2 = tcg_temp_new_i64();
2101
            TCGv_i64 t3 = tcg_temp_new_i64();
2102

    
2103
            tcg_gen_ext32u_tl(t0, t0);
2104
            tcg_gen_ext32u_tl(t1, t1);
2105
            tcg_gen_extu_tl_i64(t2, t0);
2106
            tcg_gen_extu_tl_i64(t3, t1);
2107
            tcg_gen_mul_i64(t2, t2, t3);
2108
            tcg_temp_free_i64(t3);
2109
            tcg_gen_trunc_i64_tl(t0, t2);
2110
            tcg_gen_shri_i64(t2, t2, 32);
2111
            tcg_gen_trunc_i64_tl(t1, t2);
2112
            tcg_temp_free_i64(t2);
2113
            tcg_gen_ext32s_tl(cpu_LO[0], t0);
2114
            tcg_gen_ext32s_tl(cpu_HI[0], t1);
2115
        }
2116
        opn = "multu";
2117
        break;
2118
#if defined(TARGET_MIPS64)
2119
    case OPC_DDIV:
2120
        {
2121
            int l1 = gen_new_label();
2122
            int l2 = gen_new_label();
2123

    
2124
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2125
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, -1LL << 63, l2);
2126
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1LL, l2);
2127
            tcg_gen_mov_tl(cpu_LO[0], t0);
2128
            tcg_gen_movi_tl(cpu_HI[0], 0);
2129
            tcg_gen_br(l1);
2130
            gen_set_label(l2);
2131
            tcg_gen_div_i64(cpu_LO[0], t0, t1);
2132
            tcg_gen_rem_i64(cpu_HI[0], t0, t1);
2133
            gen_set_label(l1);
2134
        }
2135
        opn = "ddiv";
2136
        break;
2137
    case OPC_DDIVU:
2138
        {
2139
            int l1 = gen_new_label();
2140

    
2141
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2142
            tcg_gen_divu_i64(cpu_LO[0], t0, t1);
2143
            tcg_gen_remu_i64(cpu_HI[0], t0, t1);
2144
            gen_set_label(l1);
2145
        }
2146
        opn = "ddivu";
2147
        break;
2148
    case OPC_DMULT:
2149
        gen_helper_dmult(t0, t1);
2150
        opn = "dmult";
2151
        break;
2152
    case OPC_DMULTU:
2153
        gen_helper_dmultu(t0, t1);
2154
        opn = "dmultu";
2155
        break;
2156
#endif
2157
    case OPC_MADD:
2158
        {
2159
            TCGv_i64 t2 = tcg_temp_new_i64();
2160
            TCGv_i64 t3 = tcg_temp_new_i64();
2161

    
2162
            tcg_gen_ext_tl_i64(t2, t0);
2163
            tcg_gen_ext_tl_i64(t3, t1);
2164
            tcg_gen_mul_i64(t2, t2, t3);
2165
            tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2166
            tcg_gen_add_i64(t2, t2, t3);
2167
            tcg_temp_free_i64(t3);
2168
            tcg_gen_trunc_i64_tl(t0, t2);
2169
            tcg_gen_shri_i64(t2, t2, 32);
2170
            tcg_gen_trunc_i64_tl(t1, t2);
2171
            tcg_temp_free_i64(t2);
2172
            tcg_gen_ext32s_tl(cpu_LO[0], t0);
2173
            tcg_gen_ext32s_tl(cpu_HI[0], t1);
2174
        }
2175
        opn = "madd";
2176
        break;
2177
    case OPC_MADDU:
2178
       {
2179
            TCGv_i64 t2 = tcg_temp_new_i64();
2180
            TCGv_i64 t3 = tcg_temp_new_i64();
2181

    
2182
            tcg_gen_ext32u_tl(t0, t0);
2183
            tcg_gen_ext32u_tl(t1, t1);
2184
            tcg_gen_extu_tl_i64(t2, t0);
2185
            tcg_gen_extu_tl_i64(t3, t1);
2186
            tcg_gen_mul_i64(t2, t2, t3);
2187
            tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2188
            tcg_gen_add_i64(t2, t2, t3);
2189
            tcg_temp_free_i64(t3);
2190
            tcg_gen_trunc_i64_tl(t0, t2);
2191
            tcg_gen_shri_i64(t2, t2, 32);
2192
            tcg_gen_trunc_i64_tl(t1, t2);
2193
            tcg_temp_free_i64(t2);
2194
            tcg_gen_ext32s_tl(cpu_LO[0], t0);
2195
            tcg_gen_ext32s_tl(cpu_HI[0], t1);
2196
        }
2197
        opn = "maddu";
2198
        break;
2199
    case OPC_MSUB:
2200
        {
2201
            TCGv_i64 t2 = tcg_temp_new_i64();
2202
            TCGv_i64 t3 = tcg_temp_new_i64();
2203

    
2204
            tcg_gen_ext_tl_i64(t2, t0);
2205
            tcg_gen_ext_tl_i64(t3, t1);
2206
            tcg_gen_mul_i64(t2, t2, t3);
2207
            tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2208
            tcg_gen_sub_i64(t2, t3, t2);
2209
            tcg_temp_free_i64(t3);
2210
            tcg_gen_trunc_i64_tl(t0, t2);
2211
            tcg_gen_shri_i64(t2, t2, 32);
2212
            tcg_gen_trunc_i64_tl(t1, t2);
2213
            tcg_temp_free_i64(t2);
2214
            tcg_gen_ext32s_tl(cpu_LO[0], t0);
2215
            tcg_gen_ext32s_tl(cpu_HI[0], t1);
2216
        }
2217
        opn = "msub";
2218
        break;
2219
    case OPC_MSUBU:
2220
        {
2221
            TCGv_i64 t2 = tcg_temp_new_i64();
2222
            TCGv_i64 t3 = tcg_temp_new_i64();
2223

    
2224
            tcg_gen_ext32u_tl(t0, t0);
2225
            tcg_gen_ext32u_tl(t1, t1);
2226
            tcg_gen_extu_tl_i64(t2, t0);
2227
            tcg_gen_extu_tl_i64(t3, t1);
2228
            tcg_gen_mul_i64(t2, t2, t3);
2229
            tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2230
            tcg_gen_sub_i64(t2, t3, t2);
2231
            tcg_temp_free_i64(t3);
2232
            tcg_gen_trunc_i64_tl(t0, t2);
2233
            tcg_gen_shri_i64(t2, t2, 32);
2234
            tcg_gen_trunc_i64_tl(t1, t2);
2235
            tcg_temp_free_i64(t2);
2236
            tcg_gen_ext32s_tl(cpu_LO[0], t0);
2237
            tcg_gen_ext32s_tl(cpu_HI[0], t1);
2238
        }
2239
        opn = "msubu";
2240
        break;
2241
    default:
2242
        MIPS_INVAL(opn);
2243
        generate_exception(ctx, EXCP_RI);
2244
        goto out;
2245
    }
2246
    (void)opn; /* avoid a compiler warning */
2247
    MIPS_DEBUG("%s %s %s", opn, regnames[rs], regnames[rt]);
2248
 out:
2249
    tcg_temp_free(t0);
2250
    tcg_temp_free(t1);
2251
}
2252

    
2253
static void gen_mul_vr54xx (DisasContext *ctx, uint32_t opc,
2254
                            int rd, int rs, int rt)
2255
{
2256
    const char *opn = "mul vr54xx";
2257
    TCGv t0 = tcg_temp_new();
2258
    TCGv t1 = tcg_temp_new();
2259

    
2260
    gen_load_gpr(t0, rs);
2261
    gen_load_gpr(t1, rt);
2262

    
2263
    switch (opc) {
2264
    case OPC_VR54XX_MULS:
2265
        gen_helper_muls(t0, t0, t1);
2266
        opn = "muls";
2267
        break;
2268
    case OPC_VR54XX_MULSU:
2269
        gen_helper_mulsu(t0, t0, t1);
2270
        opn = "mulsu";
2271
        break;
2272
    case OPC_VR54XX_MACC:
2273
        gen_helper_macc(t0, t0, t1);
2274
        opn = "macc";
2275
        break;
2276
    case OPC_VR54XX_MACCU:
2277
        gen_helper_maccu(t0, t0, t1);
2278
        opn = "maccu";
2279
        break;
2280
    case OPC_VR54XX_MSAC:
2281
        gen_helper_msac(t0, t0, t1);
2282
        opn = "msac";
2283
        break;
2284
    case OPC_VR54XX_MSACU:
2285
        gen_helper_msacu(t0, t0, t1);
2286
        opn = "msacu";
2287
        break;
2288
    case OPC_VR54XX_MULHI:
2289
        gen_helper_mulhi(t0, t0, t1);
2290
        opn = "mulhi";
2291
        break;
2292
    case OPC_VR54XX_MULHIU:
2293
        gen_helper_mulhiu(t0, t0, t1);
2294
        opn = "mulhiu";
2295
        break;
2296
    case OPC_VR54XX_MULSHI:
2297
        gen_helper_mulshi(t0, t0, t1);
2298
        opn = "mulshi";
2299
        break;
2300
    case OPC_VR54XX_MULSHIU:
2301
        gen_helper_mulshiu(t0, t0, t1);
2302
        opn = "mulshiu";
2303
        break;
2304
    case OPC_VR54XX_MACCHI:
2305
        gen_helper_macchi(t0, t0, t1);
2306
        opn = "macchi";
2307
        break;
2308
    case OPC_VR54XX_MACCHIU:
2309
        gen_helper_macchiu(t0, t0, t1);
2310
        opn = "macchiu";
2311
        break;
2312
    case OPC_VR54XX_MSACHI:
2313
        gen_helper_msachi(t0, t0, t1);
2314
        opn = "msachi";
2315
        break;
2316
    case OPC_VR54XX_MSACHIU:
2317
        gen_helper_msachiu(t0, t0, t1);
2318
        opn = "msachiu";
2319
        break;
2320
    default:
2321
        MIPS_INVAL("mul vr54xx");
2322
        generate_exception(ctx, EXCP_RI);
2323
        goto out;
2324
    }
2325
    gen_store_gpr(t0, rd);
2326
    (void)opn; /* avoid a compiler warning */
2327
    MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
2328

    
2329
 out:
2330
    tcg_temp_free(t0);
2331
    tcg_temp_free(t1);
2332
}
2333

    
2334
static void gen_cl (DisasContext *ctx, uint32_t opc,
2335
                    int rd, int rs)
2336
{
2337
    const char *opn = "CLx";
2338
    TCGv t0;
2339

    
2340
    if (rd == 0) {
2341
        /* Treat as NOP. */
2342
        MIPS_DEBUG("NOP");
2343
        return;
2344
    }
2345
    t0 = tcg_temp_new();
2346
    gen_load_gpr(t0, rs);
2347
    switch (opc) {
2348
    case OPC_CLO:
2349
        gen_helper_clo(cpu_gpr[rd], t0);
2350
        opn = "clo";
2351
        break;
2352
    case OPC_CLZ:
2353
        gen_helper_clz(cpu_gpr[rd], t0);
2354
        opn = "clz";
2355
        break;
2356
#if defined(TARGET_MIPS64)
2357
    case OPC_DCLO:
2358
        gen_helper_dclo(cpu_gpr[rd], t0);
2359
        opn = "dclo";
2360
        break;
2361
    case OPC_DCLZ:
2362
        gen_helper_dclz(cpu_gpr[rd], t0);
2363
        opn = "dclz";
2364
        break;
2365
#endif
2366
    }
2367
    (void)opn; /* avoid a compiler warning */
2368
    MIPS_DEBUG("%s %s, %s", opn, regnames[rd], regnames[rs]);
2369
    tcg_temp_free(t0);
2370
}
2371

    
2372
/* Godson integer instructions */
2373
static void gen_loongson_integer (DisasContext *ctx, uint32_t opc,
2374
                                int rd, int rs, int rt)
2375
{
2376
    const char *opn = "loongson";
2377
    TCGv t0, t1;
2378

    
2379
    if (rd == 0) {
2380
        /* Treat as NOP. */
2381
        MIPS_DEBUG("NOP");
2382
        return;
2383
    }
2384

    
2385
    switch (opc) {
2386
    case OPC_MULT_G_2E:
2387
    case OPC_MULT_G_2F:
2388
    case OPC_MULTU_G_2E:
2389
    case OPC_MULTU_G_2F:
2390
#if defined(TARGET_MIPS64)
2391
    case OPC_DMULT_G_2E:
2392
    case OPC_DMULT_G_2F:
2393
    case OPC_DMULTU_G_2E:
2394
    case OPC_DMULTU_G_2F:
2395
#endif
2396
        t0 = tcg_temp_new();
2397
        t1 = tcg_temp_new();
2398
        break;
2399
    default:
2400
        t0 = tcg_temp_local_new();
2401
        t1 = tcg_temp_local_new();
2402
        break;
2403
    }
2404

    
2405
    gen_load_gpr(t0, rs);
2406
    gen_load_gpr(t1, rt);
2407

    
2408
    switch (opc) {
2409
    case OPC_MULT_G_2E:
2410
    case OPC_MULT_G_2F:
2411
        tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
2412
        tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2413
        opn = "mult.g";
2414
        break;
2415
    case OPC_MULTU_G_2E:
2416
    case OPC_MULTU_G_2F:
2417
        tcg_gen_ext32u_tl(t0, t0);
2418
        tcg_gen_ext32u_tl(t1, t1);
2419
        tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
2420
        tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2421
        opn = "multu.g";
2422
        break;
2423
    case OPC_DIV_G_2E:
2424
    case OPC_DIV_G_2F:
2425
        {
2426
            int l1 = gen_new_label();
2427
            int l2 = gen_new_label();
2428
            int l3 = gen_new_label();
2429
            tcg_gen_ext32s_tl(t0, t0);
2430
            tcg_gen_ext32s_tl(t1, t1);
2431
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2432
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
2433
            tcg_gen_br(l3);
2434
            gen_set_label(l1);
2435
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, INT_MIN, l2);
2436
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1, l2);
2437
            tcg_gen_mov_tl(cpu_gpr[rd], t0);
2438
            tcg_gen_br(l3);
2439
            gen_set_label(l2);
2440
            tcg_gen_div_tl(cpu_gpr[rd], t0, t1);
2441
            tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2442
            gen_set_label(l3);
2443
        }
2444
        opn = "div.g";
2445
        break;
2446
    case OPC_DIVU_G_2E:
2447
    case OPC_DIVU_G_2F:
2448
        {
2449
            int l1 = gen_new_label();
2450
            int l2 = gen_new_label();
2451
            tcg_gen_ext32u_tl(t0, t0);
2452
            tcg_gen_ext32u_tl(t1, t1);
2453
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2454
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
2455
            tcg_gen_br(l2);
2456
            gen_set_label(l1);
2457
            tcg_gen_divu_tl(cpu_gpr[rd], t0, t1);
2458
            tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2459
            gen_set_label(l2);
2460
        }
2461
        opn = "divu.g";
2462
        break;
2463
    case OPC_MOD_G_2E:
2464
    case OPC_MOD_G_2F:
2465
        {
2466
            int l1 = gen_new_label();
2467
            int l2 = gen_new_label();
2468
            int l3 = gen_new_label();
2469
            tcg_gen_ext32u_tl(t0, t0);
2470
            tcg_gen_ext32u_tl(t1, t1);
2471
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2472
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, INT_MIN, l2);
2473
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1, l2);
2474
            gen_set_label(l1);
2475
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
2476
            tcg_gen_br(l3);
2477
            gen_set_label(l2);
2478
            tcg_gen_rem_tl(cpu_gpr[rd], t0, t1);
2479
            tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2480
            gen_set_label(l3);
2481
        }
2482
        opn = "mod.g";
2483
        break;
2484
    case OPC_MODU_G_2E:
2485
    case OPC_MODU_G_2F:
2486
        {
2487
            int l1 = gen_new_label();
2488
            int l2 = gen_new_label();
2489
            tcg_gen_ext32u_tl(t0, t0);
2490
            tcg_gen_ext32u_tl(t1, t1);
2491
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2492
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
2493
            tcg_gen_br(l2);
2494
            gen_set_label(l1);
2495
            tcg_gen_remu_tl(cpu_gpr[rd], t0, t1);
2496
            tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2497
            gen_set_label(l2);
2498
        }
2499
        opn = "modu.g";
2500
        break;
2501
#if defined(TARGET_MIPS64)
2502
    case OPC_DMULT_G_2E:
2503
    case OPC_DMULT_G_2F:
2504
        tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
2505
        opn = "dmult.g";
2506
        break;
2507
    case OPC_DMULTU_G_2E:
2508
    case OPC_DMULTU_G_2F:
2509
        tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
2510
        opn = "dmultu.g";
2511
        break;
2512
    case OPC_DDIV_G_2E:
2513
    case OPC_DDIV_G_2F:
2514
        {
2515
            int l1 = gen_new_label();
2516
            int l2 = gen_new_label();
2517
            int l3 = gen_new_label();
2518
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2519
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
2520
            tcg_gen_br(l3);
2521
            gen_set_label(l1);
2522
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, -1LL << 63, l2);
2523
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1LL, l2);
2524
            tcg_gen_mov_tl(cpu_gpr[rd], t0);
2525
            tcg_gen_br(l3);
2526
            gen_set_label(l2);
2527
            tcg_gen_div_tl(cpu_gpr[rd], t0, t1);
2528
            gen_set_label(l3);
2529
        }
2530
        opn = "ddiv.g";
2531
        break;
2532
    case OPC_DDIVU_G_2E:
2533
    case OPC_DDIVU_G_2F:
2534
        {
2535
            int l1 = gen_new_label();
2536
            int l2 = gen_new_label();
2537
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2538
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
2539
            tcg_gen_br(l2);
2540
            gen_set_label(l1);
2541
            tcg_gen_divu_tl(cpu_gpr[rd], t0, t1);
2542
            gen_set_label(l2);
2543
        }
2544
        opn = "ddivu.g";
2545
        break;
2546
    case OPC_DMOD_G_2E:
2547
    case OPC_DMOD_G_2F:
2548
        {
2549
            int l1 = gen_new_label();
2550
            int l2 = gen_new_label();
2551
            int l3 = gen_new_label();
2552
            tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2553
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, -1LL << 63, l2);
2554
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1LL, l2);
2555
            gen_set_label(l1);
2556
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
2557
            tcg_gen_br(l3);
2558
            gen_set_label(l2);
2559
            tcg_gen_rem_tl(cpu_gpr[rd], t0, t1);
2560
            gen_set_label(l3);
2561
        }
2562
        opn = "dmod.g";
2563
        break;
2564
    case OPC_DMODU_G_2E:
2565
    case OPC_DMODU_G_2F:
2566
        {
2567
            int l1 = gen_new_label();
2568
            int l2 = gen_new_label();
2569
            tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2570
            tcg_gen_movi_tl(cpu_gpr[rd], 0);
2571
            tcg_gen_br(l2);
2572
            gen_set_label(l1);
2573
            tcg_gen_remu_tl(cpu_gpr[rd], t0, t1);
2574
            gen_set_label(l2);
2575
        }
2576
        opn = "dmodu.g";
2577
        break;
2578
#endif
2579
    }
2580

    
2581
    (void)opn; /* avoid a compiler warning */
2582
    MIPS_DEBUG("%s %s, %s", opn, regnames[rd], regnames[rs]);
2583
    tcg_temp_free(t0);
2584
    tcg_temp_free(t1);
2585
}
2586

    
2587
/* Traps */
2588
static void gen_trap (DisasContext *ctx, uint32_t opc,
2589
                      int rs, int rt, int16_t imm)
2590
{
2591
    int cond;
2592
    TCGv t0 = tcg_temp_new();
2593
    TCGv t1 = tcg_temp_new();
2594

    
2595
    cond = 0;
2596
    /* Load needed operands */
2597
    switch (opc) {
2598
    case OPC_TEQ:
2599
    case OPC_TGE:
2600
    case OPC_TGEU:
2601
    case OPC_TLT:
2602
    case OPC_TLTU:
2603
    case OPC_TNE:
2604
        /* Compare two registers */
2605
        if (rs != rt) {
2606
            gen_load_gpr(t0, rs);
2607
            gen_load_gpr(t1, rt);
2608
            cond = 1;
2609
        }
2610
        break;
2611
    case OPC_TEQI:
2612
    case OPC_TGEI:
2613
    case OPC_TGEIU:
2614
    case OPC_TLTI:
2615
    case OPC_TLTIU:
2616
    case OPC_TNEI:
2617
        /* Compare register to immediate */
2618
        if (rs != 0 || imm != 0) {
2619
            gen_load_gpr(t0, rs);
2620
            tcg_gen_movi_tl(t1, (int32_t)imm);
2621
            cond = 1;
2622
        }
2623
        break;
2624
    }
2625
    if (cond == 0) {
2626
        switch (opc) {
2627
        case OPC_TEQ:   /* rs == rs */
2628
        case OPC_TEQI:  /* r0 == 0  */
2629
        case OPC_TGE:   /* rs >= rs */
2630
        case OPC_TGEI:  /* r0 >= 0  */
2631
        case OPC_TGEU:  /* rs >= rs unsigned */
2632
        case OPC_TGEIU: /* r0 >= 0  unsigned */
2633
            /* Always trap */
2634
            generate_exception(ctx, EXCP_TRAP);
2635
            break;
2636
        case OPC_TLT:   /* rs < rs           */
2637
        case OPC_TLTI:  /* r0 < 0            */
2638
        case OPC_TLTU:  /* rs < rs unsigned  */
2639
        case OPC_TLTIU: /* r0 < 0  unsigned  */
2640
        case OPC_TNE:   /* rs != rs          */
2641
        case OPC_TNEI:  /* r0 != 0           */
2642
            /* Never trap: treat as NOP. */
2643
            break;
2644
        }
2645
    } else {
2646
        int l1 = gen_new_label();
2647

    
2648
        switch (opc) {
2649
        case OPC_TEQ:
2650
        case OPC_TEQI:
2651
            tcg_gen_brcond_tl(TCG_COND_NE, t0, t1, l1);
2652
            break;
2653
        case OPC_TGE:
2654
        case OPC_TGEI:
2655
            tcg_gen_brcond_tl(TCG_COND_LT, t0, t1, l1);
2656
            break;
2657
        case OPC_TGEU:
2658
        case OPC_TGEIU:
2659
            tcg_gen_brcond_tl(TCG_COND_LTU, t0, t1, l1);
2660
            break;
2661
        case OPC_TLT:
2662
        case OPC_TLTI:
2663
            tcg_gen_brcond_tl(TCG_COND_GE, t0, t1, l1);
2664
            break;
2665
        case OPC_TLTU:
2666
        case OPC_TLTIU:
2667
            tcg_gen_brcond_tl(TCG_COND_GEU, t0, t1, l1);
2668
            break;
2669
        case OPC_TNE:
2670
        case OPC_TNEI:
2671
            tcg_gen_brcond_tl(TCG_COND_EQ, t0, t1, l1);
2672
            break;
2673
        }
2674
        generate_exception(ctx, EXCP_TRAP);
2675
        gen_set_label(l1);
2676
    }
2677
    tcg_temp_free(t0);
2678
    tcg_temp_free(t1);
2679
}
2680

    
2681
static inline void gen_goto_tb(DisasContext *ctx, int n, target_ulong dest)
2682
{
2683
    TranslationBlock *tb;
2684
    tb = ctx->tb;
2685
    if ((tb->pc & TARGET_PAGE_MASK) == (dest & TARGET_PAGE_MASK) &&
2686
        likely(!ctx->singlestep_enabled)) {
2687
        tcg_gen_goto_tb(n);
2688
        gen_save_pc(dest);
2689
        tcg_gen_exit_tb((long)tb + n);
2690
    } else {
2691
        gen_save_pc(dest);
2692
        if (ctx->singlestep_enabled) {
2693
            save_cpu_state(ctx, 0);
2694
            gen_helper_0i(raise_exception, EXCP_DEBUG);
2695
        }
2696
        tcg_gen_exit_tb(0);
2697
    }
2698
}
2699

    
2700
/* Branches (before delay slot) */
2701
static void gen_compute_branch (DisasContext *ctx, uint32_t opc,
2702
                                int insn_bytes,
2703
                                int rs, int rt, int32_t offset)
2704
{
2705
    target_ulong btgt = -1;
2706
    int blink = 0;
2707
    int bcond_compute = 0;
2708
    TCGv t0 = tcg_temp_new();
2709
    TCGv t1 = tcg_temp_new();
2710

    
2711
    if (ctx->hflags & MIPS_HFLAG_BMASK) {
2712
#ifdef MIPS_DEBUG_DISAS
2713
        LOG_DISAS("Branch in delay slot at PC 0x" TARGET_FMT_lx "\n", ctx->pc);
2714
#endif
2715
        generate_exception(ctx, EXCP_RI);
2716
        goto out;
2717
    }
2718

    
2719
    /* Load needed operands */
2720
    switch (opc) {
2721
    case OPC_BEQ:
2722
    case OPC_BEQL:
2723
    case OPC_BNE:
2724
    case OPC_BNEL:
2725
        /* Compare two registers */
2726
        if (rs != rt) {
2727
            gen_load_gpr(t0, rs);
2728
            gen_load_gpr(t1, rt);
2729
            bcond_compute = 1;
2730
        }
2731
        btgt = ctx->pc + insn_bytes + offset;
2732
        break;
2733
    case OPC_BGEZ:
2734
    case OPC_BGEZAL:
2735
    case OPC_BGEZALS:
2736
    case OPC_BGEZALL:
2737
    case OPC_BGEZL:
2738
    case OPC_BGTZ:
2739
    case OPC_BGTZL:
2740
    case OPC_BLEZ:
2741
    case OPC_BLEZL:
2742
    case OPC_BLTZ:
2743
    case OPC_BLTZAL:
2744
    case OPC_BLTZALS:
2745
    case OPC_BLTZALL:
2746
    case OPC_BLTZL:
2747
        /* Compare to zero */
2748
        if (rs != 0) {
2749
            gen_load_gpr(t0, rs);
2750
            bcond_compute = 1;
2751
        }
2752
        btgt = ctx->pc + insn_bytes + offset;
2753
        break;
2754
    case OPC_J:
2755
    case OPC_JAL:
2756
    case OPC_JALX:
2757
    case OPC_JALS:
2758
    case OPC_JALXS:
2759
        /* Jump to immediate */
2760
        btgt = ((ctx->pc + insn_bytes) & (int32_t)0xF0000000) | (uint32_t)offset;
2761
        break;
2762
    case OPC_JR:
2763
    case OPC_JALR:
2764
    case OPC_JALRC:
2765
    case OPC_JALRS:
2766
        /* Jump to register */
2767
        if (offset != 0 && offset != 16) {
2768
            /* Hint = 0 is JR/JALR, hint 16 is JR.HB/JALR.HB, the
2769
               others are reserved. */
2770
            MIPS_INVAL("jump hint");
2771
            generate_exception(ctx, EXCP_RI);
2772
            goto out;
2773
        }
2774
        gen_load_gpr(btarget, rs);
2775
        break;
2776
    default:
2777
        MIPS_INVAL("branch/jump");
2778
        generate_exception(ctx, EXCP_RI);
2779
        goto out;
2780
    }
2781
    if (bcond_compute == 0) {
2782
        /* No condition to be computed */
2783
        switch (opc) {
2784
        case OPC_BEQ:     /* rx == rx        */
2785
        case OPC_BEQL:    /* rx == rx likely */
2786
        case OPC_BGEZ:    /* 0 >= 0          */
2787
        case OPC_BGEZL:   /* 0 >= 0 likely   */
2788
        case OPC_BLEZ:    /* 0 <= 0          */
2789
        case OPC_BLEZL:   /* 0 <= 0 likely   */
2790
            /* Always take */
2791
            ctx->hflags |= MIPS_HFLAG_B;
2792
            MIPS_DEBUG("balways");
2793
            break;
2794
        case OPC_BGEZALS:
2795
        case OPC_BGEZAL:  /* 0 >= 0          */
2796
        case OPC_BGEZALL: /* 0 >= 0 likely   */
2797
            ctx->hflags |= (opc == OPC_BGEZALS
2798
                            ? MIPS_HFLAG_BDS16
2799
                            : MIPS_HFLAG_BDS32);
2800
            /* Always take and link */
2801
            blink = 31;
2802
            ctx->hflags |= MIPS_HFLAG_B;
2803
            MIPS_DEBUG("balways and link");
2804
            break;
2805
        case OPC_BNE:     /* rx != rx        */
2806
        case OPC_BGTZ:    /* 0 > 0           */
2807
        case OPC_BLTZ:    /* 0 < 0           */
2808
            /* Treat as NOP. */
2809
            MIPS_DEBUG("bnever (NOP)");
2810
            goto out;
2811
        case OPC_BLTZALS:
2812
        case OPC_BLTZAL:  /* 0 < 0           */
2813
            ctx->hflags |= (opc == OPC_BLTZALS
2814
                            ? MIPS_HFLAG_BDS16
2815
                            : MIPS_HFLAG_BDS32);
2816
            /* Handle as an unconditional branch to get correct delay
2817
               slot checking.  */
2818
            blink = 31;
2819
            btgt = ctx->pc + (opc == OPC_BLTZALS ? 6 : 8);
2820
            ctx->hflags |= MIPS_HFLAG_B;
2821
            MIPS_DEBUG("bnever and link");
2822
            break;
2823
        case OPC_BLTZALL: /* 0 < 0 likely */
2824
            tcg_gen_movi_tl(cpu_gpr[31], ctx->pc + 8);
2825
            /* Skip the instruction in the delay slot */
2826
            MIPS_DEBUG("bnever, link and skip");
2827
            ctx->pc += 4;
2828
            goto out;
2829
        case OPC_BNEL:    /* rx != rx likely */
2830
        case OPC_BGTZL:   /* 0 > 0 likely */
2831
        case OPC_BLTZL:   /* 0 < 0 likely */
2832
            /* Skip the instruction in the delay slot */
2833
            MIPS_DEBUG("bnever and skip");
2834
            ctx->pc += 4;
2835
            goto out;
2836
        case OPC_J:
2837
            ctx->hflags |= MIPS_HFLAG_B;
2838
            MIPS_DEBUG("j " TARGET_FMT_lx, btgt);
2839
            break;
2840
        case OPC_JALXS:
2841
        case OPC_JALX:
2842
            ctx->hflags |= MIPS_HFLAG_BX;
2843
            /* Fallthrough */
2844
        case OPC_JALS:
2845
        case OPC_JAL:
2846
            blink = 31;
2847
            ctx->hflags |= MIPS_HFLAG_B;
2848
            ctx->hflags |= ((opc == OPC_JALS || opc == OPC_JALXS)
2849
                            ? MIPS_HFLAG_BDS16
2850
                            : MIPS_HFLAG_BDS32);
2851
            MIPS_DEBUG("jal " TARGET_FMT_lx, btgt);
2852
            break;
2853
        case OPC_JR:
2854
            ctx->hflags |= MIPS_HFLAG_BR;
2855
            if (insn_bytes == 4)
2856
                ctx->hflags |= MIPS_HFLAG_BDS32;
2857
            MIPS_DEBUG("jr %s", regnames[rs]);
2858
            break;
2859
        case OPC_JALRS:
2860
        case OPC_JALR:
2861
        case OPC_JALRC:
2862
            blink = rt;
2863
            ctx->hflags |= MIPS_HFLAG_BR;
2864
            ctx->hflags |= (opc == OPC_JALRS
2865
                            ? MIPS_HFLAG_BDS16
2866
                            : MIPS_HFLAG_BDS32);
2867
            MIPS_DEBUG("jalr %s, %s", regnames[rt], regnames[rs]);
2868
            break;
2869
        default:
2870
            MIPS_INVAL("branch/jump");
2871
            generate_exception(ctx, EXCP_RI);
2872
            goto out;
2873
        }
2874
    } else {
2875
        switch (opc) {
2876
        case OPC_BEQ:
2877
            tcg_gen_setcond_tl(TCG_COND_EQ, bcond, t0, t1);
2878
            MIPS_DEBUG("beq %s, %s, " TARGET_FMT_lx,
2879
                       regnames[rs], regnames[rt], btgt);
2880
            goto not_likely;
2881
        case OPC_BEQL:
2882
            tcg_gen_setcond_tl(TCG_COND_EQ, bcond, t0, t1);
2883
            MIPS_DEBUG("beql %s, %s, " TARGET_FMT_lx,
2884
                       regnames[rs], regnames[rt], btgt);
2885
            goto likely;
2886
        case OPC_BNE:
2887
            tcg_gen_setcond_tl(TCG_COND_NE, bcond, t0, t1);
2888
            MIPS_DEBUG("bne %s, %s, " TARGET_FMT_lx,
2889
                       regnames[rs], regnames[rt], btgt);
2890
            goto not_likely;
2891
        case OPC_BNEL:
2892
            tcg_gen_setcond_tl(TCG_COND_NE, bcond, t0, t1);
2893
            MIPS_DEBUG("bnel %s, %s, " TARGET_FMT_lx,
2894
                       regnames[rs], regnames[rt], btgt);
2895
            goto likely;
2896
        case OPC_BGEZ:
2897
            tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
2898
            MIPS_DEBUG("bgez %s, " TARGET_FMT_lx, regnames[rs], btgt);
2899
            goto not_likely;
2900
        case OPC_BGEZL:
2901
            tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
2902
            MIPS_DEBUG("bgezl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2903
            goto likely;
2904
        case OPC_BGEZALS:
2905
        case OPC_BGEZAL:
2906
            ctx->hflags |= (opc == OPC_BGEZALS
2907
                            ? MIPS_HFLAG_BDS16
2908
                            : MIPS_HFLAG_BDS32);
2909
            tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
2910
            MIPS_DEBUG("bgezal %s, " TARGET_FMT_lx, regnames[rs], btgt);
2911
            blink = 31;
2912
            goto not_likely;
2913
        case OPC_BGEZALL:
2914
            tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
2915
            blink = 31;
2916
            MIPS_DEBUG("bgezall %s, " TARGET_FMT_lx, regnames[rs], btgt);
2917
            goto likely;
2918
        case OPC_BGTZ:
2919
            tcg_gen_setcondi_tl(TCG_COND_GT, bcond, t0, 0);
2920
            MIPS_DEBUG("bgtz %s, " TARGET_FMT_lx, regnames[rs], btgt);
2921
            goto not_likely;
2922
        case OPC_BGTZL:
2923
            tcg_gen_setcondi_tl(TCG_COND_GT, bcond, t0, 0);
2924
            MIPS_DEBUG("bgtzl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2925
            goto likely;
2926
        case OPC_BLEZ:
2927
            tcg_gen_setcondi_tl(TCG_COND_LE, bcond, t0, 0);
2928
            MIPS_DEBUG("blez %s, " TARGET_FMT_lx, regnames[rs], btgt);
2929
            goto not_likely;
2930
        case OPC_BLEZL:
2931
            tcg_gen_setcondi_tl(TCG_COND_LE, bcond, t0, 0);
2932
            MIPS_DEBUG("blezl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2933
            goto likely;
2934
        case OPC_BLTZ:
2935
            tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
2936
            MIPS_DEBUG("bltz %s, " TARGET_FMT_lx, regnames[rs], btgt);
2937
            goto not_likely;
2938
        case OPC_BLTZL:
2939
            tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
2940
            MIPS_DEBUG("bltzl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2941
            goto likely;
2942
        case OPC_BLTZALS:
2943
        case OPC_BLTZAL:
2944
            ctx->hflags |= (opc == OPC_BLTZALS
2945
                            ? MIPS_HFLAG_BDS16
2946
                            : MIPS_HFLAG_BDS32);
2947
            tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
2948
            blink = 31;
2949
            MIPS_DEBUG("bltzal %s, " TARGET_FMT_lx, regnames[rs], btgt);
2950
        not_likely:
2951
            ctx->hflags |= MIPS_HFLAG_BC;
2952
            break;
2953
        case OPC_BLTZALL:
2954
            tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
2955
            blink = 31;
2956
            MIPS_DEBUG("bltzall %s, " TARGET_FMT_lx, regnames[rs], btgt);
2957
        likely:
2958
            ctx->hflags |= MIPS_HFLAG_BL;
2959
            break;
2960
        default:
2961
            MIPS_INVAL("conditional branch/jump");
2962
            generate_exception(ctx, EXCP_RI);
2963
            goto out;
2964
        }
2965
    }
2966
    MIPS_DEBUG("enter ds: link %d cond %02x target " TARGET_FMT_lx,
2967
               blink, ctx->hflags, btgt);
2968

    
2969
    ctx->btarget = btgt;
2970
    if (blink > 0) {
2971
        int post_delay = insn_bytes;
2972
        int lowbit = !!(ctx->hflags & MIPS_HFLAG_M16);
2973

    
2974
        if (opc != OPC_JALRC)
2975
            post_delay += ((ctx->hflags & MIPS_HFLAG_BDS16) ? 2 : 4);
2976

    
2977
        tcg_gen_movi_tl(cpu_gpr[blink], ctx->pc + post_delay + lowbit);
2978
    }
2979

    
2980
 out:
2981
    if (insn_bytes == 2)
2982
        ctx->hflags |= MIPS_HFLAG_B16;
2983
    tcg_temp_free(t0);
2984
    tcg_temp_free(t1);
2985
}
2986

    
2987
/* special3 bitfield operations */
2988
static void gen_bitops (DisasContext *ctx, uint32_t opc, int rt,
2989
                        int rs, int lsb, int msb)
2990
{
2991
    TCGv t0 = tcg_temp_new();
2992
    TCGv t1 = tcg_temp_new();
2993
    target_ulong mask;
2994

    
2995
    gen_load_gpr(t1, rs);
2996
    switch (opc) {
2997
    case OPC_EXT:
2998
        if (lsb + msb > 31)
2999
            goto fail;
3000
        tcg_gen_shri_tl(t0, t1, lsb);
3001
        if (msb != 31) {
3002
            tcg_gen_andi_tl(t0, t0, (1 << (msb + 1)) - 1);
3003
        } else {
3004
            tcg_gen_ext32s_tl(t0, t0);
3005
        }
3006
        break;
3007
#if defined(TARGET_MIPS64)
3008
    case OPC_DEXTM:
3009
        tcg_gen_shri_tl(t0, t1, lsb);
3010
        if (msb != 31) {
3011
            tcg_gen_andi_tl(t0, t0, (1ULL << (msb + 1 + 32)) - 1);
3012
        }
3013
        break;
3014
    case OPC_DEXTU:
3015
        tcg_gen_shri_tl(t0, t1, lsb + 32);
3016
        tcg_gen_andi_tl(t0, t0, (1ULL << (msb + 1)) - 1);
3017
        break;
3018
    case OPC_DEXT:
3019
        tcg_gen_shri_tl(t0, t1, lsb);
3020
        tcg_gen_andi_tl(t0, t0, (1ULL << (msb + 1)) - 1);
3021
        break;
3022
#endif
3023
    case OPC_INS:
3024
        if (lsb > msb)
3025
            goto fail;
3026
        mask = ((msb - lsb + 1 < 32) ? ((1 << (msb - lsb + 1)) - 1) : ~0) << lsb;
3027
        gen_load_gpr(t0, rt);
3028
        tcg_gen_andi_tl(t0, t0, ~mask);
3029
        tcg_gen_shli_tl(t1, t1, lsb);
3030
        tcg_gen_andi_tl(t1, t1, mask);
3031
        tcg_gen_or_tl(t0, t0, t1);
3032
        tcg_gen_ext32s_tl(t0, t0);
3033
        break;
3034
#if defined(TARGET_MIPS64)
3035
    case OPC_DINSM:
3036
        if (lsb > msb)
3037
            goto fail;
3038
        mask = ((msb - lsb + 1 + 32 < 64) ? ((1ULL << (msb - lsb + 1 + 32)) - 1) : ~0ULL) << lsb;
3039
        gen_load_gpr(t0, rt);
3040
        tcg_gen_andi_tl(t0, t0, ~mask);
3041
        tcg_gen_shli_tl(t1, t1, lsb);
3042
        tcg_gen_andi_tl(t1, t1, mask);
3043
        tcg_gen_or_tl(t0, t0, t1);
3044
        break;
3045
    case OPC_DINSU:
3046
        if (lsb > msb)
3047
            goto fail;
3048
        mask = ((1ULL << (msb - lsb + 1)) - 1) << (lsb + 32);
3049
        gen_load_gpr(t0, rt);
3050
        tcg_gen_andi_tl(t0, t0, ~mask);
3051
        tcg_gen_shli_tl(t1, t1, lsb + 32);
3052
        tcg_gen_andi_tl(t1, t1, mask);
3053
        tcg_gen_or_tl(t0, t0, t1);
3054
        break;
3055
    case OPC_DINS:
3056
        if (lsb > msb)
3057
            goto fail;
3058
        gen_load_gpr(t0, rt);
3059
        mask = ((1ULL << (msb - lsb + 1)) - 1) << lsb;
3060
        gen_load_gpr(t0, rt);
3061
        tcg_gen_andi_tl(t0, t0, ~mask);
3062
        tcg_gen_shli_tl(t1, t1, lsb);
3063
        tcg_gen_andi_tl(t1, t1, mask);
3064
        tcg_gen_or_tl(t0, t0, t1);
3065
        break;
3066
#endif
3067
    default:
3068
fail:
3069
        MIPS_INVAL("bitops");
3070
        generate_exception(ctx, EXCP_RI);
3071
        tcg_temp_free(t0);
3072
        tcg_temp_free(t1);
3073
        return;
3074
    }
3075
    gen_store_gpr(t0, rt);
3076
    tcg_temp_free(t0);
3077
    tcg_temp_free(t1);
3078
}
3079

    
3080
static void gen_bshfl (DisasContext *ctx, uint32_t op2, int rt, int rd)
3081
{
3082
    TCGv t0;
3083

    
3084
    if (rd == 0) {
3085
        /* If no destination, treat it as a NOP. */
3086
        MIPS_DEBUG("NOP");
3087
        return;
3088
    }
3089

    
3090
    t0 = tcg_temp_new();
3091
    gen_load_gpr(t0, rt);
3092
    switch (op2) {
3093
    case OPC_WSBH:
3094
        {
3095
            TCGv t1 = tcg_temp_new();
3096

    
3097
            tcg_gen_shri_tl(t1, t0, 8);
3098
            tcg_gen_andi_tl(t1, t1, 0x00FF00FF);
3099
            tcg_gen_shli_tl(t0, t0, 8);
3100
            tcg_gen_andi_tl(t0, t0, ~0x00FF00FF);
3101
            tcg_gen_or_tl(t0, t0, t1);
3102
            tcg_temp_free(t1);
3103
            tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
3104
        }
3105
        break;
3106
    case OPC_SEB:
3107
        tcg_gen_ext8s_tl(cpu_gpr[rd], t0);
3108
        break;
3109
    case OPC_SEH:
3110
        tcg_gen_ext16s_tl(cpu_gpr[rd], t0);
3111
        break;
3112
#if defined(TARGET_MIPS64)
3113
    case OPC_DSBH:
3114
        {
3115
            TCGv t1 = tcg_temp_new();
3116

    
3117
            tcg_gen_shri_tl(t1, t0, 8);
3118
            tcg_gen_andi_tl(t1, t1, 0x00FF00FF00FF00FFULL);
3119
            tcg_gen_shli_tl(t0, t0, 8);
3120
            tcg_gen_andi_tl(t0, t0, ~0x00FF00FF00FF00FFULL);
3121
            tcg_gen_or_tl(cpu_gpr[rd], t0, t1);
3122
            tcg_temp_free(t1);
3123
        }
3124
        break;
3125
    case OPC_DSHD:
3126
        {
3127
            TCGv t1 = tcg_temp_new();
3128

    
3129
            tcg_gen_shri_tl(t1, t0, 16);
3130
            tcg_gen_andi_tl(t1, t1, 0x0000FFFF0000FFFFULL);
3131
            tcg_gen_shli_tl(t0, t0, 16);
3132
            tcg_gen_andi_tl(t0, t0, ~0x0000FFFF0000FFFFULL);
3133
            tcg_gen_or_tl(t0, t0, t1);
3134
            tcg_gen_shri_tl(t1, t0, 32);
3135
            tcg_gen_shli_tl(t0, t0, 32);
3136
            tcg_gen_or_tl(cpu_gpr[rd], t0, t1);
3137
            tcg_temp_free(t1);
3138
        }
3139
        break;
3140
#endif
3141
    default:
3142
        MIPS_INVAL("bsfhl");
3143
        generate_exception(ctx, EXCP_RI);
3144
        tcg_temp_free(t0);
3145
        return;
3146
    }
3147
    tcg_temp_free(t0);
3148
}
3149

    
3150
#ifndef CONFIG_USER_ONLY
3151
/* CP0 (MMU and control) */
3152
static inline void gen_mfc0_load32 (TCGv arg, target_ulong off)
3153
{
3154
    TCGv_i32 t0 = tcg_temp_new_i32();
3155

    
3156
    tcg_gen_ld_i32(t0, cpu_env, off);
3157
    tcg_gen_ext_i32_tl(arg, t0);
3158
    tcg_temp_free_i32(t0);
3159
}
3160

    
3161
static inline void gen_mfc0_load64 (TCGv arg, target_ulong off)
3162
{
3163
    tcg_gen_ld_tl(arg, cpu_env, off);
3164
    tcg_gen_ext32s_tl(arg, arg);
3165
}
3166

    
3167
static inline void gen_mtc0_store32 (TCGv arg, target_ulong off)
3168
{
3169
    TCGv_i32 t0 = tcg_temp_new_i32();
3170

    
3171
    tcg_gen_trunc_tl_i32(t0, arg);
3172
    tcg_gen_st_i32(t0, cpu_env, off);
3173
    tcg_temp_free_i32(t0);
3174
}
3175

    
3176
static inline void gen_mtc0_store64 (TCGv arg, target_ulong off)
3177
{
3178
    tcg_gen_ext32s_tl(arg, arg);
3179
    tcg_gen_st_tl(arg, cpu_env, off);
3180
}
3181

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

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

    
3189
    switch (reg) {
3190
    case 0:
3191
        switch (sel) {
3192
        case 0:
3193
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Index));
3194
            rn = "Index";
3195
            break;
3196
        case 1:
3197
            check_insn(env, ctx, ASE_MT);
3198
            gen_helper_mfc0_mvpcontrol(arg);
3199
            rn = "MVPControl";
3200
            break;
3201
        case 2:
3202
            check_insn(env, ctx, ASE_MT);
3203
            gen_helper_mfc0_mvpconf0(arg);
3204
            rn = "MVPConf0";
3205
            break;
3206
        case 3:
3207
            check_insn(env, ctx, ASE_MT);
3208
            gen_helper_mfc0_mvpconf1(arg);
3209
            rn = "MVPConf1";
3210
            break;
3211
        default:
3212
            goto die;
3213
        }
3214
        break;
3215
    case 1:
3216
        switch (sel) {
3217
        case 0:
3218
            gen_helper_mfc0_random(arg);
3219
            rn = "Random";
3220
            break;
3221
        case 1:
3222
            check_insn(env, ctx, ASE_MT);
3223
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_VPEControl));
3224
            rn = "VPEControl";
3225
            break;
3226
        case 2:
3227
            check_insn(env, ctx, ASE_MT);
3228
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_VPEConf0));
3229
            rn = "VPEConf0";
3230
            break;
3231
        case 3:
3232
            check_insn(env, ctx, ASE_MT);
3233
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_VPEConf1));
3234
            rn = "VPEConf1";
3235
            break;
3236
        case 4:
3237
            check_insn(env, ctx, ASE_MT);
3238
            gen_mfc0_load64(arg, offsetof(CPUState, CP0_YQMask));
3239
            rn = "YQMask";
3240
            break;
3241
        case 5:
3242
            check_insn(env, ctx, ASE_MT);
3243
            gen_mfc0_load64(arg, offsetof(CPUState, CP0_VPESchedule));
3244
            rn = "VPESchedule";
3245
            break;
3246
        case 6:
3247
            check_insn(env, ctx, ASE_MT);
3248
            gen_mfc0_load64(arg, offsetof(CPUState, CP0_VPEScheFBack));
3249
            rn = "VPEScheFBack";
3250
            break;
3251
        case 7:
3252
            check_insn(env, ctx, ASE_MT);
3253
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_VPEOpt));
3254
            rn = "VPEOpt";
3255
            break;
3256
        default:
3257
            goto die;
3258
        }
3259
        break;
3260
    case 2:
3261
        switch (sel) {
3262
        case 0:
3263
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_EntryLo0));
3264
            tcg_gen_ext32s_tl(arg, arg);
3265
            rn = "EntryLo0";
3266
            break;
3267
        case 1:
3268
            check_insn(env, ctx, ASE_MT);
3269
            gen_helper_mfc0_tcstatus(arg);
3270
            rn = "TCStatus";
3271
            break;
3272
        case 2:
3273
            check_insn(env, ctx, ASE_MT);
3274
            gen_helper_mfc0_tcbind(arg);
3275
            rn = "TCBind";
3276
            break;
3277
        case 3:
3278
            check_insn(env, ctx, ASE_MT);
3279
            gen_helper_mfc0_tcrestart(arg);
3280
            rn = "TCRestart";
3281
            break;
3282
        case 4:
3283
            check_insn(env, ctx, ASE_MT);
3284
            gen_helper_mfc0_tchalt(arg);
3285
            rn = "TCHalt";
3286
            break;
3287
        case 5:
3288
            check_insn(env, ctx, ASE_MT);
3289
            gen_helper_mfc0_tccontext(arg);
3290
            rn = "TCContext";
3291
            break;
3292
        case 6:
3293
            check_insn(env, ctx, ASE_MT);
3294
            gen_helper_mfc0_tcschedule(arg);
3295
            rn = "TCSchedule";
3296
            break;
3297
        case 7:
3298
            check_insn(env, ctx, ASE_MT);
3299
            gen_helper_mfc0_tcschefback(arg);
3300
            rn = "TCScheFBack";
3301
            break;
3302
        default:
3303
            goto die;
3304
        }
3305
        break;
3306
    case 3:
3307
        switch (sel) {
3308
        case 0:
3309
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_EntryLo1));
3310
            tcg_gen_ext32s_tl(arg, arg);
3311
            rn = "EntryLo1";
3312
            break;
3313
        default:
3314
            goto die;
3315
        }
3316
        break;
3317
    case 4:
3318
        switch (sel) {
3319
        case 0:
3320
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_Context));
3321
            tcg_gen_ext32s_tl(arg, arg);
3322
            rn = "Context";
3323
            break;
3324
        case 1:
3325
//            gen_helper_mfc0_contextconfig(arg); /* SmartMIPS ASE */
3326
            rn = "ContextConfig";
3327
//            break;
3328
        default:
3329
            goto die;
3330
        }
3331
        break;
3332
    case 5:
3333
        switch (sel) {
3334
        case 0:
3335
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_PageMask));
3336
            rn = "PageMask";
3337
            break;
3338
        case 1:
3339
            check_insn(env, ctx, ISA_MIPS32R2);
3340
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_PageGrain));
3341
            rn = "PageGrain";
3342
            break;
3343
        default:
3344
            goto die;
3345
        }
3346
        break;
3347
    case 6:
3348
        switch (sel) {
3349
        case 0:
3350
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Wired));
3351
            rn = "Wired";
3352
            break;
3353
        case 1:
3354
            check_insn(env, ctx, ISA_MIPS32R2);
3355
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSConf0));
3356
            rn = "SRSConf0";
3357
            break;
3358
        case 2:
3359
            check_insn(env, ctx, ISA_MIPS32R2);
3360
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSConf1));
3361
            rn = "SRSConf1";
3362
            break;
3363
        case 3:
3364
            check_insn(env, ctx, ISA_MIPS32R2);
3365
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSConf2));
3366
            rn = "SRSConf2";
3367
            break;
3368
        case 4:
3369
            check_insn(env, ctx, ISA_MIPS32R2);
3370
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSConf3));
3371
            rn = "SRSConf3";
3372
            break;
3373
        case 5:
3374
            check_insn(env, ctx, ISA_MIPS32R2);
3375
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSConf4));
3376
            rn = "SRSConf4";
3377
            break;
3378
        default:
3379
            goto die;
3380
        }
3381
        break;
3382
    case 7:
3383
        switch (sel) {
3384
        case 0:
3385
            check_insn(env, ctx, ISA_MIPS32R2);
3386
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_HWREna));
3387
            rn = "HWREna";
3388
            break;
3389
        default:
3390
            goto die;
3391
        }
3392
        break;
3393
    case 8:
3394
        switch (sel) {
3395
        case 0:
3396
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_BadVAddr));
3397
            tcg_gen_ext32s_tl(arg, arg);
3398
            rn = "BadVAddr";
3399
            break;
3400
        default:
3401
            goto die;
3402
       }
3403
        break;
3404
    case 9:
3405
        switch (sel) {
3406
        case 0:
3407
            /* Mark as an IO operation because we read the time.  */
3408
            if (use_icount)
3409
                gen_io_start();
3410
            gen_helper_mfc0_count(arg);
3411
            if (use_icount) {
3412
                gen_io_end();
3413
                ctx->bstate = BS_STOP;
3414
            }
3415
            rn = "Count";
3416
            break;
3417
        /* 6,7 are implementation dependent */
3418
        default:
3419
            goto die;
3420
        }
3421
        break;
3422
    case 10:
3423
        switch (sel) {
3424
        case 0:
3425
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_EntryHi));
3426
            tcg_gen_ext32s_tl(arg, arg);
3427
            rn = "EntryHi";
3428
            break;
3429
        default:
3430
            goto die;
3431
        }
3432
        break;
3433
    case 11:
3434
        switch (sel) {
3435
        case 0:
3436
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Compare));
3437
            rn = "Compare";
3438
            break;
3439
        /* 6,7 are implementation dependent */
3440
        default:
3441
            goto die;
3442
        }
3443
        break;
3444
    case 12:
3445
        switch (sel) {
3446
        case 0:
3447
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Status));
3448
            rn = "Status";
3449
            break;
3450
        case 1:
3451
            check_insn(env, ctx, ISA_MIPS32R2);
3452
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_IntCtl));
3453
            rn = "IntCtl";
3454
            break;
3455
        case 2:
3456
            check_insn(env, ctx, ISA_MIPS32R2);
3457
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSCtl));
3458
            rn = "SRSCtl";
3459
            break;
3460
        case 3:
3461
            check_insn(env, ctx, ISA_MIPS32R2);
3462
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSMap));
3463
            rn = "SRSMap";
3464
            break;
3465
        default:
3466
            goto die;
3467
       }
3468
        break;
3469
    case 13:
3470
        switch (sel) {
3471
        case 0:
3472
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Cause));
3473
            rn = "Cause";
3474
            break;
3475
        default:
3476
            goto die;
3477
       }
3478
        break;
3479
    case 14:
3480
        switch (sel) {
3481
        case 0:
3482
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_EPC));
3483
            tcg_gen_ext32s_tl(arg, arg);
3484
            rn = "EPC";
3485
            break;
3486
        default:
3487
            goto die;
3488
        }
3489
        break;
3490
    case 15:
3491
        switch (sel) {
3492
        case 0:
3493
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_PRid));
3494
            rn = "PRid";
3495
            break;
3496
        case 1:
3497
            check_insn(env, ctx, ISA_MIPS32R2);
3498
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_EBase));
3499
            rn = "EBase";
3500
            break;
3501
        default:
3502
            goto die;
3503
       }
3504
        break;
3505
    case 16:
3506
        switch (sel) {
3507
        case 0:
3508
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config0));
3509
            rn = "Config";
3510
            break;
3511
        case 1:
3512
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config1));
3513
            rn = "Config1";
3514
            break;
3515
        case 2:
3516
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config2));
3517
            rn = "Config2";
3518
            break;
3519
        case 3:
3520
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config3));
3521
            rn = "Config3";
3522
            break;
3523
        /* 4,5 are reserved */
3524
        /* 6,7 are implementation dependent */
3525
        case 6:
3526
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config6));
3527
            rn = "Config6";
3528
            break;
3529
        case 7:
3530
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config7));
3531
            rn = "Config7";
3532
            break;
3533
        default:
3534
            goto die;
3535
        }
3536
        break;
3537
    case 17:
3538
        switch (sel) {
3539
        case 0:
3540
            gen_helper_mfc0_lladdr(arg);
3541
            rn = "LLAddr";
3542
            break;
3543
        default:
3544
            goto die;
3545
        }
3546
        break;
3547
    case 18:
3548
        switch (sel) {
3549
        case 0 ... 7:
3550
            gen_helper_1i(mfc0_watchlo, arg, sel);
3551
            rn = "WatchLo";
3552
            break;
3553
        default:
3554
            goto die;
3555
        }
3556
        break;
3557
    case 19:
3558
        switch (sel) {
3559
        case 0 ...7:
3560
            gen_helper_1i(mfc0_watchhi, arg, sel);
3561
            rn = "WatchHi";
3562
            break;
3563
        default:
3564
            goto die;
3565
        }
3566
        break;
3567
    case 20:
3568
        switch (sel) {
3569
        case 0:
3570
#if defined(TARGET_MIPS64)
3571
            check_insn(env, ctx, ISA_MIPS3);
3572
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_XContext));
3573
            tcg_gen_ext32s_tl(arg, arg);
3574
            rn = "XContext";
3575
            break;
3576
#endif
3577
        default:
3578
            goto die;
3579
        }
3580
        break;
3581
    case 21:
3582
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
3583
        switch (sel) {
3584
        case 0:
3585
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Framemask));
3586
            rn = "Framemask";
3587
            break;
3588
        default:
3589
            goto die;
3590
        }
3591
        break;
3592
    case 22:
3593
        tcg_gen_movi_tl(arg, 0); /* unimplemented */
3594
        rn = "'Diagnostic"; /* implementation dependent */
3595
        break;
3596
    case 23:
3597
        switch (sel) {
3598
        case 0:
3599
            gen_helper_mfc0_debug(arg); /* EJTAG support */
3600
            rn = "Debug";
3601
            break;
3602
        case 1:
3603
//            gen_helper_mfc0_tracecontrol(arg); /* PDtrace support */
3604
            rn = "TraceControl";
3605
//            break;
3606
        case 2:
3607
//            gen_helper_mfc0_tracecontrol2(arg); /* PDtrace support */
3608
            rn = "TraceControl2";
3609
//            break;
3610
        case 3:
3611
//            gen_helper_mfc0_usertracedata(arg); /* PDtrace support */
3612
            rn = "UserTraceData";
3613
//            break;
3614
        case 4:
3615
//            gen_helper_mfc0_tracebpc(arg); /* PDtrace support */
3616
            rn = "TraceBPC";
3617
//            break;
3618
        default:
3619
            goto die;
3620
        }
3621
        break;
3622
    case 24:
3623
        switch (sel) {
3624
        case 0:
3625
            /* EJTAG support */
3626
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_DEPC));
3627
            tcg_gen_ext32s_tl(arg, arg);
3628
            rn = "DEPC";
3629
            break;
3630
        default:
3631
            goto die;
3632
        }
3633
        break;
3634
    case 25:
3635
        switch (sel) {
3636
        case 0:
3637
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Performance0));
3638
            rn = "Performance0";
3639
            break;
3640
        case 1:
3641
//            gen_helper_mfc0_performance1(arg);
3642
            rn = "Performance1";
3643
//            break;
3644
        case 2:
3645
//            gen_helper_mfc0_performance2(arg);
3646
            rn = "Performance2";
3647
//            break;
3648
        case 3:
3649
//            gen_helper_mfc0_performance3(arg);
3650
            rn = "Performance3";
3651
//            break;
3652
        case 4:
3653
//            gen_helper_mfc0_performance4(arg);
3654
            rn = "Performance4";
3655
//            break;
3656
        case 5:
3657
//            gen_helper_mfc0_performance5(arg);
3658
            rn = "Performance5";
3659
//            break;
3660
        case 6:
3661
//            gen_helper_mfc0_performance6(arg);
3662
            rn = "Performance6";
3663
//            break;
3664
        case 7:
3665
//            gen_helper_mfc0_performance7(arg);
3666
            rn = "Performance7";
3667
//            break;
3668
        default:
3669
            goto die;
3670
        }
3671
        break;
3672
    case 26:
3673
        tcg_gen_movi_tl(arg, 0); /* unimplemented */
3674
        rn = "ECC";
3675
        break;
3676
    case 27:
3677
        switch (sel) {
3678
        case 0 ... 3:
3679
            tcg_gen_movi_tl(arg, 0); /* unimplemented */
3680
            rn = "CacheErr";
3681
            break;
3682
        default:
3683
            goto die;
3684
        }
3685
        break;
3686
    case 28:
3687
        switch (sel) {
3688
        case 0:
3689
        case 2:
3690
        case 4:
3691
        case 6:
3692
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_TagLo));
3693
            rn = "TagLo";
3694
            break;
3695
        case 1:
3696
        case 3:
3697
        case 5:
3698
        case 7:
3699
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_DataLo));
3700
            rn = "DataLo";
3701
            break;
3702
        default:
3703
            goto die;
3704
        }
3705
        break;
3706
    case 29:
3707
        switch (sel) {
3708
        case 0:
3709
        case 2:
3710
        case 4:
3711
        case 6:
3712
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_TagHi));
3713
            rn = "TagHi";
3714
            break;
3715
        case 1:
3716
        case 3:
3717
        case 5:
3718
        case 7:
3719
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_DataHi));
3720
            rn = "DataHi";
3721
            break;
3722
        default:
3723
            goto die;
3724
        }
3725
        break;
3726
    case 30:
3727
        switch (sel) {
3728
        case 0:
3729
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_ErrorEPC));
3730
            tcg_gen_ext32s_tl(arg, arg);
3731
            rn = "ErrorEPC";
3732
            break;
3733
        default:
3734
            goto die;
3735
        }
3736
        break;
3737
    case 31:
3738
        switch (sel) {
3739
        case 0:
3740
            /* EJTAG support */
3741
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_DESAVE));
3742
            rn = "DESAVE";
3743
            break;
3744
        default:
3745
            goto die;
3746
        }
3747
        break;
3748
    default:
3749
       goto die;
3750
    }
3751
    (void)rn; /* avoid a compiler warning */
3752
    LOG_DISAS("mfc0 %s (reg %d sel %d)\n", rn, reg, sel);
3753
    return;
3754

    
3755
die:
3756
    LOG_DISAS("mfc0 %s (reg %d sel %d)\n", rn, reg, sel);
3757
    generate_exception(ctx, EXCP_RI);
3758
}
3759

    
3760
static void gen_mtc0 (CPUState *env, DisasContext *ctx, TCGv arg, int reg, int sel)
3761
{
3762
    const char *rn = "invalid";
3763

    
3764
    if (sel != 0)
3765
        check_insn(env, ctx, ISA_MIPS32);
3766

    
3767
    if (use_icount)
3768
        gen_io_start();
3769

    
3770
    switch (reg) {
3771
    case 0:
3772
        switch (sel) {
3773
        case 0:
3774
            gen_helper_mtc0_index(arg);
3775
            rn = "Index";
3776
            break;
3777
        case 1:
3778
            check_insn(env, ctx, ASE_MT);
3779
            gen_helper_mtc0_mvpcontrol(arg);
3780
            rn = "MVPControl";
3781
            break;
3782
        case 2:
3783
            check_insn(env, ctx, ASE_MT);
3784
            /* ignored */
3785
            rn = "MVPConf0";
3786
            break;
3787
        case 3:
3788
            check_insn(env, ctx, ASE_MT);
3789
            /* ignored */
3790
            rn = "MVPConf1";
3791
            break;
3792
        default:
3793
            goto die;
3794
        }
3795
        break;
3796
    case 1:
3797
        switch (sel) {
3798
        case 0:
3799
            /* ignored */
3800
            rn = "Random";
3801
            break;
3802
        case 1:
3803
            check_insn(env, ctx, ASE_MT);
3804
            gen_helper_mtc0_vpecontrol(arg);
3805
            rn = "VPEControl";
3806
            break;
3807
        case 2:
3808
            check_insn(env, ctx, ASE_MT);
3809
            gen_helper_mtc0_vpeconf0(arg);
3810
            rn = "VPEConf0";
3811
            break;
3812
        case 3:
3813
            check_insn(env, ctx, ASE_MT);
3814
            gen_helper_mtc0_vpeconf1(arg);
3815
            rn = "VPEConf1";
3816
            break;
3817
        case 4:
3818
            check_insn(env, ctx, ASE_MT);
3819
            gen_helper_mtc0_yqmask(arg);
3820
            rn = "YQMask";
3821
            break;
3822
        case 5:
3823
            check_insn(env, ctx, ASE_MT);
3824
            gen_mtc0_store64(arg, offsetof(CPUState, CP0_VPESchedule));
3825
            rn = "VPESchedule";
3826
            break;
3827
        case 6:
3828
            check_insn(env, ctx, ASE_MT);
3829
            gen_mtc0_store64(arg, offsetof(CPUState, CP0_VPEScheFBack));
3830
            rn = "VPEScheFBack";
3831
            break;
3832
        case 7:
3833
            check_insn(env, ctx, ASE_MT);
3834
            gen_helper_mtc0_vpeopt(arg);
3835
            rn = "VPEOpt";
3836
            break;
3837
        default:
3838
            goto die;
3839
        }
3840
        break;
3841
    case 2:
3842
        switch (sel) {
3843
        case 0:
3844
            gen_helper_mtc0_entrylo0(arg);
3845
            rn = "EntryLo0";
3846
            break;
3847
        case 1:
3848
            check_insn(env, ctx, ASE_MT);
3849
            gen_helper_mtc0_tcstatus(arg);
3850
            rn = "TCStatus";
3851
            break;
3852
        case 2:
3853
            check_insn(env, ctx, ASE_MT);
3854
            gen_helper_mtc0_tcbind(arg);
3855
            rn = "TCBind";
3856
            break;
3857
        case 3:
3858
            check_insn(env, ctx, ASE_MT);
3859
            gen_helper_mtc0_tcrestart(arg);
3860
            rn = "TCRestart";
3861
            break;
3862
        case 4:
3863
            check_insn(env, ctx, ASE_MT);
3864
            gen_helper_mtc0_tchalt(arg);
3865
            rn = "TCHalt";
3866
            break;
3867
        case 5:
3868
            check_insn(env, ctx, ASE_MT);
3869
            gen_helper_mtc0_tccontext(arg);
3870
            rn = "TCContext";
3871
            break;
3872
        case 6:
3873
            check_insn(env, ctx, ASE_MT);
3874
            gen_helper_mtc0_tcschedule(arg);
3875
            rn = "TCSchedule";
3876
            break;
3877
        case 7:
3878
            check_insn(env, ctx, ASE_MT);
3879
            gen_helper_mtc0_tcschefback(arg);
3880
            rn = "TCScheFBack";
3881
            break;
3882
        default:
3883
            goto die;
3884
        }
3885
        break;
3886
    case 3:
3887
        switch (sel) {
3888
        case 0:
3889
            gen_helper_mtc0_entrylo1(arg);
3890
            rn = "EntryLo1";
3891
            break;
3892
        default:
3893
            goto die;
3894
        }
3895
        break;
3896
    case 4:
3897
        switch (sel) {
3898
        case 0:
3899
            gen_helper_mtc0_context(arg);
3900
            rn = "Context";
3901
            break;
3902
        case 1:
3903
//            gen_helper_mtc0_contextconfig(arg); /* SmartMIPS ASE */
3904
            rn = "ContextConfig";
3905
//            break;
3906
        default:
3907
            goto die;
3908
        }
3909
        break;
3910
    case 5:
3911
        switch (sel) {
3912
        case 0:
3913
            gen_helper_mtc0_pagemask(arg);
3914
            rn = "PageMask";
3915
            break;
3916
        case 1:
3917
            check_insn(env, ctx, ISA_MIPS32R2);
3918
            gen_helper_mtc0_pagegrain(arg);
3919
            rn = "PageGrain";
3920
            break;
3921
        default:
3922
            goto die;
3923
        }
3924
        break;
3925
    case 6:
3926
        switch (sel) {
3927
        case 0:
3928
            gen_helper_mtc0_wired(arg);
3929
            rn = "Wired";
3930
            break;
3931
        case 1:
3932
            check_insn(env, ctx, ISA_MIPS32R2);
3933
            gen_helper_mtc0_srsconf0(arg);
3934
            rn = "SRSConf0";
3935
            break;
3936
        case 2:
3937
            check_insn(env, ctx, ISA_MIPS32R2);
3938
            gen_helper_mtc0_srsconf1(arg);
3939
            rn = "SRSConf1";
3940
            break;
3941
        case 3:
3942
            check_insn(env, ctx, ISA_MIPS32R2);
3943
            gen_helper_mtc0_srsconf2(arg);
3944
            rn = "SRSConf2";
3945
            break;
3946
        case 4:
3947
            check_insn(env, ctx, ISA_MIPS32R2);
3948
            gen_helper_mtc0_srsconf3(arg);
3949
            rn = "SRSConf3";
3950
            break;
3951
        case 5:
3952
            check_insn(env, ctx, ISA_MIPS32R2);
3953
            gen_helper_mtc0_srsconf4(arg);
3954
            rn = "SRSConf4";
3955
            break;
3956
        default:
3957
            goto die;
3958
        }
3959
        break;
3960
    case 7:
3961
        switch (sel) {
3962
        case 0:
3963
            check_insn(env, ctx, ISA_MIPS32R2);
3964
            gen_helper_mtc0_hwrena(arg);
3965
            rn = "HWREna";
3966
            break;
3967
        default:
3968
            goto die;
3969
        }
3970
        break;
3971
    case 8:
3972
        /* ignored */
3973
        rn = "BadVAddr";
3974
        break;
3975
    case 9:
3976
        switch (sel) {
3977
        case 0:
3978
            gen_helper_mtc0_count(arg);
3979
            rn = "Count";
3980
            break;
3981
        /* 6,7 are implementation dependent */
3982
        default:
3983
            goto die;
3984
        }
3985
        break;
3986
    case 10:
3987
        switch (sel) {
3988
        case 0:
3989
            gen_helper_mtc0_entryhi(arg);
3990
            rn = "EntryHi";
3991
            break;
3992
        default:
3993
            goto die;
3994
        }
3995
        break;
3996
    case 11:
3997
        switch (sel) {
3998
        case 0:
3999
            gen_helper_mtc0_compare(arg);
4000
            rn = "Compare";
4001
            break;
4002
        /* 6,7 are implementation dependent */
4003
        default:
4004
            goto die;
4005
        }
4006
        break;
4007
    case 12:
4008
        switch (sel) {
4009
        case 0:
4010
            save_cpu_state(ctx, 1);
4011
            gen_helper_mtc0_status(arg);
4012
            /* BS_STOP isn't good enough here, hflags may have changed. */
4013
            gen_save_pc(ctx->pc + 4);
4014
            ctx->bstate = BS_EXCP;
4015
            rn = "Status";
4016
            break;
4017
        case 1:
4018
            check_insn(env, ctx, ISA_MIPS32R2);
4019
            gen_helper_mtc0_intctl(arg);
4020
            /* Stop translation as we may have switched the execution mode */
4021
            ctx->bstate = BS_STOP;
4022
            rn = "IntCtl";
4023
            break;
4024
        case 2:
4025
            check_insn(env, ctx, ISA_MIPS32R2);
4026
            gen_helper_mtc0_srsctl(arg);
4027
            /* Stop translation as we may have switched the execution mode */
4028
            ctx->bstate = BS_STOP;
4029
            rn = "SRSCtl";
4030
            break;
4031
        case 3:
4032
            check_insn(env, ctx, ISA_MIPS32R2);
4033
            gen_mtc0_store32(arg, offsetof(CPUState, CP0_SRSMap));
4034
            /* Stop translation as we may have switched the execution mode */
4035
            ctx->bstate = BS_STOP;
4036
            rn = "SRSMap";
4037
            break;
4038
        default:
4039
            goto die;
4040
        }
4041
        break;
4042
    case 13:
4043
        switch (sel) {
4044
        case 0:
4045
            save_cpu_state(ctx, 1);
4046
            gen_helper_mtc0_cause(arg);
4047
            rn = "Cause";
4048
            break;
4049
        default:
4050
            goto die;
4051
        }
4052
        break;
4053
    case 14:
4054
        switch (sel) {
4055
        case 0:
4056
            gen_mtc0_store64(arg, offsetof(CPUState, CP0_EPC));
4057
            rn = "EPC";
4058
            break;
4059
        default:
4060
            goto die;
4061
        }
4062
        break;
4063
    case 15:
4064
        switch (sel) {
4065
        case 0:
4066
            /* ignored */
4067
            rn = "PRid";
4068
            break;
4069
        case 1:
4070
            check_insn(env, ctx, ISA_MIPS32R2);
4071
            gen_helper_mtc0_ebase(arg);
4072
            rn = "EBase";
4073
            break;
4074
        default:
4075
            goto die;
4076
        }
4077
        break;
4078
    case 16:
4079
        switch (sel) {
4080
        case 0:
4081
            gen_helper_mtc0_config0(arg);
4082
            rn = "Config";
4083
            /* Stop translation as we may have switched the execution mode */
4084
            ctx->bstate = BS_STOP;
4085
            break;
4086
        case 1:
4087
            /* ignored, read only */
4088
            rn = "Config1";
4089
            break;
4090
        case 2:
4091
            gen_helper_mtc0_config2(arg);
4092
            rn = "Config2";
4093
            /* Stop translation as we may have switched the execution mode */
4094
            ctx->bstate = BS_STOP;
4095
            break;
4096
        case 3:
4097
            /* ignored, read only */
4098
            rn = "Config3";
4099
            break;
4100
        /* 4,5 are reserved */
4101
        /* 6,7 are implementation dependent */
4102
        case 6:
4103
            /* ignored */
4104
            rn = "Config6";
4105
            break;
4106
        case 7:
4107
            /* ignored */
4108
            rn = "Config7";
4109
            break;
4110
        default:
4111
            rn = "Invalid config selector";
4112
            goto die;
4113
        }
4114
        break;
4115
    case 17:
4116
        switch (sel) {
4117
        case 0:
4118
            gen_helper_mtc0_lladdr(arg);
4119
            rn = "LLAddr";
4120
            break;
4121
        default:
4122
            goto die;
4123
        }
4124
        break;
4125
    case 18:
4126
        switch (sel) {
4127
        case 0 ... 7:
4128
            gen_helper_1i(mtc0_watchlo, arg, sel);
4129
            rn = "WatchLo";
4130
            break;
4131
        default:
4132
            goto die;
4133
        }
4134
        break;
4135
    case 19:
4136
        switch (sel) {
4137
        case 0 ... 7:
4138
            gen_helper_1i(mtc0_watchhi, arg, sel);
4139
            rn = "WatchHi";
4140
            break;
4141
        default:
4142
            goto die;
4143
        }
4144
        break;
4145
    case 20:
4146
        switch (sel) {
4147
        case 0:
4148
#if defined(TARGET_MIPS64)
4149
            check_insn(env, ctx, ISA_MIPS3);
4150
            gen_helper_mtc0_xcontext(arg);
4151
            rn = "XContext";
4152
            break;
4153
#endif
4154
        default:
4155
            goto die;
4156
        }
4157
        break;
4158
    case 21:
4159
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
4160
        switch (sel) {
4161
        case 0:
4162
            gen_helper_mtc0_framemask(arg);
4163
            rn = "Framemask";
4164
            break;
4165
        default:
4166
            goto die;
4167
        }
4168
        break;
4169
    case 22:
4170
        /* ignored */
4171
        rn = "Diagnostic"; /* implementation dependent */
4172
        break;
4173
    case 23:
4174
        switch (sel) {
4175
        case 0:
4176
            gen_helper_mtc0_debug(arg); /* EJTAG support */
4177
            /* BS_STOP isn't good enough here, hflags may have changed. */
4178
            gen_save_pc(ctx->pc + 4);
4179
            ctx->bstate = BS_EXCP;
4180
            rn = "Debug";
4181
            break;
4182
        case 1:
4183
//            gen_helper_mtc0_tracecontrol(arg); /* PDtrace support */
4184
            rn = "TraceControl";
4185
            /* Stop translation as we may have switched the execution mode */
4186
            ctx->bstate = BS_STOP;
4187
//            break;
4188
        case 2:
4189
//            gen_helper_mtc0_tracecontrol2(arg); /* PDtrace support */
4190
            rn = "TraceControl2";
4191
            /* Stop translation as we may have switched the execution mode */
4192
            ctx->bstate = BS_STOP;
4193
//            break;
4194
        case 3:
4195
            /* Stop translation as we may have switched the execution mode */
4196
            ctx->bstate = BS_STOP;
4197
//            gen_helper_mtc0_usertracedata(arg); /* PDtrace support */
4198
            rn = "UserTraceData";
4199
            /* Stop translation as we may have switched the execution mode */
4200
            ctx->bstate = BS_STOP;
4201
//            break;
4202
        case 4:
4203
//            gen_helper_mtc0_tracebpc(arg); /* PDtrace support */
4204
            /* Stop translation as we may have switched the execution mode */
4205
            ctx->bstate = BS_STOP;
4206
            rn = "TraceBPC";
4207
//            break;
4208
        default:
4209
            goto die;
4210
        }
4211
        break;
4212
    case 24:
4213
        switch (sel) {
4214
        case 0:
4215
            /* EJTAG support */
4216
            gen_mtc0_store64(arg, offsetof(CPUState, CP0_DEPC));
4217
            rn = "DEPC";
4218
            break;
4219
        default:
4220
            goto die;
4221
        }
4222
        break;
4223
    case 25:
4224
        switch (sel) {
4225
        case 0:
4226
            gen_helper_mtc0_performance0(arg);
4227
            rn = "Performance0";
4228
            break;
4229
        case 1:
4230
//            gen_helper_mtc0_performance1(arg);
4231
            rn = "Performance1";
4232
//            break;
4233
        case 2:
4234
//            gen_helper_mtc0_performance2(arg);
4235
            rn = "Performance2";
4236
//            break;
4237
        case 3:
4238
//            gen_helper_mtc0_performance3(arg);
4239
            rn = "Performance3";
4240
//            break;
4241
        case 4:
4242
//            gen_helper_mtc0_performance4(arg);
4243
            rn = "Performance4";
4244
//            break;
4245
        case 5:
4246
//            gen_helper_mtc0_performance5(arg);
4247
            rn = "Performance5";
4248
//            break;
4249
        case 6:
4250
//            gen_helper_mtc0_performance6(arg);
4251
            rn = "Performance6";
4252
//            break;
4253
        case 7:
4254
//            gen_helper_mtc0_performance7(arg);
4255
            rn = "Performance7";
4256
//            break;
4257
        default:
4258
            goto die;
4259
        }
4260
       break;
4261
    case 26:
4262
        /* ignored */
4263
        rn = "ECC";
4264
        break;
4265
    case 27:
4266
        switch (sel) {
4267
        case 0 ... 3:
4268
            /* ignored */
4269
            rn = "CacheErr";
4270
            break;
4271
        default:
4272
            goto die;
4273
        }
4274
       break;
4275
    case 28:
4276
        switch (sel) {
4277
        case 0:
4278
        case 2:
4279
        case 4:
4280
        case 6:
4281
            gen_helper_mtc0_taglo(arg);
4282
            rn = "TagLo";
4283
            break;
4284
        case 1:
4285
        case 3:
4286
        case 5:
4287
        case 7:
4288
            gen_helper_mtc0_datalo(arg);
4289
            rn = "DataLo";
4290
            break;
4291
        default:
4292
            goto die;
4293
        }
4294
        break;
4295
    case 29:
4296
        switch (sel) {
4297
        case 0:
4298
        case 2:
4299
        case 4:
4300
        case 6:
4301
            gen_helper_mtc0_taghi(arg);
4302
            rn = "TagHi";
4303
            break;
4304
        case 1:
4305
        case 3:
4306
        case 5:
4307
        case 7:
4308
            gen_helper_mtc0_datahi(arg);
4309
            rn = "DataHi";
4310
            break;
4311
        default:
4312
            rn = "invalid sel";
4313
            goto die;
4314
        }
4315
       break;
4316
    case 30:
4317
        switch (sel) {
4318
        case 0:
4319
            gen_mtc0_store64(arg, offsetof(CPUState, CP0_ErrorEPC));
4320
            rn = "ErrorEPC";
4321
            break;
4322
        default:
4323
            goto die;
4324
        }
4325
        break;
4326
    case 31:
4327
        switch (sel) {
4328
        case 0:
4329
            /* EJTAG support */
4330
            gen_mtc0_store32(arg, offsetof(CPUState, CP0_DESAVE));
4331
            rn = "DESAVE";
4332
            break;
4333
        default:
4334
            goto die;
4335
        }
4336
        /* Stop translation as we may have switched the execution mode */
4337
        ctx->bstate = BS_STOP;
4338
        break;
4339
    default:
4340
       goto die;
4341
    }
4342
    (void)rn; /* avoid a compiler warning */
4343
    LOG_DISAS("mtc0 %s (reg %d sel %d)\n", rn, reg, sel);
4344
    /* For simplicity assume that all writes can cause interrupts.  */
4345
    if (use_icount) {
4346
        gen_io_end();
4347
        ctx->bstate = BS_STOP;
4348
    }
4349
    return;
4350

    
4351
die:
4352
    LOG_DISAS("mtc0 %s (reg %d sel %d)\n", rn, reg, sel);
4353
    generate_exception(ctx, EXCP_RI);
4354
}
4355

    
4356
#if defined(TARGET_MIPS64)
4357
static void gen_dmfc0 (CPUState *env, DisasContext *ctx, TCGv arg, int reg, int sel)
4358
{
4359
    const char *rn = "invalid";
4360

    
4361
    if (sel != 0)
4362
        check_insn(env, ctx, ISA_MIPS64);
4363

    
4364
    switch (reg) {
4365
    case 0:
4366
        switch (sel) {
4367
        case 0:
4368
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Index));
4369
            rn = "Index";
4370
            break;
4371
        case 1:
4372
            check_insn(env, ctx, ASE_MT);
4373
            gen_helper_mfc0_mvpcontrol(arg);
4374
            rn = "MVPControl";
4375
            break;
4376
        case 2:
4377
            check_insn(env, ctx, ASE_MT);
4378
            gen_helper_mfc0_mvpconf0(arg);
4379
            rn = "MVPConf0";
4380
            break;
4381
        case 3:
4382
            check_insn(env, ctx, ASE_MT);
4383
            gen_helper_mfc0_mvpconf1(arg);
4384
            rn = "MVPConf1";
4385
            break;
4386
        default:
4387
            goto die;
4388
        }
4389
        break;
4390
    case 1:
4391
        switch (sel) {
4392
        case 0:
4393
            gen_helper_mfc0_random(arg);
4394
            rn = "Random";
4395
            break;
4396
        case 1:
4397
            check_insn(env, ctx, ASE_MT);
4398
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_VPEControl));
4399
            rn = "VPEControl";
4400
            break;
4401
        case 2:
4402
            check_insn(env, ctx, ASE_MT);
4403
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_VPEConf0));
4404
            rn = "VPEConf0";
4405
            break;
4406
        case 3:
4407
            check_insn(env, ctx, ASE_MT);
4408
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_VPEConf1));
4409
            rn = "VPEConf1";
4410
            break;
4411
        case 4:
4412
            check_insn(env, ctx, ASE_MT);
4413
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_YQMask));
4414
            rn = "YQMask";
4415
            break;
4416
        case 5:
4417
            check_insn(env, ctx, ASE_MT);
4418
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_VPESchedule));
4419
            rn = "VPESchedule";
4420
            break;
4421
        case 6:
4422
            check_insn(env, ctx, ASE_MT);
4423
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_VPEScheFBack));
4424
            rn = "VPEScheFBack";
4425
            break;
4426
        case 7:
4427
            check_insn(env, ctx, ASE_MT);
4428
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_VPEOpt));
4429
            rn = "VPEOpt";
4430
            break;
4431
        default:
4432
            goto die;
4433
        }
4434
        break;
4435
    case 2:
4436
        switch (sel) {
4437
        case 0:
4438
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_EntryLo0));
4439
            rn = "EntryLo0";
4440
            break;
4441
        case 1:
4442
            check_insn(env, ctx, ASE_MT);
4443
            gen_helper_mfc0_tcstatus(arg);
4444
            rn = "TCStatus";
4445
            break;
4446
        case 2:
4447
            check_insn(env, ctx, ASE_MT);
4448
            gen_helper_mfc0_tcbind(arg);
4449
            rn = "TCBind";
4450
            break;
4451
        case 3:
4452
            check_insn(env, ctx, ASE_MT);
4453
            gen_helper_dmfc0_tcrestart(arg);
4454
            rn = "TCRestart";
4455
            break;
4456
        case 4:
4457
            check_insn(env, ctx, ASE_MT);
4458
            gen_helper_dmfc0_tchalt(arg);
4459
            rn = "TCHalt";
4460
            break;
4461
        case 5:
4462
            check_insn(env, ctx, ASE_MT);
4463
            gen_helper_dmfc0_tccontext(arg);
4464
            rn = "TCContext";
4465
            break;
4466
        case 6:
4467
            check_insn(env, ctx, ASE_MT);
4468
            gen_helper_dmfc0_tcschedule(arg);
4469
            rn = "TCSchedule";
4470
            break;
4471
        case 7:
4472
            check_insn(env, ctx, ASE_MT);
4473
            gen_helper_dmfc0_tcschefback(arg);
4474
            rn = "TCScheFBack";
4475
            break;
4476
        default:
4477
            goto die;
4478
        }
4479
        break;
4480
    case 3:
4481
        switch (sel) {
4482
        case 0:
4483
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_EntryLo1));
4484
            rn = "EntryLo1";
4485
            break;
4486
        default:
4487
            goto die;
4488
        }
4489
        break;
4490
    case 4:
4491
        switch (sel) {
4492
        case 0:
4493
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_Context));
4494
            rn = "Context";
4495
            break;
4496
        case 1:
4497
//            gen_helper_dmfc0_contextconfig(arg); /* SmartMIPS ASE */
4498
            rn = "ContextConfig";
4499
//            break;
4500
        default:
4501
            goto die;
4502
        }
4503
        break;
4504
    case 5:
4505
        switch (sel) {
4506
        case 0:
4507
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_PageMask));
4508
            rn = "PageMask";
4509
            break;
4510
        case 1:
4511
            check_insn(env, ctx, ISA_MIPS32R2);
4512
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_PageGrain));
4513
            rn = "PageGrain";
4514
            break;
4515
        default:
4516
            goto die;
4517
        }
4518
        break;
4519
    case 6:
4520
        switch (sel) {
4521
        case 0:
4522
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Wired));
4523
            rn = "Wired";
4524
            break;
4525
        case 1:
4526
            check_insn(env, ctx, ISA_MIPS32R2);
4527
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSConf0));
4528
            rn = "SRSConf0";
4529
            break;
4530
        case 2:
4531
            check_insn(env, ctx, ISA_MIPS32R2);
4532
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSConf1));
4533
            rn = "SRSConf1";
4534
            break;
4535
        case 3:
4536
            check_insn(env, ctx, ISA_MIPS32R2);
4537
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSConf2));
4538
            rn = "SRSConf2";
4539
            break;
4540
        case 4:
4541
            check_insn(env, ctx, ISA_MIPS32R2);
4542
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSConf3));
4543
            rn = "SRSConf3";
4544
            break;
4545
        case 5:
4546
            check_insn(env, ctx, ISA_MIPS32R2);
4547
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSConf4));
4548
            rn = "SRSConf4";
4549
            break;
4550
        default:
4551
            goto die;
4552
        }
4553
        break;
4554
    case 7:
4555
        switch (sel) {
4556
        case 0:
4557
            check_insn(env, ctx, ISA_MIPS32R2);
4558
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_HWREna));
4559
            rn = "HWREna";
4560
            break;
4561
        default:
4562
            goto die;
4563
        }
4564
        break;
4565
    case 8:
4566
        switch (sel) {
4567
        case 0:
4568
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_BadVAddr));
4569
            rn = "BadVAddr";
4570
            break;
4571
        default:
4572
            goto die;
4573
        }
4574
        break;
4575
    case 9:
4576
        switch (sel) {
4577
        case 0:
4578
            /* Mark as an IO operation because we read the time.  */
4579
            if (use_icount)
4580
                gen_io_start();
4581
            gen_helper_mfc0_count(arg);
4582
            if (use_icount) {
4583
                gen_io_end();
4584
                ctx->bstate = BS_STOP;
4585
            }
4586
            rn = "Count";
4587
            break;
4588
        /* 6,7 are implementation dependent */
4589
        default:
4590
            goto die;
4591
        }
4592
        break;
4593
    case 10:
4594
        switch (sel) {
4595
        case 0:
4596
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_EntryHi));
4597
            rn = "EntryHi";
4598
            break;
4599
        default:
4600
            goto die;
4601
        }
4602
        break;
4603
    case 11:
4604
        switch (sel) {
4605
        case 0:
4606
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Compare));
4607
            rn = "Compare";
4608
            break;
4609
        /* 6,7 are implementation dependent */
4610
        default:
4611
            goto die;
4612
        }
4613
        break;
4614
    case 12:
4615
        switch (sel) {
4616
        case 0:
4617
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Status));
4618
            rn = "Status";
4619
            break;
4620
        case 1:
4621
            check_insn(env, ctx, ISA_MIPS32R2);
4622
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_IntCtl));
4623
            rn = "IntCtl";
4624
            break;
4625
        case 2:
4626
            check_insn(env, ctx, ISA_MIPS32R2);
4627
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSCtl));
4628
            rn = "SRSCtl";
4629
            break;
4630
        case 3:
4631
            check_insn(env, ctx, ISA_MIPS32R2);
4632
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_SRSMap));
4633
            rn = "SRSMap";
4634
            break;
4635
        default:
4636
            goto die;
4637
        }
4638
        break;
4639
    case 13:
4640
        switch (sel) {
4641
        case 0:
4642
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Cause));
4643
            rn = "Cause";
4644
            break;
4645
        default:
4646
            goto die;
4647
        }
4648
        break;
4649
    case 14:
4650
        switch (sel) {
4651
        case 0:
4652
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_EPC));
4653
            rn = "EPC";
4654
            break;
4655
        default:
4656
            goto die;
4657
        }
4658
        break;
4659
    case 15:
4660
        switch (sel) {
4661
        case 0:
4662
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_PRid));
4663
            rn = "PRid";
4664
            break;
4665
        case 1:
4666
            check_insn(env, ctx, ISA_MIPS32R2);
4667
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_EBase));
4668
            rn = "EBase";
4669
            break;
4670
        default:
4671
            goto die;
4672
        }
4673
        break;
4674
    case 16:
4675
        switch (sel) {
4676
        case 0:
4677
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config0));
4678
            rn = "Config";
4679
            break;
4680
        case 1:
4681
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config1));
4682
            rn = "Config1";
4683
            break;
4684
        case 2:
4685
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config2));
4686
            rn = "Config2";
4687
            break;
4688
        case 3:
4689
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config3));
4690
            rn = "Config3";
4691
            break;
4692
       /* 6,7 are implementation dependent */
4693
        case 6:
4694
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config6));
4695
            rn = "Config6";
4696
            break;
4697
        case 7:
4698
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Config7));
4699
            rn = "Config7";
4700
            break;
4701
        default:
4702
            goto die;
4703
        }
4704
        break;
4705
    case 17:
4706
        switch (sel) {
4707
        case 0:
4708
            gen_helper_dmfc0_lladdr(arg);
4709
            rn = "LLAddr";
4710
            break;
4711
        default:
4712
            goto die;
4713
        }
4714
        break;
4715
    case 18:
4716
        switch (sel) {
4717
        case 0 ... 7:
4718
            gen_helper_1i(dmfc0_watchlo, arg, sel);
4719
            rn = "WatchLo";
4720
            break;
4721
        default:
4722
            goto die;
4723
        }
4724
        break;
4725
    case 19:
4726
        switch (sel) {
4727
        case 0 ... 7:
4728
            gen_helper_1i(mfc0_watchhi, arg, sel);
4729
            rn = "WatchHi";
4730
            break;
4731
        default:
4732
            goto die;
4733
        }
4734
        break;
4735
    case 20:
4736
        switch (sel) {
4737
        case 0:
4738
            check_insn(env, ctx, ISA_MIPS3);
4739
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_XContext));
4740
            rn = "XContext";
4741
            break;
4742
        default:
4743
            goto die;
4744
        }
4745
        break;
4746
    case 21:
4747
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
4748
        switch (sel) {
4749
        case 0:
4750
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Framemask));
4751
            rn = "Framemask";
4752
            break;
4753
        default:
4754
            goto die;
4755
        }
4756
        break;
4757
    case 22:
4758
        tcg_gen_movi_tl(arg, 0); /* unimplemented */
4759
        rn = "'Diagnostic"; /* implementation dependent */
4760
        break;
4761
    case 23:
4762
        switch (sel) {
4763
        case 0:
4764
            gen_helper_mfc0_debug(arg); /* EJTAG support */
4765
            rn = "Debug";
4766
            break;
4767
        case 1:
4768
//            gen_helper_dmfc0_tracecontrol(arg); /* PDtrace support */
4769
            rn = "TraceControl";
4770
//            break;
4771
        case 2:
4772
//            gen_helper_dmfc0_tracecontrol2(arg); /* PDtrace support */
4773
            rn = "TraceControl2";
4774
//            break;
4775
        case 3:
4776
//            gen_helper_dmfc0_usertracedata(arg); /* PDtrace support */
4777
            rn = "UserTraceData";
4778
//            break;
4779
        case 4:
4780
//            gen_helper_dmfc0_tracebpc(arg); /* PDtrace support */
4781
            rn = "TraceBPC";
4782
//            break;
4783
        default:
4784
            goto die;
4785
        }
4786
        break;
4787
    case 24:
4788
        switch (sel) {
4789
        case 0:
4790
            /* EJTAG support */
4791
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_DEPC));
4792
            rn = "DEPC";
4793
            break;
4794
        default:
4795
            goto die;
4796
        }
4797
        break;
4798
    case 25:
4799
        switch (sel) {
4800
        case 0:
4801
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_Performance0));
4802
            rn = "Performance0";
4803
            break;
4804
        case 1:
4805
//            gen_helper_dmfc0_performance1(arg);
4806
            rn = "Performance1";
4807
//            break;
4808
        case 2:
4809
//            gen_helper_dmfc0_performance2(arg);
4810
            rn = "Performance2";
4811
//            break;
4812
        case 3:
4813
//            gen_helper_dmfc0_performance3(arg);
4814
            rn = "Performance3";
4815
//            break;
4816
        case 4:
4817
//            gen_helper_dmfc0_performance4(arg);
4818
            rn = "Performance4";
4819
//            break;
4820
        case 5:
4821
//            gen_helper_dmfc0_performance5(arg);
4822
            rn = "Performance5";
4823
//            break;
4824
        case 6:
4825
//            gen_helper_dmfc0_performance6(arg);
4826
            rn = "Performance6";
4827
//            break;
4828
        case 7:
4829
//            gen_helper_dmfc0_performance7(arg);
4830
            rn = "Performance7";
4831
//            break;
4832
        default:
4833
            goto die;
4834
        }
4835
        break;
4836
    case 26:
4837
        tcg_gen_movi_tl(arg, 0); /* unimplemented */
4838
        rn = "ECC";
4839
        break;
4840
    case 27:
4841
        switch (sel) {
4842
        /* ignored */
4843
        case 0 ... 3:
4844
            tcg_gen_movi_tl(arg, 0); /* unimplemented */
4845
            rn = "CacheErr";
4846
            break;
4847
        default:
4848
            goto die;
4849
        }
4850
        break;
4851
    case 28:
4852
        switch (sel) {
4853
        case 0:
4854
        case 2:
4855
        case 4:
4856
        case 6:
4857
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_TagLo));
4858
            rn = "TagLo";
4859
            break;
4860
        case 1:
4861
        case 3:
4862
        case 5:
4863
        case 7:
4864
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_DataLo));
4865
            rn = "DataLo";
4866
            break;
4867
        default:
4868
            goto die;
4869
        }
4870
        break;
4871
    case 29:
4872
        switch (sel) {
4873
        case 0:
4874
        case 2:
4875
        case 4:
4876
        case 6:
4877
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_TagHi));
4878
            rn = "TagHi";
4879
            break;
4880
        case 1:
4881
        case 3:
4882
        case 5:
4883
        case 7:
4884
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_DataHi));
4885
            rn = "DataHi";
4886
            break;
4887
        default:
4888
            goto die;
4889
        }
4890
        break;
4891
    case 30:
4892
        switch (sel) {
4893
        case 0:
4894
            tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUState, CP0_ErrorEPC));
4895
            rn = "ErrorEPC";
4896
            break;
4897
        default:
4898
            goto die;
4899
        }
4900
        break;
4901
    case 31:
4902
        switch (sel) {
4903
        case 0:
4904
            /* EJTAG support */
4905
            gen_mfc0_load32(arg, offsetof(CPUState, CP0_DESAVE));
4906
            rn = "DESAVE";
4907
            break;
4908
        default:
4909
            goto die;
4910
        }
4911
        break;
4912
    default:
4913
        goto die;
4914
    }
4915
    (void)rn; /* avoid a compiler warning */
4916
    LOG_DISAS("dmfc0 %s (reg %d sel %d)\n", rn, reg, sel);
4917
    return;
4918

    
4919
die:
4920
    LOG_DISAS("dmfc0 %s (reg %d sel %d)\n", rn, reg, sel);
4921
    generate_exception(ctx, EXCP_RI);
4922
}
4923

    
4924
static void gen_dmtc0 (CPUState *env, DisasContext *ctx, TCGv arg, int reg, int sel)
4925
{
4926
    const char *rn = "invalid";
4927

    
4928
    if (sel != 0)
4929
        check_insn(env, ctx, ISA_MIPS64);
4930

    
4931
    if (use_icount)
4932
        gen_io_start();
4933

    
4934
    switch (reg) {
4935
    case 0:
4936
        switch (sel) {
4937
        case 0:
4938
            gen_helper_mtc0_index(arg);
4939
            rn = "Index";
4940
            break;
4941
        case 1:
4942
            check_insn(env, ctx, ASE_MT);
4943
            gen_helper_mtc0_mvpcontrol(arg);
4944
            rn = "MVPControl";
4945
            break;
4946
        case 2:
4947
            check_insn(env, ctx, ASE_MT);
4948
            /* ignored */
4949
            rn = "MVPConf0";
4950
            break;
4951
        case 3:
4952
            check_insn(env, ctx, ASE_MT);
4953
            /* ignored */
4954
            rn = "MVPConf1";
4955
            break;
4956
        default:
4957
            goto die;
4958
        }
4959
        break;
4960
    case 1:
4961
        switch (sel) {
4962
        case 0:
4963
            /* ignored */
4964
            rn = "Random";
4965
            break;
4966
        case 1:
4967
            check_insn(env, ctx, ASE_MT);
4968
            gen_helper_mtc0_vpecontrol(arg);
4969
            rn = "VPEControl";
4970
            break;
4971
        case 2:
4972
            check_insn(env, ctx, ASE_MT);
4973
            gen_helper_mtc0_vpeconf0(arg);
4974
            rn = "VPEConf0";
4975
            break;
4976
        case 3:
4977
            check_insn(env, ctx, ASE_MT);
4978
            gen_helper_mtc0_vpeconf1(arg);
4979
            rn = "VPEConf1";
4980
            break;
4981
        case 4:
4982
            check_insn(env, ctx, ASE_MT);
4983
            gen_helper_mtc0_yqmask(arg);
4984
            rn = "YQMask";
4985
            break;
4986
        case 5:
4987
            check_insn(env, ctx, ASE_MT);
4988
            tcg_gen_st_tl(arg, cpu_env, offsetof(CPUState, CP0_VPESchedule));
4989
            rn = "VPESchedule";
4990
            break;
4991
        case 6:
4992
            check_insn(env, ctx, ASE_MT);
4993
            tcg_gen_st_tl(arg, cpu_env, offsetof(CPUState, CP0_VPEScheFBack));
4994
            rn = "VPEScheFBack";
4995
            break;
4996
        case 7:
4997
            check_insn(env, ctx, ASE_MT);
4998
            gen_helper_mtc0_vpeopt(arg);
4999
            rn = "VPEOpt";
5000
            break;
5001
        default:
5002
            goto die;
5003
        }
5004
        break;
5005
    case 2:
5006
        switch (sel) {
5007
        case 0:
5008
            gen_helper_mtc0_entrylo0(arg);
5009
            rn = "EntryLo0";
5010
            break;
5011
        case 1:
5012
            check_insn(env, ctx, ASE_MT);
5013
            gen_helper_mtc0_tcstatus(arg);
5014
            rn = "TCStatus";
5015
            break;
5016
        case 2:
5017
            check_insn(env, ctx, ASE_MT);
5018
            gen_helper_mtc0_tcbind(arg);
5019
            rn = "TCBind";
5020
            break;
5021
        case 3:
5022
            check_insn(env, ctx, ASE_MT);
5023
            gen_helper_mtc0_tcrestart(arg);
5024
            rn = "TCRestart";
5025
            break;
5026
        case 4:
5027
            check_insn(env, ctx, ASE_MT);
5028
            gen_helper_mtc0_tchalt(arg);
5029
            rn = "TCHalt";
5030
            break;
5031
        case 5:
5032
            check_insn(env, ctx, ASE_MT);
5033
            gen_helper_mtc0_tccontext(arg);
5034
            rn = "TCContext";
5035
            break;
5036
        case 6:
5037
            check_insn(env, ctx, ASE_MT);
5038
            gen_helper_mtc0_tcschedule(arg);
5039
            rn = "TCSchedule";
5040
            break;
5041
        case 7:
5042
            check_insn(env, ctx, ASE_MT);
5043
            gen_helper_mtc0_tcschefback(arg);
5044
            rn = "TCScheFBack";
5045
            break;
5046
        default:
5047
            goto die;
5048
        }
5049
        break;
5050
    case 3:
5051
        switch (sel) {
5052
        case 0:
5053
            gen_helper_mtc0_entrylo1(arg);
5054
            rn = "EntryLo1";
5055
            break;
5056
        default:
5057
            goto die;
5058
        }
5059
        break;
5060
    case 4:
5061
        switch (sel) {
5062
        case 0:
5063
            gen_helper_mtc0_context(arg);
5064
            rn = "Context";
5065
            break;
5066
        case 1:
5067
//           gen_helper_mtc0_contextconfig(arg); /* SmartMIPS ASE */
5068
            rn = "ContextConfig";
5069
//           break;
5070
        default:
5071
            goto die;
5072
        }
5073
        break;
5074
    case 5:
5075
        switch (sel) {
5076
        case 0:
5077
            gen_helper_mtc0_pagemask(arg);
5078
            rn = "PageMask";
5079
            break;
5080
        case 1:
5081
            check_insn(env, ctx, ISA_MIPS32R2);
5082
            gen_helper_mtc0_pagegrain(arg);
5083
            rn = "PageGrain";
5084
            break;
5085
        default:
5086
            goto die;
5087
        }
5088
        break;
5089
    case 6:
5090
        switch (sel) {
5091
        case 0:
5092
            gen_helper_mtc0_wired(arg);
5093
            rn = "Wired";
5094
            break;
5095
        case 1:
5096
            check_insn(env, ctx, ISA_MIPS32R2);
5097
            gen_helper_mtc0_srsconf0(arg);
5098
            rn = "SRSConf0";
5099
            break;
5100
        case 2:
5101
            check_insn(env, ctx, ISA_MIPS32R2);
5102
            gen_helper_mtc0_srsconf1(arg);
5103
            rn = "SRSConf1";
5104
            break;
5105
        case 3:
5106
            check_insn(env, ctx, ISA_MIPS32R2);
5107
            gen_helper_mtc0_srsconf2(arg);
5108
            rn = "SRSConf2";
5109
            break;
5110
        case 4:
5111
            check_insn(env, ctx, ISA_MIPS32R2);
5112
            gen_helper_mtc0_srsconf3(arg);
5113
            rn = "SRSConf3";
5114
            break;
5115
        case 5:
5116
            check_insn(env, ctx, ISA_MIPS32R2);
5117
            gen_helper_mtc0_srsconf4(arg);
5118
            rn = "SRSConf4";
5119
            break;
5120
        default:
5121
            goto die;
5122
        }
5123
        break;
5124
    case 7:
5125
        switch (sel) {
5126
        case 0:
5127
            check_insn(env, ctx, ISA_MIPS32R2);
5128
            gen_helper_mtc0_hwrena(arg);
5129
            rn = "HWREna";
5130
            break;
5131
        default:
5132
            goto die;
5133
        }
5134
        break;
5135
    case 8:
5136
        /* ignored */
5137
        rn = "BadVAddr";
5138
        break;
5139
    case 9:
5140
        switch (sel) {
5141
        case 0:
5142
            gen_helper_mtc0_count(arg);
5143
            rn = "Count";
5144
            break;
5145
        /* 6,7 are implementation dependent */
5146
        default:
5147
            goto die;
5148
        }
5149
        /* Stop translation as we may have switched the execution mode */
5150
        ctx->bstate = BS_STOP;
5151
        break;
5152
    case 10:
5153
        switch (sel) {
5154
        case 0:
5155
            gen_helper_mtc0_entryhi(arg);
5156
            rn = "EntryHi";
5157
            break;
5158
        default:
5159
            goto die;
5160
        }
5161
        break;
5162
    case 11:
5163
        switch (sel) {
5164
        case 0:
5165
            gen_helper_mtc0_compare(arg);
5166
            rn = "Compare";
5167
            break;
5168
        /* 6,7 are implementation dependent */
5169
        default:
5170
            goto die;
5171
        }
5172
        /* Stop translation as we may have switched the execution mode */
5173
        ctx->bstate = BS_STOP;
5174
        break;
5175
    case 12:
5176
        switch (sel) {
5177
        case 0:
5178
            save_cpu_state(ctx, 1);
5179
            gen_helper_mtc0_status(arg);
5180
            /* BS_STOP isn't good enough here, hflags may have changed. */
5181
            gen_save_pc(ctx->pc + 4);
5182
            ctx->bstate = BS_EXCP;
5183
            rn = "Status";
5184
            break;
5185
        case 1:
5186
            check_insn(env, ctx, ISA_MIPS32R2);
5187
            gen_helper_mtc0_intctl(arg);
5188
            /* Stop translation as we may have switched the execution mode */
5189
            ctx->bstate = BS_STOP;
5190
            rn = "IntCtl";
5191
            break;
5192
        case 2:
5193
            check_insn(env, ctx, ISA_MIPS32R2);
5194
            gen_helper_mtc0_srsctl(arg);
5195
            /* Stop translation as we may have switched the execution mode */
5196
            ctx->bstate = BS_STOP;
5197
            rn = "SRSCtl";
5198
            break;
5199
        case 3:
5200
            check_insn(env, ctx, ISA_MIPS32R2);
5201
            gen_mtc0_store32(arg, offsetof(CPUState, CP0_SRSMap));
5202
            /* Stop translation as we may have switched the execution mode */
5203
            ctx->bstate = BS_STOP;
5204
            rn = "SRSMap";
5205
            break;
5206
        default:
5207
            goto die;
5208
        }
5209
        break;
5210
    case 13:
5211
        switch (sel) {
5212
        case 0:
5213
            save_cpu_state(ctx, 1);
5214
            /* Mark as an IO operation because we may trigger a software
5215
               interrupt.  */
5216
            if (use_icount) {
5217
                gen_io_start();
5218
            }
5219
            gen_helper_mtc0_cause(arg);
5220
            if (use_icount) {
5221
                gen_io_end();
5222
            }
5223
            /* Stop translation as we may have triggered an intetrupt */
5224
            ctx->bstate = BS_STOP;
5225
            rn = "Cause";
5226
            break;
5227
        default:
5228
            goto die;
5229
        }
5230
        break;
5231
    case 14:
5232
        switch (sel) {
5233
        case 0:
5234
            tcg_gen_st_tl(arg, cpu_env, offsetof(CPUState, CP0_EPC));
5235
            rn = "EPC";
5236
            break;
5237
        default:
5238
            goto die;
5239
        }
5240
        break;
5241
    case 15:
5242
        switch (sel) {
5243
        case 0:
5244
            /* ignored */
5245
            rn = "PRid";
5246
            break;
5247
        case 1:
5248
            check_insn(env, ctx, ISA_MIPS32R2);
5249
            gen_helper_mtc0_ebase(arg);
5250
            rn = "EBase";
5251
            break;
5252
        default:
5253
            goto die;
5254
        }
5255
        break;
5256
    case 16:
5257
        switch (sel) {
5258
        case 0:
5259
            gen_helper_mtc0_config0(arg);
5260
            rn = "Config";
5261
            /* Stop translation as we may have switched the execution mode */
5262
            ctx->bstate = BS_STOP;
5263
            break;
5264
        case 1:
5265
            /* ignored, read only */
5266
            rn = "Config1";
5267
            break;
5268
        case 2:
5269
            gen_helper_mtc0_config2(arg);
5270
            rn = "Config2";
5271
            /* Stop translation as we may have switched the execution mode */
5272
            ctx->bstate = BS_STOP;
5273
            break;
5274
        case 3:
5275
            /* ignored */
5276
            rn = "Config3";
5277
            break;
5278
        /* 6,7 are implementation dependent */
5279
        default:
5280
            rn = "Invalid config selector";
5281
            goto die;
5282
        }
5283
        break;
5284
    case 17:
5285
        switch (sel) {
5286
        case 0:
5287
            gen_helper_mtc0_lladdr(arg);
5288
            rn = "LLAddr";
5289
            break;
5290
        default:
5291
            goto die;
5292
        }
5293
        break;
5294
    case 18:
5295
        switch (sel) {
5296
        case 0 ... 7:
5297
            gen_helper_1i(mtc0_watchlo, arg, sel);
5298
            rn = "WatchLo";
5299
            break;
5300
        default:
5301
            goto die;
5302
        }
5303
        break;
5304
    case 19:
5305
        switch (sel) {
5306
        case 0 ... 7:
5307
            gen_helper_1i(mtc0_watchhi, arg, sel);
5308
            rn = "WatchHi";
5309
            break;
5310
        default:
5311
            goto die;
5312
        }
5313
        break;
5314
    case 20:
5315
        switch (sel) {
5316
        case 0:
5317
            check_insn(env, ctx, ISA_MIPS3);
5318
            gen_helper_mtc0_xcontext(arg);
5319
            rn = "XContext";
5320
            break;
5321
        default:
5322
            goto die;
5323
        }
5324
        break;
5325
    case 21:
5326
       /* Officially reserved, but sel 0 is used for R1x000 framemask */
5327
        switch (sel) {
5328
        case 0:
5329
            gen_helper_mtc0_framemask(arg);
5330
            rn = "Framemask";
5331
            break;
5332
        default:
5333
            goto die;
5334
        }
5335
        break;
5336
    case 22:
5337
        /* ignored */
5338
        rn = "Diagnostic"; /* implementation dependent */
5339
        break;
5340
    case 23:
5341
        switch (sel) {
5342
        case 0:
5343
            gen_helper_mtc0_debug(arg); /* EJTAG support */
5344
            /* BS_STOP isn't good enough here, hflags may have changed. */
5345
            gen_save_pc(ctx->pc + 4);
5346
            ctx->bstate = BS_EXCP;
5347
            rn = "Debug";
5348
            break;
5349
        case 1:
5350
//            gen_helper_mtc0_tracecontrol(arg); /* PDtrace support */
5351
            /* Stop translation as we may have switched the execution mode */
5352
            ctx->bstate = BS_STOP;
5353
            rn = "TraceControl";
5354
//            break;
5355
        case 2:
5356
//            gen_helper_mtc0_tracecontrol2(arg); /* PDtrace support */
5357
            /* Stop translation as we may have switched the execution mode */
5358
            ctx->bstate = BS_STOP;
5359
            rn = "TraceControl2";
5360
//            break;
5361
        case 3:
5362
//            gen_helper_mtc0_usertracedata(arg); /* PDtrace support */
5363
            /* Stop translation as we may have switched the execution mode */
5364
            ctx->bstate = BS_STOP;
5365
            rn = "UserTraceData";
5366
//            break;
5367
        case 4:
5368
//            gen_helper_mtc0_tracebpc(arg); /* PDtrace support */
5369
            /* Stop translation as we may have switched the execution mode */
5370
            ctx->bstate = BS_STOP;
5371
            rn = "TraceBPC";
5372
//            break;
5373
        default:
5374
            goto die;
5375
        }
5376
        break;
5377
    case 24:
5378
        switch (sel) {
5379
        case 0:
5380
            /* EJTAG support */
5381
            tcg_gen_st_tl(arg, cpu_env, offsetof(CPUState, CP0_DEPC));
5382
            rn = "DEPC";
5383
            break;
5384
        default:
5385
            goto die;
5386
        }
5387
        break;
5388
    case 25:
5389
        switch (sel) {
5390
        case 0:
5391
            gen_helper_mtc0_performance0(arg);
5392
            rn = "Performance0";
5393
            break;
5394
        case 1:
5395
//            gen_helper_mtc0_performance1(arg);
5396
            rn = "Performance1";
5397
//            break;
5398
        case 2:
5399
//            gen_helper_mtc0_performance2(arg);
5400
            rn = "Performance2";
5401
//            break;
5402
        case 3:
5403
//            gen_helper_mtc0_performance3(arg);
5404
            rn = "Performance3";
5405
//            break;
5406
        case 4:
5407
//            gen_helper_mtc0_performance4(arg);
5408
            rn = "Performance4";
5409
//            break;
5410
        case 5:
5411
//            gen_helper_mtc0_performance5(arg);
5412
            rn = "Performance5";
5413
//            break;
5414
        case 6:
5415
//            gen_helper_mtc0_performance6(arg);
5416
            rn = "Performance6";
5417
//            break;
5418
        case 7:
5419
//            gen_helper_mtc0_performance7(arg);
5420
            rn = "Performance7";
5421
//            break;
5422
        default:
5423
            goto die;
5424
        }
5425
        break;
5426
    case 26:
5427
        /* ignored */
5428
        rn = "ECC";
5429
        break;
5430
    case 27:
5431
        switch (sel) {
5432
        case 0 ... 3:
5433
            /* ignored */
5434
            rn = "CacheErr";
5435
            break;
5436
        default:
5437
            goto die;
5438
        }
5439
        break;
5440
    case 28:
5441
        switch (sel) {
5442
        case 0:
5443
        case 2:
5444
        case 4:
5445
        case 6:
5446
            gen_helper_mtc0_taglo(arg);
5447
            rn = "TagLo";
5448
            break;
5449
        case 1:
5450
        case 3:
5451
        case 5:
5452
        case 7:
5453
            gen_helper_mtc0_datalo(arg);
5454
            rn = "DataLo";
5455
            break;
5456
        default:
5457
            goto die;
5458
        }
5459
        break;
5460
    case 29:
5461
        switch (sel) {
5462
        case 0:
5463
        case 2:
5464
        case 4:
5465
        case 6:
5466
            gen_helper_mtc0_taghi(arg);
5467
            rn = "TagHi";
5468
            break;
5469
        case 1:
5470
        case 3:
5471
        case 5:
5472
        case 7:
5473
            gen_helper_mtc0_datahi(arg);
5474
            rn = "DataHi";
5475
            break;
5476
        default:
5477
            rn = "invalid sel";
5478
            goto die;
5479
        }
5480
        break;
5481
    case 30:
5482
        switch (sel) {
5483
        case 0:
5484
            tcg_gen_st_tl(arg, cpu_env, offsetof(CPUState, CP0_ErrorEPC));
5485
            rn = "ErrorEPC";
5486
            break;
5487
        default:
5488
            goto die;
5489
        }
5490
        break;
5491
    case 31:
5492
        switch (sel) {
5493
        case 0:
5494
            /* EJTAG support */
5495
            gen_mtc0_store32(arg, offsetof(CPUState, CP0_DESAVE));
5496
            rn = "DESAVE";
5497
            break;
5498
        default:
5499
            goto die;
5500
        }
5501
        /* Stop translation as we may have switched the execution mode */
5502
        ctx->bstate = BS_STOP;
5503
        break;
5504
    default:
5505
        goto die;
5506
    }
5507
    (void)rn; /* avoid a compiler warning */
5508
    LOG_DISAS("dmtc0 %s (reg %d sel %d)\n", rn, reg, sel);
5509
    /* For simplicity assume that all writes can cause interrupts.  */
5510
    if (use_icount) {
5511
        gen_io_end();
5512
        ctx->bstate = BS_STOP;
5513
    }
5514
    return;
5515

    
5516
die:
5517
    LOG_DISAS("dmtc0 %s (reg %d sel %d)\n", rn, reg, sel);
5518
    generate_exception(ctx, EXCP_RI);
5519
}
5520
#endif /* TARGET_MIPS64 */
5521

    
5522
static void gen_mftr(CPUState *env, DisasContext *ctx, int rt, int rd,
5523
                     int u, int sel, int h)
5524
{
5525
    int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
5526
    TCGv t0 = tcg_temp_local_new();
5527

    
5528
    if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
5529
        ((env->tcs[other_tc].CP0_TCBind & (0xf << CP0TCBd_CurVPE)) !=
5530
         (env->active_tc.CP0_TCBind & (0xf << CP0TCBd_CurVPE))))
5531
        tcg_gen_movi_tl(t0, -1);
5532
    else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
5533
             (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC)))
5534
        tcg_gen_movi_tl(t0, -1);
5535
    else if (u == 0) {
5536
        switch (rt) {
5537
        case 2:
5538
            switch (sel) {
5539
            case 1:
5540
                gen_helper_mftc0_tcstatus(t0);
5541
                break;
5542
            case 2:
5543
                gen_helper_mftc0_tcbind(t0);
5544
                break;
5545
            case 3:
5546
                gen_helper_mftc0_tcrestart(t0);
5547
                break;
5548
            case 4:
5549
                gen_helper_mftc0_tchalt(t0);
5550
                break;
5551
            case 5:
5552
                gen_helper_mftc0_tccontext(t0);
5553
                break;
5554
            case 6:
5555
                gen_helper_mftc0_tcschedule(t0);
5556
                break;
5557
            case 7:
5558
                gen_helper_mftc0_tcschefback(t0);
5559
                break;
5560
            default:
5561
                gen_mfc0(env, ctx, t0, rt, sel);
5562
                break;
5563
            }
5564
            break;
5565
        case 10:
5566
            switch (sel) {
5567
            case 0:
5568
                gen_helper_mftc0_entryhi(t0);
5569
                break;
5570
            default:
5571
                gen_mfc0(env, ctx, t0, rt, sel);
5572
                break;
5573
            }
5574
        case 12:
5575
            switch (sel) {
5576
            case 0:
5577
                gen_helper_mftc0_status(t0);
5578
                break;
5579
            default:
5580
                gen_mfc0(env, ctx, t0, rt, sel);
5581
                break;
5582
            }
5583
        case 23:
5584
            switch (sel) {
5585
            case 0:
5586
                gen_helper_mftc0_debug(t0);
5587
                break;
5588
            default:
5589
                gen_mfc0(env, ctx, t0, rt, sel);
5590
                break;
5591
            }
5592
            break;
5593
        default:
5594
            gen_mfc0(env, ctx, t0, rt, sel);
5595
        }
5596
    } else switch (sel) {
5597
    /* GPR registers. */
5598
    case 0:
5599
        gen_helper_1i(mftgpr, t0, rt);
5600
        break;
5601
    /* Auxiliary CPU registers */
5602
    case 1:
5603
        switch (rt) {
5604
        case 0:
5605
            gen_helper_1i(mftlo, t0, 0);
5606
            break;
5607
        case 1:
5608
            gen_helper_1i(mfthi, t0, 0);
5609
            break;
5610
        case 2:
5611
            gen_helper_1i(mftacx, t0, 0);
5612
            break;
5613
        case 4:
5614
            gen_helper_1i(mftlo, t0, 1);
5615
            break;
5616
        case 5:
5617
            gen_helper_1i(mfthi, t0, 1);
5618
            break;
5619
        case 6:
5620
            gen_helper_1i(mftacx, t0, 1);
5621
            break;
5622
        case 8:
5623
            gen_helper_1i(mftlo, t0, 2);
5624
            break;
5625
        case 9:
5626
            gen_helper_1i(mfthi, t0, 2);
5627
            break;
5628
        case 10:
5629
            gen_helper_1i(mftacx, t0, 2);
5630
            break;
5631
        case 12:
5632
            gen_helper_1i(mftlo, t0, 3);
5633
            break;
5634
        case 13:
5635
            gen_helper_1i(mfthi, t0, 3);
5636
            break;
5637
        case 14:
5638
            gen_helper_1i(mftacx, t0, 3);
5639
            break;
5640
        case 16:
5641
            gen_helper_mftdsp(t0);
5642
            break;
5643
        default:
5644
            goto die;
5645
        }
5646
        break;
5647
    /* Floating point (COP1). */
5648
    case 2:
5649
        /* XXX: For now we support only a single FPU context. */
5650
        if (h == 0) {
5651
            TCGv_i32 fp0 = tcg_temp_new_i32();
5652

    
5653
            gen_load_fpr32(fp0, rt);
5654
            tcg_gen_ext_i32_tl(t0, fp0);
5655
            tcg_temp_free_i32(fp0);
5656
        } else {
5657
            TCGv_i32 fp0 = tcg_temp_new_i32();
5658

    
5659
            gen_load_fpr32h(fp0, rt);
5660
            tcg_gen_ext_i32_tl(t0, fp0);
5661
            tcg_temp_free_i32(fp0);
5662
        }
5663
        break;
5664
    case 3:
5665
        /* XXX: For now we support only a single FPU context. */
5666
        gen_helper_1i(cfc1, t0, rt);
5667
        break;
5668
    /* COP2: Not implemented. */
5669
    case 4:
5670
    case 5:
5671
        /* fall through */
5672
    default:
5673
        goto die;
5674
    }
5675
    LOG_DISAS("mftr (reg %d u %d sel %d h %d)\n", rt, u, sel, h);
5676
    gen_store_gpr(t0, rd);
5677
    tcg_temp_free(t0);
5678
    return;
5679

    
5680
die:
5681
    tcg_temp_free(t0);
5682
    LOG_DISAS("mftr (reg %d u %d sel %d h %d)\n", rt, u, sel, h);
5683
    generate_exception(ctx, EXCP_RI);
5684
}
5685

    
5686
static void gen_mttr(CPUState *env, DisasContext *ctx, int rd, int rt,
5687
                     int u, int sel, int h)
5688
{
5689
    int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
5690
    TCGv t0 = tcg_temp_local_new();
5691

    
5692
    gen_load_gpr(t0, rt);
5693
    if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
5694
        ((env->tcs[other_tc].CP0_TCBind & (0xf << CP0TCBd_CurVPE)) !=
5695
         (env->active_tc.CP0_TCBind & (0xf << CP0TCBd_CurVPE))))
5696
        /* NOP */ ;
5697
    else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
5698
             (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC)))
5699
        /* NOP */ ;
5700
    else if (u == 0) {
5701
        switch (rd) {
5702
        case 2:
5703
            switch (sel) {
5704
            case 1:
5705
                gen_helper_mttc0_tcstatus(t0);
5706
                break;
5707
            case 2:
5708
                gen_helper_mttc0_tcbind(t0);
5709
                break;
5710
            case 3:
5711
                gen_helper_mttc0_tcrestart(t0);
5712
                break;
5713
            case 4:
5714
                gen_helper_mttc0_tchalt(t0);
5715
                break;
5716
            case 5:
5717
                gen_helper_mttc0_tccontext(t0);
5718
                break;
5719
            case 6:
5720
                gen_helper_mttc0_tcschedule(t0);
5721
                break;
5722
            case 7:
5723
                gen_helper_mttc0_tcschefback(t0);
5724
                break;
5725
            default:
5726
                gen_mtc0(env, ctx, t0, rd, sel);
5727
                break;
5728
            }
5729
            break;
5730
        case 10:
5731
            switch (sel) {
5732
            case 0:
5733
                gen_helper_mttc0_entryhi(t0);
5734
                break;
5735
            default:
5736
                gen_mtc0(env, ctx, t0, rd, sel);
5737
                break;
5738
            }
5739
        case 12:
5740
            switch (sel) {
5741
            case 0:
5742
                gen_helper_mttc0_status(t0);
5743
                break;
5744
            default:
5745
                gen_mtc0(env, ctx, t0, rd, sel);
5746
                break;
5747
            }
5748
        case 23:
5749
            switch (sel) {
5750
            case 0:
5751
                gen_helper_mttc0_debug(t0);
5752
                break;
5753
            default:
5754
                gen_mtc0(env, ctx, t0, rd, sel);
5755
                break;
5756
            }
5757
            break;
5758
        default:
5759
            gen_mtc0(env, ctx, t0, rd, sel);
5760
        }
5761
    } else switch (sel) {
5762
    /* GPR registers. */
5763
    case 0:
5764
        gen_helper_1i(mttgpr, t0, rd);
5765
        break;
5766
    /* Auxiliary CPU registers */
5767
    case 1:
5768
        switch (rd) {
5769
        case 0:
5770
            gen_helper_1i(mttlo, t0, 0);
5771
            break;
5772
        case 1:
5773
            gen_helper_1i(mtthi, t0, 0);
5774
            break;
5775
        case 2:
5776
            gen_helper_1i(mttacx, t0, 0);
5777
            break;
5778
        case 4:
5779
            gen_helper_1i(mttlo, t0, 1);
5780
            break;
5781
        case 5:
5782
            gen_helper_1i(mtthi, t0, 1);
5783
            break;
5784
        case 6:
5785
            gen_helper_1i(mttacx, t0, 1);
5786
            break;
5787
        case 8:
5788
            gen_helper_1i(mttlo, t0, 2);
5789
            break;
5790
        case 9:
5791
            gen_helper_1i(mtthi, t0, 2);
5792
            break;
5793
        case 10:
5794
            gen_helper_1i(mttacx, t0, 2);
5795
            break;
5796
        case 12:
5797
            gen_helper_1i(mttlo, t0, 3);
5798
            break;
5799
        case 13:
5800
            gen_helper_1i(mtthi, t0, 3);
5801
            break;
5802
        case 14:
5803
            gen_helper_1i(mttacx, t0, 3);
5804
            break;
5805
        case 16:
5806
            gen_helper_mttdsp(t0);
5807
            break;
5808
        default:
5809
            goto die;
5810
        }
5811
        break;
5812
    /* Floating point (COP1). */
5813
    case 2:
5814
        /* XXX: For now we support only a single FPU context. */
5815
        if (h == 0) {
5816
            TCGv_i32 fp0 = tcg_temp_new_i32();
5817

    
5818
            tcg_gen_trunc_tl_i32(fp0, t0);
5819
            gen_store_fpr32(fp0, rd);
5820
            tcg_temp_free_i32(fp0);
5821
        } else {
5822
            TCGv_i32 fp0 = tcg_temp_new_i32();
5823

    
5824
            tcg_gen_trunc_tl_i32(fp0, t0);
5825
            gen_store_fpr32h(fp0, rd);
5826
            tcg_temp_free_i32(fp0);
5827
        }
5828
        break;
5829
    case 3:
5830
        /* XXX: For now we support only a single FPU context. */
5831
        gen_helper_1i(ctc1, t0, rd);
5832
        break;
5833
    /* COP2: Not implemented. */
5834
    case 4:
5835
    case 5:
5836
        /* fall through */
5837
    default:
5838
        goto die;
5839
    }
5840
    LOG_DISAS("mttr (reg %d u %d sel %d h %d)\n", rd, u, sel, h);
5841
    tcg_temp_free(t0);
5842
    return;
5843

    
5844
die:
5845
    tcg_temp_free(t0);
5846
    LOG_DISAS("mttr (reg %d u %d sel %d h %d)\n", rd, u, sel, h);
5847
    generate_exception(ctx, EXCP_RI);
5848
}
5849

    
5850
static void gen_cp0 (CPUState *env, DisasContext *ctx, uint32_t opc, int rt, int rd)
5851
{
5852
    const char *opn = "ldst";
5853

    
5854
    switch (opc) {
5855
    case OPC_MFC0:
5856
        if (rt == 0) {
5857
            /* Treat as NOP. */
5858
            return;
5859
        }
5860
        gen_mfc0(env, ctx, cpu_gpr[rt], rd, ctx->opcode & 0x7);
5861
        opn = "mfc0";
5862
        break;
5863
    case OPC_MTC0:
5864
        {
5865
            TCGv t0 = tcg_temp_new();
5866

    
5867
            gen_load_gpr(t0, rt);
5868
            gen_mtc0(env, ctx, t0, rd, ctx->opcode & 0x7);
5869
            tcg_temp_free(t0);
5870
        }
5871
        opn = "mtc0";
5872
        break;
5873
#if defined(TARGET_MIPS64)
5874
    case OPC_DMFC0:
5875
        check_insn(env, ctx, ISA_MIPS3);
5876
        if (rt == 0) {
5877
            /* Treat as NOP. */
5878
            return;
5879
        }
5880
        gen_dmfc0(env, ctx, cpu_gpr[rt], rd, ctx->opcode & 0x7);
5881
        opn = "dmfc0";
5882
        break;
5883
    case OPC_DMTC0:
5884
        check_insn(env, ctx, ISA_MIPS3);
5885
        {
5886
            TCGv t0 = tcg_temp_new();
5887

    
5888
            gen_load_gpr(t0, rt);
5889
            gen_dmtc0(env, ctx, t0, rd, ctx->opcode & 0x7);
5890
            tcg_temp_free(t0);
5891
        }
5892
        opn = "dmtc0";
5893
        break;
5894
#endif
5895
    case OPC_MFTR:
5896
        check_insn(env, ctx, ASE_MT);
5897
        if (rd == 0) {
5898
            /* Treat as NOP. */
5899
            return;
5900
        }
5901
        gen_mftr(env, ctx, rt, rd, (ctx->opcode >> 5) & 1,
5902
                 ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
5903
        opn = "mftr";
5904
        break;
5905
    case OPC_MTTR:
5906
        check_insn(env, ctx, ASE_MT);
5907
        gen_mttr(env, ctx, rd, rt, (ctx->opcode >> 5) & 1,
5908
                 ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
5909
        opn = "mttr";
5910
        break;
5911
    case OPC_TLBWI:
5912
        opn = "tlbwi";
5913
        if (!env->tlb->helper_tlbwi)
5914
            goto die;
5915
        gen_helper_tlbwi();
5916
        break;
5917
    case OPC_TLBWR:
5918
        opn = "tlbwr";
5919
        if (!env->tlb->helper_tlbwr)
5920
            goto die;
5921
        gen_helper_tlbwr();
5922
        break;
5923
    case OPC_TLBP:
5924
        opn = "tlbp";
5925
        if (!env->tlb->helper_tlbp)
5926
            goto die;
5927
        gen_helper_tlbp();
5928
        break;
5929
    case OPC_TLBR:
5930
        opn = "tlbr";
5931
        if (!env->tlb->helper_tlbr)
5932
            goto die;
5933
        gen_helper_tlbr();
5934
        break;
5935
    case OPC_ERET:
5936
        opn = "eret";
5937
        check_insn(env, ctx, ISA_MIPS2);
5938
        gen_helper_eret();
5939
        ctx->bstate = BS_EXCP;
5940
        break;
5941
    case OPC_DERET:
5942
        opn = "deret";
5943
        check_insn(env, ctx, ISA_MIPS32);
5944
        if (!(ctx->hflags & MIPS_HFLAG_DM)) {
5945
            MIPS_INVAL(opn);
5946
            generate_exception(ctx, EXCP_RI);
5947
        } else {
5948
            gen_helper_deret();
5949
            ctx->bstate = BS_EXCP;
5950
        }
5951
        break;
5952
    case OPC_WAIT:
5953
        opn = "wait";
5954
        check_insn(env, ctx, ISA_MIPS3 | ISA_MIPS32);
5955
        /* If we get an exception, we want to restart at next instruction */
5956
        ctx->pc += 4;
5957
        save_cpu_state(ctx, 1);
5958
        ctx->pc -= 4;
5959
        gen_helper_wait();
5960
        ctx->bstate = BS_EXCP;
5961
        break;
5962
    default:
5963
 die:
5964
        MIPS_INVAL(opn);
5965
        generate_exception(ctx, EXCP_RI);
5966
        return;
5967
    }
5968
    (void)opn; /* avoid a compiler warning */
5969
    MIPS_DEBUG("%s %s %d", opn, regnames[rt], rd);
5970
}
5971
#endif /* !CONFIG_USER_ONLY */
5972

    
5973
/* CP1 Branches (before delay slot) */
5974
static void gen_compute_branch1 (CPUState *env, DisasContext *ctx, uint32_t op,
5975
                                 int32_t cc, int32_t offset)
5976
{
5977
    target_ulong btarget;
5978
    const char *opn = "cp1 cond branch";
5979
    TCGv_i32 t0 = tcg_temp_new_i32();
5980

    
5981
    if (cc != 0)
5982
        check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
5983

    
5984
    btarget = ctx->pc + 4 + offset;
5985

    
5986
    switch (op) {
5987
    case OPC_BC1F:
5988
        tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
5989
        tcg_gen_not_i32(t0, t0);
5990
        tcg_gen_andi_i32(t0, t0, 1);
5991
        tcg_gen_extu_i32_tl(bcond, t0);
5992
        opn = "bc1f";
5993
        goto not_likely;
5994
    case OPC_BC1FL:
5995
        tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
5996
        tcg_gen_not_i32(t0, t0);
5997
        tcg_gen_andi_i32(t0, t0, 1);
5998
        tcg_gen_extu_i32_tl(bcond, t0);
5999
        opn = "bc1fl";
6000
        goto likely;
6001
    case OPC_BC1T:
6002
        tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6003
        tcg_gen_andi_i32(t0, t0, 1);
6004
        tcg_gen_extu_i32_tl(bcond, t0);
6005
        opn = "bc1t";
6006
        goto not_likely;
6007
    case OPC_BC1TL:
6008
        tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6009
        tcg_gen_andi_i32(t0, t0, 1);
6010
        tcg_gen_extu_i32_tl(bcond, t0);
6011
        opn = "bc1tl";
6012
    likely:
6013
        ctx->hflags |= MIPS_HFLAG_BL;
6014
        break;
6015
    case OPC_BC1FANY2:
6016
        {
6017
            TCGv_i32 t1 = tcg_temp_new_i32();
6018
            tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6019
            tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
6020
            tcg_gen_nor_i32(t0, t0, t1);
6021
            tcg_temp_free_i32(t1);
6022
            tcg_gen_andi_i32(t0, t0, 1);
6023
            tcg_gen_extu_i32_tl(bcond, t0);
6024
        }
6025
        opn = "bc1any2f";
6026
        goto not_likely;
6027
    case OPC_BC1TANY2:
6028
        {
6029
            TCGv_i32 t1 = tcg_temp_new_i32();
6030
            tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6031
            tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
6032
            tcg_gen_or_i32(t0, t0, t1);
6033
            tcg_temp_free_i32(t1);
6034
            tcg_gen_andi_i32(t0, t0, 1);
6035
            tcg_gen_extu_i32_tl(bcond, t0);
6036
        }
6037
        opn = "bc1any2t";
6038
        goto not_likely;
6039
    case OPC_BC1FANY4:
6040
        {
6041
            TCGv_i32 t1 = tcg_temp_new_i32();
6042
            tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6043
            tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
6044
            tcg_gen_or_i32(t0, t0, t1);
6045
            tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+2));
6046
            tcg_gen_or_i32(t0, t0, t1);
6047
            tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+3));
6048
            tcg_gen_nor_i32(t0, t0, t1);
6049
            tcg_temp_free_i32(t1);
6050
            tcg_gen_andi_i32(t0, t0, 1);
6051
            tcg_gen_extu_i32_tl(bcond, t0);
6052
        }
6053
        opn = "bc1any4f";
6054
        goto not_likely;
6055
    case OPC_BC1TANY4:
6056
        {
6057
            TCGv_i32 t1 = tcg_temp_new_i32();
6058
            tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6059
            tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
6060
            tcg_gen_or_i32(t0, t0, t1);
6061
            tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+2));
6062
            tcg_gen_or_i32(t0, t0, t1);
6063
            tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+3));
6064
            tcg_gen_or_i32(t0, t0, t1);
6065
            tcg_temp_free_i32(t1);
6066
            tcg_gen_andi_i32(t0, t0, 1);
6067
            tcg_gen_extu_i32_tl(bcond, t0);
6068
        }
6069
        opn = "bc1any4t";
6070
    not_likely:
6071
        ctx->hflags |= MIPS_HFLAG_BC;
6072
        break;
6073
    default:
6074
        MIPS_INVAL(opn);
6075
        generate_exception (ctx, EXCP_RI);
6076
        goto out;
6077
    }
6078
    (void)opn; /* avoid a compiler warning */
6079
    MIPS_DEBUG("%s: cond %02x target " TARGET_FMT_lx, opn,
6080
               ctx->hflags, btarget);
6081
    ctx->btarget = btarget;
6082

    
6083
 out:
6084
    tcg_temp_free_i32(t0);
6085
}
6086

    
6087
/* Coprocessor 1 (FPU) */
6088

    
6089
#define FOP(func, fmt) (((fmt) << 21) | (func))
6090

    
6091
enum fopcode {
6092
    OPC_ADD_S = FOP(0, FMT_S),
6093
    OPC_SUB_S = FOP(1, FMT_S),
6094
    OPC_MUL_S = FOP(2, FMT_S),
6095
    OPC_DIV_S = FOP(3, FMT_S),
6096
    OPC_SQRT_S = FOP(4, FMT_S),
6097
    OPC_ABS_S = FOP(5, FMT_S),
6098
    OPC_MOV_S = FOP(6, FMT_S),
6099
    OPC_NEG_S = FOP(7, FMT_S),
6100
    OPC_ROUND_L_S = FOP(8, FMT_S),
6101
    OPC_TRUNC_L_S = FOP(9, FMT_S),
6102
    OPC_CEIL_L_S = FOP(10, FMT_S),
6103
    OPC_FLOOR_L_S = FOP(11, FMT_S),
6104
    OPC_ROUND_W_S = FOP(12, FMT_S),
6105
    OPC_TRUNC_W_S = FOP(13, FMT_S),
6106
    OPC_CEIL_W_S = FOP(14, FMT_S),
6107
    OPC_FLOOR_W_S = FOP(15, FMT_S),
6108
    OPC_MOVCF_S = FOP(17, FMT_S),
6109
    OPC_MOVZ_S = FOP(18, FMT_S),
6110
    OPC_MOVN_S = FOP(19, FMT_S),
6111
    OPC_RECIP_S = FOP(21, FMT_S),
6112
    OPC_RSQRT_S = FOP(22, FMT_S),
6113
    OPC_RECIP2_S = FOP(28, FMT_S),
6114
    OPC_RECIP1_S = FOP(29, FMT_S),
6115
    OPC_RSQRT1_S = FOP(30, FMT_S),
6116
    OPC_RSQRT2_S = FOP(31, FMT_S),
6117
    OPC_CVT_D_S = FOP(33, FMT_S),
6118
    OPC_CVT_W_S = FOP(36, FMT_S),
6119
    OPC_CVT_L_S = FOP(37, FMT_S),
6120
    OPC_CVT_PS_S = FOP(38, FMT_S),
6121
    OPC_CMP_F_S = FOP (48, FMT_S),
6122
    OPC_CMP_UN_S = FOP (49, FMT_S),
6123
    OPC_CMP_EQ_S = FOP (50, FMT_S),
6124
    OPC_CMP_UEQ_S = FOP (51, FMT_S),
6125
    OPC_CMP_OLT_S = FOP (52, FMT_S),
6126
    OPC_CMP_ULT_S = FOP (53, FMT_S),
6127
    OPC_CMP_OLE_S = FOP (54, FMT_S),
6128
    OPC_CMP_ULE_S = FOP (55, FMT_S),
6129
    OPC_CMP_SF_S = FOP (56, FMT_S),
6130
    OPC_CMP_NGLE_S = FOP (57, FMT_S),
6131
    OPC_CMP_SEQ_S = FOP (58, FMT_S),
6132
    OPC_CMP_NGL_S = FOP (59, FMT_S),
6133
    OPC_CMP_LT_S = FOP (60, FMT_S),
6134
    OPC_CMP_NGE_S = FOP (61, FMT_S),
6135
    OPC_CMP_LE_S = FOP (62, FMT_S),
6136
    OPC_CMP_NGT_S = FOP (63, FMT_S),
6137

    
6138
    OPC_ADD_D = FOP(0, FMT_D),
6139
    OPC_SUB_D = FOP(1, FMT_D),
6140
    OPC_MUL_D = FOP(2, FMT_D),
6141
    OPC_DIV_D = FOP(3, FMT_D),
6142
    OPC_SQRT_D = FOP(4, FMT_D),
6143
    OPC_ABS_D = FOP(5, FMT_D),
6144
    OPC_MOV_D = FOP(6, FMT_D),
6145
    OPC_NEG_D = FOP(7, FMT_D),
6146
    OPC_ROUND_L_D = FOP(8, FMT_D),
6147
    OPC_TRUNC_L_D = FOP(9, FMT_D),
6148
    OPC_CEIL_L_D = FOP(10, FMT_D),
6149
    OPC_FLOOR_L_D = FOP(11, FMT_D),
6150
    OPC_ROUND_W_D = FOP(12, FMT_D),
6151
    OPC_TRUNC_W_D = FOP(13, FMT_D),
6152
    OPC_CEIL_W_D = FOP(14, FMT_D),
6153
    OPC_FLOOR_W_D = FOP(15, FMT_D),
6154
    OPC_MOVCF_D = FOP(17, FMT_D),
6155
    OPC_MOVZ_D = FOP(18, FMT_D),
6156
    OPC_MOVN_D = FOP(19, FMT_D),
6157
    OPC_RECIP_D = FOP(21, FMT_D),
6158
    OPC_RSQRT_D = FOP(22, FMT_D),
6159
    OPC_RECIP2_D = FOP(28, FMT_D),
6160
    OPC_RECIP1_D = FOP(29, FMT_D),
6161
    OPC_RSQRT1_D = FOP(30, FMT_D),
6162
    OPC_RSQRT2_D = FOP(31, FMT_D),
6163
    OPC_CVT_S_D = FOP(32, FMT_D),
6164
    OPC_CVT_W_D = FOP(36, FMT_D),
6165
    OPC_CVT_L_D = FOP(37, FMT_D),
6166
    OPC_CMP_F_D = FOP (48, FMT_D),
6167
    OPC_CMP_UN_D = FOP (49, FMT_D),
6168
    OPC_CMP_EQ_D = FOP (50, FMT_D),
6169
    OPC_CMP_UEQ_D = FOP (51, FMT_D),
6170
    OPC_CMP_OLT_D = FOP (52, FMT_D),
6171
    OPC_CMP_ULT_D = FOP (53, FMT_D),
6172
    OPC_CMP_OLE_D = FOP (54, FMT_D),
6173
    OPC_CMP_ULE_D = FOP (55, FMT_D),
6174
    OPC_CMP_SF_D = FOP (56, FMT_D),
6175
    OPC_CMP_NGLE_D = FOP (57, FMT_D),
6176
    OPC_CMP_SEQ_D = FOP (58, FMT_D),
6177
    OPC_CMP_NGL_D = FOP (59, FMT_D),
6178
    OPC_CMP_LT_D = FOP (60, FMT_D),
6179
    OPC_CMP_NGE_D = FOP (61, FMT_D),
6180
    OPC_CMP_LE_D = FOP (62, FMT_D),
6181
    OPC_CMP_NGT_D = FOP (63, FMT_D),
6182

    
6183
    OPC_CVT_S_W = FOP(32, FMT_W),
6184
    OPC_CVT_D_W = FOP(33, FMT_W),
6185
    OPC_CVT_S_L = FOP(32, FMT_L),
6186
    OPC_CVT_D_L = FOP(33, FMT_L),
6187
    OPC_CVT_PS_PW = FOP(38, FMT_W),
6188

    
6189
    OPC_ADD_PS = FOP(0, FMT_PS),
6190
    OPC_SUB_PS = FOP(1, FMT_PS),
6191
    OPC_MUL_PS = FOP(2, FMT_PS),
6192
    OPC_DIV_PS = FOP(3, FMT_PS),
6193
    OPC_ABS_PS = FOP(5, FMT_PS),
6194
    OPC_MOV_PS = FOP(6, FMT_PS),
6195
    OPC_NEG_PS = FOP(7, FMT_PS),
6196
    OPC_MOVCF_PS = FOP(17, FMT_PS),
6197
    OPC_MOVZ_PS = FOP(18, FMT_PS),
6198
    OPC_MOVN_PS = FOP(19, FMT_PS),
6199
    OPC_ADDR_PS = FOP(24, FMT_PS),
6200
    OPC_MULR_PS = FOP(26, FMT_PS),
6201
    OPC_RECIP2_PS = FOP(28, FMT_PS),
6202
    OPC_RECIP1_PS = FOP(29, FMT_PS),
6203
    OPC_RSQRT1_PS = FOP(30, FMT_PS),
6204
    OPC_RSQRT2_PS = FOP(31, FMT_PS),
6205

    
6206
    OPC_CVT_S_PU = FOP(32, FMT_PS),
6207
    OPC_CVT_PW_PS = FOP(36, FMT_PS),
6208
    OPC_CVT_S_PL = FOP(40, FMT_PS),
6209
    OPC_PLL_PS = FOP(44, FMT_PS),
6210
    OPC_PLU_PS = FOP(45, FMT_PS),
6211
    OPC_PUL_PS = FOP(46, FMT_PS),
6212
    OPC_PUU_PS = FOP(47, FMT_PS),
6213
    OPC_CMP_F_PS = FOP (48, FMT_PS),
6214
    OPC_CMP_UN_PS = FOP (49, FMT_PS),
6215
    OPC_CMP_EQ_PS = FOP (50, FMT_PS),
6216
    OPC_CMP_UEQ_PS = FOP (51, FMT_PS),
6217
    OPC_CMP_OLT_PS = FOP (52, FMT_PS),
6218
    OPC_CMP_ULT_PS = FOP (53, FMT_PS),
6219
    OPC_CMP_OLE_PS = FOP (54, FMT_PS),
6220
    OPC_CMP_ULE_PS = FOP (55, FMT_PS),
6221
    OPC_CMP_SF_PS = FOP (56, FMT_PS),
6222
    OPC_CMP_NGLE_PS = FOP (57, FMT_PS),
6223
    OPC_CMP_SEQ_PS = FOP (58, FMT_PS),
6224
    OPC_CMP_NGL_PS = FOP (59, FMT_PS),
6225
    OPC_CMP_LT_PS = FOP (60, FMT_PS),
6226
    OPC_CMP_NGE_PS = FOP (61, FMT_PS),
6227
    OPC_CMP_LE_PS = FOP (62, FMT_PS),
6228
    OPC_CMP_NGT_PS = FOP (63, FMT_PS),
6229
};
6230

    
6231
static void gen_cp1 (DisasContext *ctx, uint32_t opc, int rt, int fs)
6232
{
6233
    const char *opn = "cp1 move";
6234
    TCGv t0 = tcg_temp_new();
6235

    
6236
    switch (opc) {
6237
    case OPC_MFC1:
6238
        {
6239
            TCGv_i32 fp0 = tcg_temp_new_i32();
6240

    
6241
            gen_load_fpr32(fp0, fs);
6242
            tcg_gen_ext_i32_tl(t0, fp0);
6243
            tcg_temp_free_i32(fp0);
6244
        }
6245
        gen_store_gpr(t0, rt);
6246
        opn = "mfc1";
6247
        break;
6248
    case OPC_MTC1:
6249
        gen_load_gpr(t0, rt);
6250
        {
6251
            TCGv_i32 fp0 = tcg_temp_new_i32();
6252

    
6253
            tcg_gen_trunc_tl_i32(fp0, t0);
6254
            gen_store_fpr32(fp0, fs);
6255
            tcg_temp_free_i32(fp0);
6256
        }
6257
        opn = "mtc1";
6258
        break;
6259
    case OPC_CFC1:
6260
        gen_helper_1i(cfc1, t0, fs);
6261
        gen_store_gpr(t0, rt);
6262
        opn = "cfc1";
6263
        break;
6264
    case OPC_CTC1:
6265
        gen_load_gpr(t0, rt);
6266
        gen_helper_1i(ctc1, t0, fs);
6267
        opn = "ctc1";
6268
        break;
6269
#if defined(TARGET_MIPS64)
6270
    case OPC_DMFC1:
6271
        gen_load_fpr64(ctx, t0, fs);
6272
        gen_store_gpr(t0, rt);
6273
        opn = "dmfc1";
6274
        break;
6275
    case OPC_DMTC1:
6276
        gen_load_gpr(t0, rt);
6277
        gen_store_fpr64(ctx, t0, fs);
6278
        opn = "dmtc1";
6279
        break;
6280
#endif
6281
    case OPC_MFHC1:
6282
        {
6283
            TCGv_i32 fp0 = tcg_temp_new_i32();
6284

    
6285
            gen_load_fpr32h(fp0, fs);
6286
            tcg_gen_ext_i32_tl(t0, fp0);
6287
            tcg_temp_free_i32(fp0);
6288
        }
6289
        gen_store_gpr(t0, rt);
6290
        opn = "mfhc1";
6291
        break;
6292
    case OPC_MTHC1:
6293
        gen_load_gpr(t0, rt);
6294
        {
6295
            TCGv_i32 fp0 = tcg_temp_new_i32();
6296

    
6297
            tcg_gen_trunc_tl_i32(fp0, t0);
6298
            gen_store_fpr32h(fp0, fs);
6299
            tcg_temp_free_i32(fp0);
6300
        }
6301
        opn = "mthc1";
6302
        break;
6303
    default:
6304
        MIPS_INVAL(opn);
6305
        generate_exception (ctx, EXCP_RI);
6306
        goto out;
6307
    }
6308
    (void)opn; /* avoid a compiler warning */
6309
    MIPS_DEBUG("%s %s %s", opn, regnames[rt], fregnames[fs]);
6310

    
6311
 out:
6312
    tcg_temp_free(t0);
6313
}
6314

    
6315
static void gen_movci (DisasContext *ctx, int rd, int rs, int cc, int tf)
6316
{
6317
    int l1;
6318
    TCGCond cond;
6319
    TCGv_i32 t0;
6320

    
6321
    if (rd == 0) {
6322
        /* Treat as NOP. */
6323
        return;
6324
    }
6325

    
6326
    if (tf)
6327
        cond = TCG_COND_EQ;
6328
    else
6329
        cond = TCG_COND_NE;
6330

    
6331
    l1 = gen_new_label();
6332
    t0 = tcg_temp_new_i32();
6333
    tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
6334
    tcg_gen_brcondi_i32(cond, t0, 0, l1);
6335
    tcg_temp_free_i32(t0);
6336
    if (rs == 0) {
6337
        tcg_gen_movi_tl(cpu_gpr[rd], 0);
6338
    } else {
6339
        tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
6340
    }
6341
    gen_set_label(l1);
6342
}
6343

    
6344
static inline void gen_movcf_s (int fs, int fd, int cc, int tf)
6345
{
6346
    int cond;
6347
    TCGv_i32 t0 = tcg_temp_new_i32();
6348
    int l1 = gen_new_label();
6349

    
6350
    if (tf)
6351
        cond = TCG_COND_EQ;
6352
    else
6353
        cond = TCG_COND_NE;
6354

    
6355
    tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
6356
    tcg_gen_brcondi_i32(cond, t0, 0, l1);
6357
    gen_load_fpr32(t0, fs);
6358
    gen_store_fpr32(t0, fd);
6359
    gen_set_label(l1);
6360
    tcg_temp_free_i32(t0);
6361
}
6362

    
6363
static inline void gen_movcf_d (DisasContext *ctx, int fs, int fd, int cc, int tf)
6364
{
6365
    int cond;
6366
    TCGv_i32 t0 = tcg_temp_new_i32();
6367
    TCGv_i64 fp0;
6368
    int l1 = gen_new_label();
6369

    
6370
    if (tf)
6371
        cond = TCG_COND_EQ;
6372
    else
6373
        cond = TCG_COND_NE;
6374

    
6375
    tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
6376
    tcg_gen_brcondi_i32(cond, t0, 0, l1);
6377
    tcg_temp_free_i32(t0);
6378
    fp0 = tcg_temp_new_i64();
6379
    gen_load_fpr64(ctx, fp0, fs);
6380
    gen_store_fpr64(ctx, fp0, fd);
6381
    tcg_temp_free_i64(fp0);
6382
    gen_set_label(l1);
6383
}
6384

    
6385
static inline void gen_movcf_ps (int fs, int fd, int cc, int tf)
6386
{
6387
    int cond;
6388
    TCGv_i32 t0 = tcg_temp_new_i32();
6389
    int l1 = gen_new_label();
6390
    int l2 = gen_new_label();
6391

    
6392
    if (tf)
6393
        cond = TCG_COND_EQ;
6394
    else
6395
        cond = TCG_COND_NE;
6396

    
6397
    tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
6398
    tcg_gen_brcondi_i32(cond, t0, 0, l1);
6399
    gen_load_fpr32(t0, fs);
6400
    gen_store_fpr32(t0, fd);
6401
    gen_set_label(l1);
6402

    
6403
    tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc+1));
6404
    tcg_gen_brcondi_i32(cond, t0, 0, l2);
6405
    gen_load_fpr32h(t0, fs);
6406
    gen_store_fpr32h(t0, fd);
6407
    tcg_temp_free_i32(t0);
6408
    gen_set_label(l2);
6409
}
6410

    
6411

    
6412
static void gen_farith (DisasContext *ctx, enum fopcode op1,
6413
                        int ft, int fs, int fd, int cc)
6414
{
6415
    const char *opn = "farith";
6416
    const char *condnames[] = {
6417
            "c.f",
6418
            "c.un",
6419
            "c.eq",
6420
            "c.ueq",
6421
            "c.olt",
6422
            "c.ult",
6423
            "c.ole",
6424
            "c.ule",
6425
            "c.sf",
6426
            "c.ngle",
6427
            "c.seq",
6428
            "c.ngl",
6429
            "c.lt",
6430
            "c.nge",
6431
            "c.le",
6432
            "c.ngt",
6433
    };
6434
    const char *condnames_abs[] = {
6435
            "cabs.f",
6436
            "cabs.un",
6437
            "cabs.eq",
6438
            "cabs.ueq",
6439
            "cabs.olt",
6440
            "cabs.ult",
6441
            "cabs.ole",
6442
            "cabs.ule",
6443
            "cabs.sf",
6444
            "cabs.ngle",
6445
            "cabs.seq",
6446
            "cabs.ngl",
6447
            "cabs.lt",
6448
            "cabs.nge",
6449
            "cabs.le",
6450
            "cabs.ngt",
6451
    };
6452
    enum { BINOP, CMPOP, OTHEROP } optype = OTHEROP;
6453
    uint32_t func = ctx->opcode & 0x3f;
6454

    
6455
    switch (op1) {
6456
    case OPC_ADD_S:
6457
        {
6458
            TCGv_i32 fp0 = tcg_temp_new_i32();
6459
            TCGv_i32 fp1 = tcg_temp_new_i32();
6460

    
6461
            gen_load_fpr32(fp0, fs);
6462
            gen_load_fpr32(fp1, ft);
6463
            gen_helper_float_add_s(fp0, fp0, fp1);
6464
            tcg_temp_free_i32(fp1);
6465
            gen_store_fpr32(fp0, fd);
6466
            tcg_temp_free_i32(fp0);
6467
        }
6468
        opn = "add.s";
6469
        optype = BINOP;
6470
        break;
6471
    case OPC_SUB_S:
6472
        {
6473
            TCGv_i32 fp0 = tcg_temp_new_i32();
6474
            TCGv_i32 fp1 = tcg_temp_new_i32();
6475

    
6476
            gen_load_fpr32(fp0, fs);
6477
            gen_load_fpr32(fp1, ft);
6478
            gen_helper_float_sub_s(fp0, fp0, fp1);
6479
            tcg_temp_free_i32(fp1);
6480
            gen_store_fpr32(fp0, fd);
6481
            tcg_temp_free_i32(fp0);
6482
        }
6483
        opn = "sub.s";
6484
        optype = BINOP;
6485
        break;
6486
    case OPC_MUL_S:
6487
        {
6488
            TCGv_i32 fp0 = tcg_temp_new_i32();
6489
            TCGv_i32 fp1 = tcg_temp_new_i32();
6490

    
6491
            gen_load_fpr32(fp0, fs);
6492
            gen_load_fpr32(fp1, ft);
6493
            gen_helper_float_mul_s(fp0, fp0, fp1);
6494
            tcg_temp_free_i32(fp1);
6495
            gen_store_fpr32(fp0, fd);
6496
            tcg_temp_free_i32(fp0);
6497
        }
6498
        opn = "mul.s";
6499
        optype = BINOP;
6500
        break;
6501
    case OPC_DIV_S:
6502
        {
6503
            TCGv_i32 fp0 = tcg_temp_new_i32();
6504
            TCGv_i32 fp1 = tcg_temp_new_i32();
6505

    
6506
            gen_load_fpr32(fp0, fs);
6507
            gen_load_fpr32(fp1, ft);
6508
            gen_helper_float_div_s(fp0, fp0, fp1);
6509
            tcg_temp_free_i32(fp1);
6510
            gen_store_fpr32(fp0, fd);
6511
            tcg_temp_free_i32(fp0);
6512
        }
6513
        opn = "div.s";
6514
        optype = BINOP;
6515
        break;
6516
    case OPC_SQRT_S:
6517
        {
6518
            TCGv_i32 fp0 = tcg_temp_new_i32();
6519

    
6520
            gen_load_fpr32(fp0, fs);
6521
            gen_helper_float_sqrt_s(fp0, fp0);
6522
            gen_store_fpr32(fp0, fd);
6523
            tcg_temp_free_i32(fp0);
6524
        }
6525
        opn = "sqrt.s";
6526
        break;
6527
    case OPC_ABS_S:
6528
        {
6529
            TCGv_i32 fp0 = tcg_temp_new_i32();
6530

    
6531
            gen_load_fpr32(fp0, fs);
6532
            gen_helper_float_abs_s(fp0, fp0);
6533
            gen_store_fpr32(fp0, fd);
6534
            tcg_temp_free_i32(fp0);
6535
        }
6536
        opn = "abs.s";
6537
        break;
6538
    case OPC_MOV_S:
6539
        {
6540
            TCGv_i32 fp0 = tcg_temp_new_i32();
6541

    
6542
            gen_load_fpr32(fp0, fs);
6543
            gen_store_fpr32(fp0, fd);
6544
            tcg_temp_free_i32(fp0);
6545
        }
6546
        opn = "mov.s";
6547
        break;
6548
    case OPC_NEG_S:
6549
        {
6550
            TCGv_i32 fp0 = tcg_temp_new_i32();
6551

    
6552
            gen_load_fpr32(fp0, fs);
6553
            gen_helper_float_chs_s(fp0, fp0);
6554
            gen_store_fpr32(fp0, fd);
6555
            tcg_temp_free_i32(fp0);
6556
        }
6557
        opn = "neg.s";
6558
        break;
6559
    case OPC_ROUND_L_S:
6560
        check_cp1_64bitmode(ctx);
6561
        {
6562
            TCGv_i32 fp32 = tcg_temp_new_i32();
6563
            TCGv_i64 fp64 = tcg_temp_new_i64();
6564

    
6565
            gen_load_fpr32(fp32, fs);
6566
            gen_helper_float_roundl_s(fp64, fp32);
6567
            tcg_temp_free_i32(fp32);
6568
            gen_store_fpr64(ctx, fp64, fd);
6569
            tcg_temp_free_i64(fp64);
6570
        }
6571
        opn = "round.l.s";
6572
        break;
6573
    case OPC_TRUNC_L_S:
6574
        check_cp1_64bitmode(ctx);
6575
        {
6576
            TCGv_i32 fp32 = tcg_temp_new_i32();
6577
            TCGv_i64 fp64 = tcg_temp_new_i64();
6578

    
6579
            gen_load_fpr32(fp32, fs);
6580
            gen_helper_float_truncl_s(fp64, fp32);
6581
            tcg_temp_free_i32(fp32);
6582
            gen_store_fpr64(ctx, fp64, fd);
6583
            tcg_temp_free_i64(fp64);
6584
        }
6585
        opn = "trunc.l.s";
6586
        break;
6587
    case OPC_CEIL_L_S:
6588
        check_cp1_64bitmode(ctx);
6589
        {
6590
            TCGv_i32 fp32 = tcg_temp_new_i32();
6591
            TCGv_i64 fp64 = tcg_temp_new_i64();
6592

    
6593
            gen_load_fpr32(fp32, fs);
6594
            gen_helper_float_ceill_s(fp64, fp32);
6595
            tcg_temp_free_i32(fp32);
6596
            gen_store_fpr64(ctx, fp64, fd);
6597
            tcg_temp_free_i64(fp64);
6598
        }
6599
        opn = "ceil.l.s";
6600
        break;
6601
    case OPC_FLOOR_L_S:
6602
        check_cp1_64bitmode(ctx);
6603
        {
6604
            TCGv_i32 fp32 = tcg_temp_new_i32();
6605
            TCGv_i64 fp64 = tcg_temp_new_i64();
6606

    
6607
            gen_load_fpr32(fp32, fs);
6608
            gen_helper_float_floorl_s(fp64, fp32);
6609
            tcg_temp_free_i32(fp32);
6610
            gen_store_fpr64(ctx, fp64, fd);
6611
            tcg_temp_free_i64(fp64);
6612
        }
6613
        opn = "floor.l.s";
6614
        break;
6615
    case OPC_ROUND_W_S:
6616
        {
6617
            TCGv_i32 fp0 = tcg_temp_new_i32();
6618

    
6619
            gen_load_fpr32(fp0, fs);
6620
            gen_helper_float_roundw_s(fp0, fp0);
6621
            gen_store_fpr32(fp0, fd);
6622
            tcg_temp_free_i32(fp0);
6623
        }
6624
        opn = "round.w.s";
6625
        break;
6626
    case OPC_TRUNC_W_S:
6627
        {
6628
            TCGv_i32 fp0 = tcg_temp_new_i32();
6629

    
6630
            gen_load_fpr32(fp0, fs);
6631
            gen_helper_float_truncw_s(fp0, fp0);
6632
            gen_store_fpr32(fp0, fd);
6633
            tcg_temp_free_i32(fp0);
6634
        }
6635
        opn = "trunc.w.s";
6636
        break;
6637
    case OPC_CEIL_W_S:
6638
        {
6639
            TCGv_i32 fp0 = tcg_temp_new_i32();
6640

    
6641
            gen_load_fpr32(fp0, fs);
6642
            gen_helper_float_ceilw_s(fp0, fp0);
6643
            gen_store_fpr32(fp0, fd);
6644
            tcg_temp_free_i32(fp0);
6645
        }
6646
        opn = "ceil.w.s";
6647
        break;
6648
    case OPC_FLOOR_W_S:
6649
        {
6650
            TCGv_i32 fp0 = tcg_temp_new_i32();
6651

    
6652
            gen_load_fpr32(fp0, fs);
6653
            gen_helper_float_floorw_s(fp0, fp0);
6654
            gen_store_fpr32(fp0, fd);
6655
            tcg_temp_free_i32(fp0);
6656
        }
6657
        opn = "floor.w.s";
6658
        break;
6659
    case OPC_MOVCF_S:
6660
        gen_movcf_s(fs, fd, (ft >> 2) & 0x7, ft & 0x1);
6661
        opn = "movcf.s";
6662
        break;
6663
    case OPC_MOVZ_S:
6664
        {
6665
            int l1 = gen_new_label();
6666
            TCGv_i32 fp0;
6667

    
6668
            if (ft != 0) {
6669
                tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
6670
            }
6671
            fp0 = tcg_temp_new_i32();
6672
            gen_load_fpr32(fp0, fs);
6673
            gen_store_fpr32(fp0, fd);
6674
            tcg_temp_free_i32(fp0);
6675
            gen_set_label(l1);
6676
        }
6677
        opn = "movz.s";
6678
        break;
6679
    case OPC_MOVN_S:
6680
        {
6681
            int l1 = gen_new_label();
6682
            TCGv_i32 fp0;
6683

    
6684
            if (ft != 0) {
6685
                tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
6686
                fp0 = tcg_temp_new_i32();
6687
                gen_load_fpr32(fp0, fs);
6688
                gen_store_fpr32(fp0, fd);
6689
                tcg_temp_free_i32(fp0);
6690
                gen_set_label(l1);
6691
            }
6692
        }
6693
        opn = "movn.s";
6694
        break;
6695
    case OPC_RECIP_S:
6696
        check_cop1x(ctx);
6697
        {
6698
            TCGv_i32 fp0 = tcg_temp_new_i32();
6699

    
6700
            gen_load_fpr32(fp0, fs);
6701
            gen_helper_float_recip_s(fp0, fp0);
6702
            gen_store_fpr32(fp0, fd);
6703
            tcg_temp_free_i32(fp0);
6704
        }
6705
        opn = "recip.s";
6706
        break;
6707
    case OPC_RSQRT_S:
6708
        check_cop1x(ctx);
6709
        {
6710
            TCGv_i32 fp0 = tcg_temp_new_i32();
6711

    
6712
            gen_load_fpr32(fp0, fs);
6713
            gen_helper_float_rsqrt_s(fp0, fp0);
6714
            gen_store_fpr32(fp0, fd);
6715
            tcg_temp_free_i32(fp0);
6716
        }
6717
        opn = "rsqrt.s";
6718
        break;
6719
    case OPC_RECIP2_S:
6720
        check_cp1_64bitmode(ctx);
6721
        {
6722
            TCGv_i32 fp0 = tcg_temp_new_i32();
6723
            TCGv_i32 fp1 = tcg_temp_new_i32();
6724

    
6725
            gen_load_fpr32(fp0, fs);
6726
            gen_load_fpr32(fp1, fd);
6727
            gen_helper_float_recip2_s(fp0, fp0, fp1);
6728
            tcg_temp_free_i32(fp1);
6729
            gen_store_fpr32(fp0, fd);
6730
            tcg_temp_free_i32(fp0);
6731
        }
6732
        opn = "recip2.s";
6733
        break;
6734
    case OPC_RECIP1_S:
6735
        check_cp1_64bitmode(ctx);
6736
        {
6737
            TCGv_i32 fp0 = tcg_temp_new_i32();
6738

    
6739
            gen_load_fpr32(fp0, fs);
6740
            gen_helper_float_recip1_s(fp0, fp0);
6741
            gen_store_fpr32(fp0, fd);
6742
            tcg_temp_free_i32(fp0);
6743
        }
6744
        opn = "recip1.s";
6745
        break;
6746
    case OPC_RSQRT1_S:
6747
        check_cp1_64bitmode(ctx);
6748
        {
6749
            TCGv_i32 fp0 = tcg_temp_new_i32();
6750

    
6751
            gen_load_fpr32(fp0, fs);
6752
            gen_helper_float_rsqrt1_s(fp0, fp0);
6753
            gen_store_fpr32(fp0, fd);
6754
            tcg_temp_free_i32(fp0);
6755
        }
6756
        opn = "rsqrt1.s";
6757
        break;
6758
    case OPC_RSQRT2_S:
6759
        check_cp1_64bitmode(ctx);
6760
        {
6761
            TCGv_i32 fp0 = tcg_temp_new_i32();
6762
            TCGv_i32 fp1 = tcg_temp_new_i32();
6763

    
6764
            gen_load_fpr32(fp0, fs);
6765
            gen_load_fpr32(fp1, ft);
6766
            gen_helper_float_rsqrt2_s(fp0, fp0, fp1);
6767
            tcg_temp_free_i32(fp1);
6768
            gen_store_fpr32(fp0, fd);
6769
            tcg_temp_free_i32(fp0);
6770
        }
6771
        opn = "rsqrt2.s";
6772
        break;
6773
    case OPC_CVT_D_S:
6774
        check_cp1_registers(ctx, fd);
6775
        {
6776
            TCGv_i32 fp32 = tcg_temp_new_i32();
6777
            TCGv_i64 fp64 = tcg_temp_new_i64();
6778

    
6779
            gen_load_fpr32(fp32, fs);
6780
            gen_helper_float_cvtd_s(fp64, fp32);
6781
            tcg_temp_free_i32(fp32);
6782
            gen_store_fpr64(ctx, fp64, fd);
6783
            tcg_temp_free_i64(fp64);
6784
        }
6785
        opn = "cvt.d.s";
6786
        break;
6787
    case OPC_CVT_W_S:
6788
        {
6789
            TCGv_i32 fp0 = tcg_temp_new_i32();
6790

    
6791
            gen_load_fpr32(fp0, fs);
6792
            gen_helper_float_cvtw_s(fp0, fp0);
6793
            gen_store_fpr32(fp0, fd);
6794
            tcg_temp_free_i32(fp0);
6795
        }
6796
        opn = "cvt.w.s";
6797
        break;
6798
    case OPC_CVT_L_S:
6799
        check_cp1_64bitmode(ctx);
6800
        {
6801
            TCGv_i32 fp32 = tcg_temp_new_i32();
6802
            TCGv_i64 fp64 = tcg_temp_new_i64();
6803

    
6804
            gen_load_fpr32(fp32, fs);
6805
            gen_helper_float_cvtl_s(fp64, fp32);
6806
            tcg_temp_free_i32(fp32);
6807
            gen_store_fpr64(ctx, fp64, fd);
6808
            tcg_temp_free_i64(fp64);
6809
        }
6810
        opn = "cvt.l.s";
6811
        break;
6812
    case OPC_CVT_PS_S:
6813
        check_cp1_64bitmode(ctx);
6814
        {
6815
            TCGv_i64 fp64 = tcg_temp_new_i64();
6816
            TCGv_i32 fp32_0 = tcg_temp_new_i32();
6817
            TCGv_i32 fp32_1 = tcg_temp_new_i32();
6818

    
6819
            gen_load_fpr32(fp32_0, fs);
6820
            gen_load_fpr32(fp32_1, ft);
6821
            tcg_gen_concat_i32_i64(fp64, fp32_0, fp32_1);
6822
            tcg_temp_free_i32(fp32_1);
6823
            tcg_temp_free_i32(fp32_0);
6824
            gen_store_fpr64(ctx, fp64, fd);
6825
            tcg_temp_free_i64(fp64);
6826
        }
6827
        opn = "cvt.ps.s";
6828
        break;
6829
    case OPC_CMP_F_S:
6830
    case OPC_CMP_UN_S:
6831
    case OPC_CMP_EQ_S:
6832
    case OPC_CMP_UEQ_S:
6833
    case OPC_CMP_OLT_S:
6834
    case OPC_CMP_ULT_S:
6835
    case OPC_CMP_OLE_S:
6836
    case OPC_CMP_ULE_S:
6837
    case OPC_CMP_SF_S:
6838
    case OPC_CMP_NGLE_S:
6839
    case OPC_CMP_SEQ_S:
6840
    case OPC_CMP_NGL_S:
6841
    case OPC_CMP_LT_S:
6842
    case OPC_CMP_NGE_S:
6843
    case OPC_CMP_LE_S:
6844
    case OPC_CMP_NGT_S:
6845
        if (ctx->opcode & (1 << 6)) {
6846
            gen_cmpabs_s(ctx, func-48, ft, fs, cc);
6847
            opn = condnames_abs[func-48];
6848
        } else {
6849
            gen_cmp_s(ctx, func-48, ft, fs, cc);
6850
            opn = condnames[func-48];
6851
        }
6852
        break;
6853
    case OPC_ADD_D:
6854
        check_cp1_registers(ctx, fs | ft | fd);
6855
        {
6856
            TCGv_i64 fp0 = tcg_temp_new_i64();
6857
            TCGv_i64 fp1 = tcg_temp_new_i64();
6858

    
6859
            gen_load_fpr64(ctx, fp0, fs);
6860
            gen_load_fpr64(ctx, fp1, ft);
6861
            gen_helper_float_add_d(fp0, fp0, fp1);
6862
            tcg_temp_free_i64(fp1);
6863
            gen_store_fpr64(ctx, fp0, fd);
6864
            tcg_temp_free_i64(fp0);
6865
        }
6866
        opn = "add.d";
6867
        optype = BINOP;
6868
        break;
6869
    case OPC_SUB_D:
6870
        check_cp1_registers(ctx, fs | ft | fd);
6871
        {
6872
            TCGv_i64 fp0 = tcg_temp_new_i64();
6873
            TCGv_i64 fp1 = tcg_temp_new_i64();
6874

    
6875
            gen_load_fpr64(ctx, fp0, fs);
6876
            gen_load_fpr64(ctx, fp1, ft);
6877
            gen_helper_float_sub_d(fp0, fp0, fp1);
6878
            tcg_temp_free_i64(fp1);
6879
            gen_store_fpr64(ctx, fp0, fd);
6880
            tcg_temp_free_i64(fp0);
6881
        }
6882
        opn = "sub.d";
6883
        optype = BINOP;
6884
        break;
6885
    case OPC_MUL_D:
6886
        check_cp1_registers(ctx, fs | ft | fd);
6887
        {
6888
            TCGv_i64 fp0 = tcg_temp_new_i64();
6889
            TCGv_i64 fp1 = tcg_temp_new_i64();
6890

    
6891
            gen_load_fpr64(ctx, fp0, fs);
6892
            gen_load_fpr64(ctx, fp1, ft);
6893
            gen_helper_float_mul_d(fp0, fp0, fp1);
6894
            tcg_temp_free_i64(fp1);
6895
            gen_store_fpr64(ctx, fp0, fd);
6896
            tcg_temp_free_i64(fp0);
6897
        }
6898
        opn = "mul.d";
6899
        optype = BINOP;
6900
        break;
6901
    case OPC_DIV_D:
6902
        check_cp1_registers(ctx, fs | ft | fd);
6903
        {
6904
            TCGv_i64 fp0 = tcg_temp_new_i64();
6905
            TCGv_i64 fp1 = tcg_temp_new_i64();
6906

    
6907
            gen_load_fpr64(ctx, fp0, fs);
6908
            gen_load_fpr64(ctx, fp1, ft);
6909
            gen_helper_float_div_d(fp0, fp0, fp1);
6910
            tcg_temp_free_i64(fp1);
6911
            gen_store_fpr64(ctx, fp0, fd);
6912
            tcg_temp_free_i64(fp0);
6913
        }
6914
        opn = "div.d";
6915
        optype = BINOP;
6916
        break;
6917
    case OPC_SQRT_D:
6918
        check_cp1_registers(ctx, fs | fd);
6919
        {
6920
            TCGv_i64 fp0 = tcg_temp_new_i64();
6921

    
6922
            gen_load_fpr64(ctx, fp0, fs);
6923
            gen_helper_float_sqrt_d(fp0, fp0);
6924
            gen_store_fpr64(ctx, fp0, fd);
6925
            tcg_temp_free_i64(fp0);
6926
        }
6927
        opn = "sqrt.d";
6928
        break;
6929
    case OPC_ABS_D:
6930
        check_cp1_registers(ctx, fs | fd);
6931
        {
6932
            TCGv_i64 fp0 = tcg_temp_new_i64();
6933

    
6934
            gen_load_fpr64(ctx, fp0, fs);
6935
            gen_helper_float_abs_d(fp0, fp0);
6936
            gen_store_fpr64(ctx, fp0, fd);
6937
            tcg_temp_free_i64(fp0);
6938
        }
6939
        opn = "abs.d";
6940
        break;
6941
    case OPC_MOV_D:
6942
        check_cp1_registers(ctx, fs | fd);
6943
        {
6944
            TCGv_i64 fp0 = tcg_temp_new_i64();
6945

    
6946
            gen_load_fpr64(ctx, fp0, fs);
6947
            gen_store_fpr64(ctx, fp0, fd);
6948
            tcg_temp_free_i64(fp0);
6949
        }
6950
        opn = "mov.d";
6951
        break;
6952
    case OPC_NEG_D:
6953
        check_cp1_registers(ctx, fs | fd);
6954
        {
6955
            TCGv_i64 fp0 = tcg_temp_new_i64();
6956

    
6957
            gen_load_fpr64(ctx, fp0, fs);
6958
            gen_helper_float_chs_d(fp0, fp0);
6959
            gen_store_fpr64(ctx, fp0, fd);
6960
            tcg_temp_free_i64(fp0);
6961
        }
6962
        opn = "neg.d";
6963
        break;
6964
    case OPC_ROUND_L_D:
6965
        check_cp1_64bitmode(ctx);
6966
        {
6967
            TCGv_i64 fp0 = tcg_temp_new_i64();
6968

    
6969
            gen_load_fpr64(ctx, fp0, fs);
6970
            gen_helper_float_roundl_d(fp0, fp0);
6971
            gen_store_fpr64(ctx, fp0, fd);
6972
            tcg_temp_free_i64(fp0);
6973
        }
6974
        opn = "round.l.d";
6975
        break;
6976
    case OPC_TRUNC_L_D:
6977
        check_cp1_64bitmode(ctx);
6978
        {
6979
            TCGv_i64 fp0 = tcg_temp_new_i64();
6980

    
6981
            gen_load_fpr64(ctx, fp0, fs);
6982
            gen_helper_float_truncl_d(fp0, fp0);
6983
            gen_store_fpr64(ctx, fp0, fd);
6984
            tcg_temp_free_i64(fp0);
6985
        }
6986
        opn = "trunc.l.d";
6987
        break;
6988
    case OPC_CEIL_L_D:
6989
        check_cp1_64bitmode(ctx);
6990
        {
6991
            TCGv_i64 fp0 = tcg_temp_new_i64();
6992

    
6993
            gen_load_fpr64(ctx, fp0, fs);
6994
            gen_helper_float_ceill_d(fp0, fp0);
6995
            gen_store_fpr64(ctx, fp0, fd);
6996
            tcg_temp_free_i64(fp0);
6997
        }
6998
        opn = "ceil.l.d";
6999
        break;
7000
    case OPC_FLOOR_L_D:
7001
        check_cp1_64bitmode(ctx);
7002
        {
7003
            TCGv_i64 fp0 = tcg_temp_new_i64();
7004

    
7005
            gen_load_fpr64(ctx, fp0, fs);
7006
            gen_helper_float_floorl_d(fp0, fp0);
7007
            gen_store_fpr64(ctx, fp0, fd);
7008
            tcg_temp_free_i64(fp0);
7009
        }
7010
        opn = "floor.l.d";
7011
        break;
7012
    case OPC_ROUND_W_D:
7013
        check_cp1_registers(ctx, fs);
7014
        {
7015
            TCGv_i32 fp32 = tcg_temp_new_i32();
7016
            TCGv_i64 fp64 = tcg_temp_new_i64();
7017

    
7018
            gen_load_fpr64(ctx, fp64, fs);
7019
            gen_helper_float_roundw_d(fp32, fp64);
7020
            tcg_temp_free_i64(fp64);
7021
            gen_store_fpr32(fp32, fd);
7022
            tcg_temp_free_i32(fp32);
7023
        }
7024
        opn = "round.w.d";
7025
        break;
7026
    case OPC_TRUNC_W_D:
7027
        check_cp1_registers(ctx, fs);
7028
        {
7029
            TCGv_i32 fp32 = tcg_temp_new_i32();
7030
            TCGv_i64 fp64 = tcg_temp_new_i64();
7031

    
7032
            gen_load_fpr64(ctx, fp64, fs);
7033
            gen_helper_float_truncw_d(fp32, fp64);
7034
            tcg_temp_free_i64(fp64);
7035
            gen_store_fpr32(fp32, fd);
7036
            tcg_temp_free_i32(fp32);
7037
        }
7038
        opn = "trunc.w.d";
7039
        break;
7040
    case OPC_CEIL_W_D:
7041
        check_cp1_registers(ctx, fs);
7042
        {
7043
            TCGv_i32 fp32 = tcg_temp_new_i32();
7044
            TCGv_i64 fp64 = tcg_temp_new_i64();
7045

    
7046
            gen_load_fpr64(ctx, fp64, fs);
7047
            gen_helper_float_ceilw_d(fp32, fp64);
7048
            tcg_temp_free_i64(fp64);
7049
            gen_store_fpr32(fp32, fd);
7050
            tcg_temp_free_i32(fp32);
7051
        }
7052
        opn = "ceil.w.d";
7053
        break;
7054
    case OPC_FLOOR_W_D:
7055
        check_cp1_registers(ctx, fs);
7056
        {
7057
            TCGv_i32 fp32 = tcg_temp_new_i32();
7058
            TCGv_i64 fp64 = tcg_temp_new_i64();
7059

    
7060
            gen_load_fpr64(ctx, fp64, fs);
7061
            gen_helper_float_floorw_d(fp32, fp64);
7062
            tcg_temp_free_i64(fp64);
7063
            gen_store_fpr32(fp32, fd);
7064
            tcg_temp_free_i32(fp32);
7065
        }
7066
        opn = "floor.w.d";
7067
        break;
7068
    case OPC_MOVCF_D:
7069
        gen_movcf_d(ctx, fs, fd, (ft >> 2) & 0x7, ft & 0x1);
7070
        opn = "movcf.d";
7071
        break;
7072
    case OPC_MOVZ_D:
7073
        {
7074
            int l1 = gen_new_label();
7075
            TCGv_i64 fp0;
7076

    
7077
            if (ft != 0) {
7078
                tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
7079
            }
7080
            fp0 = tcg_temp_new_i64();
7081
            gen_load_fpr64(ctx, fp0, fs);
7082
            gen_store_fpr64(ctx, fp0, fd);
7083
            tcg_temp_free_i64(fp0);
7084
            gen_set_label(l1);
7085
        }
7086
        opn = "movz.d";
7087
        break;
7088
    case OPC_MOVN_D:
7089
        {
7090
            int l1 = gen_new_label();
7091
            TCGv_i64 fp0;
7092

    
7093
            if (ft != 0) {
7094
                tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
7095
                fp0 = tcg_temp_new_i64();
7096
                gen_load_fpr64(ctx, fp0, fs);
7097
                gen_store_fpr64(ctx, fp0, fd);
7098
                tcg_temp_free_i64(fp0);
7099
                gen_set_label(l1);
7100
            }
7101
        }
7102
        opn = "movn.d";
7103
        break;
7104
    case OPC_RECIP_D:
7105
        check_cp1_64bitmode(ctx);
7106
        {
7107
            TCGv_i64 fp0 = tcg_temp_new_i64();
7108

    
7109
            gen_load_fpr64(ctx, fp0, fs);
7110
            gen_helper_float_recip_d(fp0, fp0);
7111
            gen_store_fpr64(ctx, fp0, fd);
7112
            tcg_temp_free_i64(fp0);
7113
        }
7114
        opn = "recip.d";
7115
        break;
7116
    case OPC_RSQRT_D:
7117
        check_cp1_64bitmode(ctx);
7118
        {
7119
            TCGv_i64 fp0 = tcg_temp_new_i64();
7120

    
7121
            gen_load_fpr64(ctx, fp0, fs);
7122
            gen_helper_float_rsqrt_d(fp0, fp0);
7123
            gen_store_fpr64(ctx, fp0, fd);
7124
            tcg_temp_free_i64(fp0);
7125
        }
7126
        opn = "rsqrt.d";
7127
        break;
7128
    case OPC_RECIP2_D:
7129
        check_cp1_64bitmode(ctx);
7130
        {
7131
            TCGv_i64 fp0 = tcg_temp_new_i64();
7132
            TCGv_i64 fp1 = tcg_temp_new_i64();
7133

    
7134
            gen_load_fpr64(ctx, fp0, fs);
7135
            gen_load_fpr64(ctx, fp1, ft);
7136
            gen_helper_float_recip2_d(fp0, fp0, fp1);
7137
            tcg_temp_free_i64(fp1);
7138
            gen_store_fpr64(ctx, fp0, fd);
7139
            tcg_temp_free_i64(fp0);
7140
        }
7141
        opn = "recip2.d";
7142
        break;
7143
    case OPC_RECIP1_D:
7144
        check_cp1_64bitmode(ctx);
7145
        {
7146
            TCGv_i64 fp0 = tcg_temp_new_i64();
7147

    
7148
            gen_load_fpr64(ctx, fp0, fs);
7149
            gen_helper_float_recip1_d(fp0, fp0);
7150
            gen_store_fpr64(ctx, fp0, fd);
7151
            tcg_temp_free_i64(fp0);
7152
        }
7153
        opn = "recip1.d";
7154
        break;
7155
    case OPC_RSQRT1_D:
7156
        check_cp1_64bitmode(ctx);
7157
        {
7158
            TCGv_i64 fp0 = tcg_temp_new_i64();
7159

    
7160
            gen_load_fpr64(ctx, fp0, fs);
7161
            gen_helper_float_rsqrt1_d(fp0, fp0);
7162
            gen_store_fpr64(ctx, fp0, fd);
7163
            tcg_temp_free_i64(fp0);
7164
        }
7165
        opn = "rsqrt1.d";
7166
        break;
7167
    case OPC_RSQRT2_D:
7168
        check_cp1_64bitmode(ctx);
7169
        {
7170
            TCGv_i64 fp0 = tcg_temp_new_i64();
7171
            TCGv_i64 fp1 = tcg_temp_new_i64();
7172

    
7173
            gen_load_fpr64(ctx, fp0, fs);
7174
            gen_load_fpr64(ctx, fp1, ft);
7175
            gen_helper_float_rsqrt2_d(fp0, fp0, fp1);
7176
            tcg_temp_free_i64(fp1);
7177
            gen_store_fpr64(ctx, fp0, fd);
7178
            tcg_temp_free_i64(fp0);
7179
        }
7180
        opn = "rsqrt2.d";
7181
        break;
7182
    case OPC_CMP_F_D:
7183
    case OPC_CMP_UN_D:
7184
    case OPC_CMP_EQ_D:
7185
    case OPC_CMP_UEQ_D:
7186
    case OPC_CMP_OLT_D:
7187
    case OPC_CMP_ULT_D:
7188
    case OPC_CMP_OLE_D:
7189
    case OPC_CMP_ULE_D:
7190
    case OPC_CMP_SF_D:
7191
    case OPC_CMP_NGLE_D:
7192
    case OPC_CMP_SEQ_D:
7193
    case OPC_CMP_NGL_D:
7194
    case OPC_CMP_LT_D:
7195
    case OPC_CMP_NGE_D:
7196
    case OPC_CMP_LE_D:
7197
    case OPC_CMP_NGT_D:
7198
        if (ctx->opcode & (1 << 6)) {
7199
            gen_cmpabs_d(ctx, func-48, ft, fs, cc);
7200
            opn = condnames_abs[func-48];
7201
        } else {
7202
            gen_cmp_d(ctx, func-48, ft, fs, cc);
7203
            opn = condnames[func-48];
7204
        }
7205
        break;
7206
    case OPC_CVT_S_D:
7207
        check_cp1_registers(ctx, fs);
7208
        {
7209
            TCGv_i32 fp32 = tcg_temp_new_i32();
7210
            TCGv_i64 fp64 = tcg_temp_new_i64();
7211

    
7212
            gen_load_fpr64(ctx, fp64, fs);
7213
            gen_helper_float_cvts_d(fp32, fp64);
7214
            tcg_temp_free_i64(fp64);
7215
            gen_store_fpr32(fp32, fd);
7216
            tcg_temp_free_i32(fp32);
7217
        }
7218
        opn = "cvt.s.d";
7219
        break;
7220
    case OPC_CVT_W_D:
7221
        check_cp1_registers(ctx, fs);
7222
        {
7223
            TCGv_i32 fp32 = tcg_temp_new_i32();
7224
            TCGv_i64 fp64 = tcg_temp_new_i64();
7225

    
7226
            gen_load_fpr64(ctx, fp64, fs);
7227
            gen_helper_float_cvtw_d(fp32, fp64);
7228
            tcg_temp_free_i64(fp64);
7229
            gen_store_fpr32(fp32, fd);
7230
            tcg_temp_free_i32(fp32);
7231
        }
7232
        opn = "cvt.w.d";
7233
        break;
7234
    case OPC_CVT_L_D:
7235
        check_cp1_64bitmode(ctx);
7236
        {
7237
            TCGv_i64 fp0 = tcg_temp_new_i64();
7238

    
7239
            gen_load_fpr64(ctx, fp0, fs);
7240
            gen_helper_float_cvtl_d(fp0, fp0);
7241
            gen_store_fpr64(ctx, fp0, fd);
7242
            tcg_temp_free_i64(fp0);
7243
        }
7244
        opn = "cvt.l.d";
7245
        break;
7246
    case OPC_CVT_S_W:
7247
        {
7248
            TCGv_i32 fp0 = tcg_temp_new_i32();
7249

    
7250
            gen_load_fpr32(fp0, fs);
7251
            gen_helper_float_cvts_w(fp0, fp0);
7252
            gen_store_fpr32(fp0, fd);
7253
            tcg_temp_free_i32(fp0);
7254
        }
7255
        opn = "cvt.s.w";
7256
        break;
7257
    case OPC_CVT_D_W:
7258
        check_cp1_registers(ctx, fd);
7259
        {
7260
            TCGv_i32 fp32 = tcg_temp_new_i32();
7261
            TCGv_i64 fp64 = tcg_temp_new_i64();
7262

    
7263
            gen_load_fpr32(fp32, fs);
7264
            gen_helper_float_cvtd_w(fp64, fp32);
7265
            tcg_temp_free_i32(fp32);
7266
            gen_store_fpr64(ctx, fp64, fd);
7267
            tcg_temp_free_i64(fp64);
7268
        }
7269
        opn = "cvt.d.w";
7270
        break;
7271
    case OPC_CVT_S_L:
7272
        check_cp1_64bitmode(ctx);
7273
        {
7274
            TCGv_i32 fp32 = tcg_temp_new_i32();
7275
            TCGv_i64 fp64 = tcg_temp_new_i64();
7276

    
7277
            gen_load_fpr64(ctx, fp64, fs);
7278
            gen_helper_float_cvts_l(fp32, fp64);
7279
            tcg_temp_free_i64(fp64);
7280
            gen_store_fpr32(fp32, fd);
7281
            tcg_temp_free_i32(fp32);
7282
        }
7283
        opn = "cvt.s.l";
7284
        break;
7285
    case OPC_CVT_D_L:
7286
        check_cp1_64bitmode(ctx);
7287
        {
7288
            TCGv_i64 fp0 = tcg_temp_new_i64();
7289

    
7290
            gen_load_fpr64(ctx, fp0, fs);
7291
            gen_helper_float_cvtd_l(fp0, fp0);
7292
            gen_store_fpr64(ctx, fp0, fd);
7293
            tcg_temp_free_i64(fp0);
7294
        }
7295
        opn = "cvt.d.l";
7296
        break;
7297
    case OPC_CVT_PS_PW:
7298
        check_cp1_64bitmode(ctx);
7299
        {
7300
            TCGv_i64 fp0 = tcg_temp_new_i64();
7301

    
7302
            gen_load_fpr64(ctx, fp0, fs);
7303
            gen_helper_float_cvtps_pw(fp0, fp0);
7304
            gen_store_fpr64(ctx, fp0, fd);
7305
            tcg_temp_free_i64(fp0);
7306
        }
7307
        opn = "cvt.ps.pw";
7308
        break;
7309
    case OPC_ADD_PS:
7310
        check_cp1_64bitmode(ctx);
7311
        {
7312
            TCGv_i64 fp0 = tcg_temp_new_i64();
7313
            TCGv_i64 fp1 = tcg_temp_new_i64();
7314

    
7315
            gen_load_fpr64(ctx, fp0, fs);
7316
            gen_load_fpr64(ctx, fp1, ft);
7317
            gen_helper_float_add_ps(fp0, fp0, fp1);
7318
            tcg_temp_free_i64(fp1);
7319
            gen_store_fpr64(ctx, fp0, fd);
7320
            tcg_temp_free_i64(fp0);
7321
        }
7322
        opn = "add.ps";
7323
        break;
7324
    case OPC_SUB_PS:
7325
        check_cp1_64bitmode(ctx);
7326
        {
7327
            TCGv_i64 fp0 = tcg_temp_new_i64();
7328
            TCGv_i64 fp1 = tcg_temp_new_i64();
7329

    
7330
            gen_load_fpr64(ctx, fp0, fs);
7331
            gen_load_fpr64(ctx, fp1, ft);
7332
            gen_helper_float_sub_ps(fp0, fp0, fp1);
7333
            tcg_temp_free_i64(fp1);
7334
            gen_store_fpr64(ctx, fp0, fd);
7335
            tcg_temp_free_i64(fp0);
7336
        }
7337
        opn = "sub.ps";
7338
        break;
7339
    case OPC_MUL_PS:
7340
        check_cp1_64bitmode(ctx);
7341
        {
7342
            TCGv_i64 fp0 = tcg_temp_new_i64();
7343
            TCGv_i64 fp1 = tcg_temp_new_i64();
7344

    
7345
            gen_load_fpr64(ctx, fp0, fs);
7346
            gen_load_fpr64(ctx, fp1, ft);
7347
            gen_helper_float_mul_ps(fp0, fp0, fp1);
7348
            tcg_temp_free_i64(fp1);
7349
            gen_store_fpr64(ctx, fp0, fd);
7350
            tcg_temp_free_i64(fp0);
7351
        }
7352
        opn = "mul.ps";
7353
        break;
7354
    case OPC_ABS_PS:
7355
        check_cp1_64bitmode(ctx);
7356
        {
7357
            TCGv_i64 fp0 = tcg_temp_new_i64();
7358

    
7359
            gen_load_fpr64(ctx, fp0, fs);
7360
            gen_helper_float_abs_ps(fp0, fp0);
7361
            gen_store_fpr64(ctx, fp0, fd);
7362
            tcg_temp_free_i64(fp0);
7363
        }
7364
        opn = "abs.ps";
7365
        break;
7366
    case OPC_MOV_PS:
7367
        check_cp1_64bitmode(ctx);
7368
        {
7369
            TCGv_i64 fp0 = tcg_temp_new_i64();
7370

    
7371
            gen_load_fpr64(ctx, fp0, fs);
7372
            gen_store_fpr64(ctx, fp0, fd);
7373
            tcg_temp_free_i64(fp0);
7374
        }
7375
        opn = "mov.ps";
7376
        break;
7377
    case OPC_NEG_PS:
7378
        check_cp1_64bitmode(ctx);
7379
        {
7380
            TCGv_i64 fp0 = tcg_temp_new_i64();
7381

    
7382
            gen_load_fpr64(ctx, fp0, fs);
7383
            gen_helper_float_chs_ps(fp0, fp0);
7384
            gen_store_fpr64(ctx, fp0, fd);
7385
            tcg_temp_free_i64(fp0);
7386
        }
7387
        opn = "neg.ps";
7388
        break;
7389
    case OPC_MOVCF_PS:
7390
        check_cp1_64bitmode(ctx);
7391
        gen_movcf_ps(fs, fd, (ft >> 2) & 0x7, ft & 0x1);
7392
        opn = "movcf.ps";
7393
        break;
7394
    case OPC_MOVZ_PS:
7395
        check_cp1_64bitmode(ctx);
7396
        {
7397
            int l1 = gen_new_label();
7398
            TCGv_i64 fp0;
7399

    
7400
            if (ft != 0)
7401
                tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
7402
            fp0 = tcg_temp_new_i64();
7403
            gen_load_fpr64(ctx, fp0, fs);
7404
            gen_store_fpr64(ctx, fp0, fd);
7405
            tcg_temp_free_i64(fp0);
7406
            gen_set_label(l1);
7407
        }
7408
        opn = "movz.ps";
7409
        break;
7410
    case OPC_MOVN_PS:
7411
        check_cp1_64bitmode(ctx);
7412
        {
7413
            int l1 = gen_new_label();
7414
            TCGv_i64 fp0;
7415

    
7416
            if (ft != 0) {
7417
                tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
7418
                fp0 = tcg_temp_new_i64();
7419
                gen_load_fpr64(ctx, fp0, fs);
7420
                gen_store_fpr64(ctx, fp0, fd);
7421
                tcg_temp_free_i64(fp0);
7422
                gen_set_label(l1);
7423
            }
7424
        }
7425
        opn = "movn.ps";
7426
        break;
7427
    case OPC_ADDR_PS:
7428
        check_cp1_64bitmode(ctx);
7429
        {
7430
            TCGv_i64 fp0 = tcg_temp_new_i64();
7431
            TCGv_i64 fp1 = tcg_temp_new_i64();
7432

    
7433
            gen_load_fpr64(ctx, fp0, ft);
7434
            gen_load_fpr64(ctx, fp1, fs);
7435
            gen_helper_float_addr_ps(fp0, fp0, fp1);
7436
            tcg_temp_free_i64(fp1);
7437
            gen_store_fpr64(ctx, fp0, fd);
7438
            tcg_temp_free_i64(fp0);
7439
        }
7440
        opn = "addr.ps";
7441
        break;
7442
    case OPC_MULR_PS:
7443
        check_cp1_64bitmode(ctx);
7444
        {
7445
            TCGv_i64 fp0 = tcg_temp_new_i64();
7446
            TCGv_i64 fp1 = tcg_temp_new_i64();
7447

    
7448
            gen_load_fpr64(ctx, fp0, ft);
7449
            gen_load_fpr64(ctx, fp1, fs);
7450
            gen_helper_float_mulr_ps(fp0, fp0, fp1);
7451
            tcg_temp_free_i64(fp1);
7452
            gen_store_fpr64(ctx, fp0, fd);
7453
            tcg_temp_free_i64(fp0);
7454
        }
7455
        opn = "mulr.ps";
7456
        break;
7457
    case OPC_RECIP2_PS:
7458
        check_cp1_64bitmode(ctx);
7459
        {
7460
            TCGv_i64 fp0 = tcg_temp_new_i64();
7461
            TCGv_i64 fp1 = tcg_temp_new_i64();
7462

    
7463
            gen_load_fpr64(ctx, fp0, fs);
7464
            gen_load_fpr64(ctx, fp1, fd);
7465
            gen_helper_float_recip2_ps(fp0, fp0, fp1);
7466
            tcg_temp_free_i64(fp1);
7467
            gen_store_fpr64(ctx, fp0, fd);
7468
            tcg_temp_free_i64(fp0);
7469
        }
7470
        opn = "recip2.ps";
7471
        break;
7472
    case OPC_RECIP1_PS:
7473
        check_cp1_64bitmode(ctx);
7474
        {
7475
            TCGv_i64 fp0 = tcg_temp_new_i64();
7476

    
7477
            gen_load_fpr64(ctx, fp0, fs);
7478
            gen_helper_float_recip1_ps(fp0, fp0);
7479
            gen_store_fpr64(ctx, fp0, fd);
7480
            tcg_temp_free_i64(fp0);
7481
        }
7482
        opn = "recip1.ps";
7483
        break;
7484
    case OPC_RSQRT1_PS:
7485
        check_cp1_64bitmode(ctx);
7486
        {
7487
            TCGv_i64 fp0 = tcg_temp_new_i64();
7488

    
7489
            gen_load_fpr64(ctx, fp0, fs);
7490
            gen_helper_float_rsqrt1_ps(fp0, fp0);
7491
            gen_store_fpr64(ctx, fp0, fd);
7492
            tcg_temp_free_i64(fp0);
7493
        }
7494
        opn = "rsqrt1.ps";
7495
        break;
7496
    case OPC_RSQRT2_PS:
7497
        check_cp1_64bitmode(ctx);
7498
        {
7499
            TCGv_i64 fp0 = tcg_temp_new_i64();
7500
            TCGv_i64 fp1 = tcg_temp_new_i64();
7501

    
7502
            gen_load_fpr64(ctx, fp0, fs);
7503
            gen_load_fpr64(ctx, fp1, ft);
7504
            gen_helper_float_rsqrt2_ps(fp0, fp0, fp1);
7505
            tcg_temp_free_i64(fp1);
7506
            gen_store_fpr64(ctx, fp0, fd);
7507
            tcg_temp_free_i64(fp0);
7508
        }
7509
        opn = "rsqrt2.ps";
7510
        break;
7511
    case OPC_CVT_S_PU:
7512
        check_cp1_64bitmode(ctx);
7513
        {
7514
            TCGv_i32 fp0 = tcg_temp_new_i32();
7515

    
7516
            gen_load_fpr32h(fp0, fs);
7517
            gen_helper_float_cvts_pu(fp0, fp0);
7518
            gen_store_fpr32(fp0, fd);
7519
            tcg_temp_free_i32(fp0);
7520
        }
7521
        opn = "cvt.s.pu";
7522
        break;
7523
    case OPC_CVT_PW_PS:
7524
        check_cp1_64bitmode(ctx);
7525
        {
7526
            TCGv_i64 fp0 = tcg_temp_new_i64();
7527

    
7528
            gen_load_fpr64(ctx, fp0, fs);
7529
            gen_helper_float_cvtpw_ps(fp0, fp0);
7530
            gen_store_fpr64(ctx, fp0, fd);
7531
            tcg_temp_free_i64(fp0);
7532
        }
7533
        opn = "cvt.pw.ps";
7534
        break;
7535
    case OPC_CVT_S_PL:
7536
        check_cp1_64bitmode(ctx);
7537
        {
7538
            TCGv_i32 fp0 = tcg_temp_new_i32();
7539

    
7540
            gen_load_fpr32(fp0, fs);
7541
            gen_helper_float_cvts_pl(fp0, fp0);
7542
            gen_store_fpr32(fp0, fd);
7543
            tcg_temp_free_i32(fp0);
7544
        }
7545
        opn = "cvt.s.pl";
7546
        break;
7547
    case OPC_PLL_PS:
7548
        check_cp1_64bitmode(ctx);
7549
        {
7550
            TCGv_i32 fp0 = tcg_temp_new_i32();
7551
            TCGv_i32 fp1 = tcg_temp_new_i32();
7552

    
7553
            gen_load_fpr32(fp0, fs);
7554
            gen_load_fpr32(fp1, ft);
7555
            gen_store_fpr32h(fp0, fd);
7556
            gen_store_fpr32(fp1, fd);
7557
            tcg_temp_free_i32(fp0);
7558
            tcg_temp_free_i32(fp1);
7559
        }
7560
        opn = "pll.ps";
7561
        break;
7562
    case OPC_PLU_PS:
7563
        check_cp1_64bitmode(ctx);
7564
        {
7565
            TCGv_i32 fp0 = tcg_temp_new_i32();
7566
            TCGv_i32 fp1 = tcg_temp_new_i32();
7567

    
7568
            gen_load_fpr32(fp0, fs);
7569
            gen_load_fpr32h(fp1, ft);
7570
            gen_store_fpr32(fp1, fd);
7571
            gen_store_fpr32h(fp0, fd);
7572
            tcg_temp_free_i32(fp0);
7573
            tcg_temp_free_i32(fp1);
7574
        }
7575
        opn = "plu.ps";
7576
        break;
7577
    case OPC_PUL_PS:
7578
        check_cp1_64bitmode(ctx);
7579
        {
7580
            TCGv_i32 fp0 = tcg_temp_new_i32();
7581
            TCGv_i32 fp1 = tcg_temp_new_i32();
7582

    
7583
            gen_load_fpr32h(fp0, fs);
7584
            gen_load_fpr32(fp1, ft);
7585
            gen_store_fpr32(fp1, fd);
7586
            gen_store_fpr32h(fp0, fd);
7587
            tcg_temp_free_i32(fp0);
7588
            tcg_temp_free_i32(fp1);
7589
        }
7590
        opn = "pul.ps";
7591
        break;
7592
    case OPC_PUU_PS:
7593
        check_cp1_64bitmode(ctx);
7594
        {
7595
            TCGv_i32 fp0 = tcg_temp_new_i32();
7596
            TCGv_i32 fp1 = tcg_temp_new_i32();
7597

    
7598
            gen_load_fpr32h(fp0, fs);
7599
            gen_load_fpr32h(fp1, ft);
7600
            gen_store_fpr32(fp1, fd);
7601
            gen_store_fpr32h(fp0, fd);
7602
            tcg_temp_free_i32(fp0);
7603
            tcg_temp_free_i32(fp1);
7604
        }
7605
        opn = "puu.ps";
7606
        break;
7607
    case OPC_CMP_F_PS:
7608
    case OPC_CMP_UN_PS:
7609
    case OPC_CMP_EQ_PS:
7610
    case OPC_CMP_UEQ_PS:
7611
    case OPC_CMP_OLT_PS:
7612
    case OPC_CMP_ULT_PS:
7613
    case OPC_CMP_OLE_PS:
7614
    case OPC_CMP_ULE_PS:
7615
    case OPC_CMP_SF_PS:
7616
    case OPC_CMP_NGLE_PS:
7617
    case OPC_CMP_SEQ_PS:
7618
    case OPC_CMP_NGL_PS:
7619
    case OPC_CMP_LT_PS:
7620
    case OPC_CMP_NGE_PS:
7621
    case OPC_CMP_LE_PS:
7622
    case OPC_CMP_NGT_PS:
7623
        if (ctx->opcode & (1 << 6)) {
7624
            gen_cmpabs_ps(ctx, func-48, ft, fs, cc);
7625
            opn = condnames_abs[func-48];
7626
        } else {
7627
            gen_cmp_ps(ctx, func-48, ft, fs, cc);
7628
            opn = condnames[func-48];
7629
        }
7630
        break;
7631
    default:
7632
        MIPS_INVAL(opn);
7633
        generate_exception (ctx, EXCP_RI);
7634
        return;
7635
    }
7636
    (void)opn; /* avoid a compiler warning */
7637
    switch (optype) {
7638
    case BINOP:
7639
        MIPS_DEBUG("%s %s, %s, %s", opn, fregnames[fd], fregnames[fs], fregnames[ft]);
7640
        break;
7641
    case CMPOP:
7642
        MIPS_DEBUG("%s %s,%s", opn, fregnames[fs], fregnames[ft]);
7643
        break;
7644
    default:
7645
        MIPS_DEBUG("%s %s,%s", opn, fregnames[fd], fregnames[fs]);
7646
        break;
7647
    }
7648
}
7649

    
7650
/* Coprocessor 3 (FPU) */
7651
static void gen_flt3_ldst (DisasContext *ctx, uint32_t opc,
7652
                           int fd, int fs, int base, int index)
7653
{
7654
    const char *opn = "extended float load/store";
7655
    int store = 0;
7656
    TCGv t0 = tcg_temp_new();
7657

    
7658
    if (base == 0) {
7659
        gen_load_gpr(t0, index);
7660
    } else if (index == 0) {
7661
        gen_load_gpr(t0, base);
7662
    } else {
7663
        gen_load_gpr(t0, index);
7664
        gen_op_addr_add(ctx, t0, cpu_gpr[base], t0);
7665
    }
7666
    /* Don't do NOP if destination is zero: we must perform the actual
7667
       memory access. */
7668
    save_cpu_state(ctx, 0);
7669
    switch (opc) {
7670
    case OPC_LWXC1:
7671
        check_cop1x(ctx);
7672
        {
7673
            TCGv_i32 fp0 = tcg_temp_new_i32();
7674

    
7675
            tcg_gen_qemu_ld32s(t0, t0, ctx->mem_idx);
7676
            tcg_gen_trunc_tl_i32(fp0, t0);
7677
            gen_store_fpr32(fp0, fd);
7678
            tcg_temp_free_i32(fp0);
7679
        }
7680
        opn = "lwxc1";
7681
        break;
7682
    case OPC_LDXC1:
7683
        check_cop1x(ctx);
7684
        check_cp1_registers(ctx, fd);
7685
        {
7686
            TCGv_i64 fp0 = tcg_temp_new_i64();
7687

    
7688
            tcg_gen_qemu_ld64(fp0, t0, ctx->mem_idx);
7689
            gen_store_fpr64(ctx, fp0, fd);
7690
            tcg_temp_free_i64(fp0);
7691
        }
7692
        opn = "ldxc1";
7693
        break;
7694
    case OPC_LUXC1:
7695
        check_cp1_64bitmode(ctx);
7696
        tcg_gen_andi_tl(t0, t0, ~0x7);
7697
        {
7698
            TCGv_i64 fp0 = tcg_temp_new_i64();
7699

    
7700
            tcg_gen_qemu_ld64(fp0, t0, ctx->mem_idx);
7701
            gen_store_fpr64(ctx, fp0, fd);
7702
            tcg_temp_free_i64(fp0);
7703
        }
7704
        opn = "luxc1";
7705
        break;
7706
    case OPC_SWXC1:
7707
        check_cop1x(ctx);
7708
        {
7709
            TCGv_i32 fp0 = tcg_temp_new_i32();
7710
            TCGv t1 = tcg_temp_new();
7711

    
7712
            gen_load_fpr32(fp0, fs);
7713
            tcg_gen_extu_i32_tl(t1, fp0);
7714
            tcg_gen_qemu_st32(t1, t0, ctx->mem_idx);
7715
            tcg_temp_free_i32(fp0);
7716
            tcg_temp_free(t1);
7717
        }
7718
        opn = "swxc1";
7719
        store = 1;
7720
        break;
7721
    case OPC_SDXC1:
7722
        check_cop1x(ctx);
7723
        check_cp1_registers(ctx, fs);
7724
        {
7725
            TCGv_i64 fp0 = tcg_temp_new_i64();
7726

    
7727
            gen_load_fpr64(ctx, fp0, fs);
7728
            tcg_gen_qemu_st64(fp0, t0, ctx->mem_idx);
7729
            tcg_temp_free_i64(fp0);
7730
        }
7731
        opn = "sdxc1";
7732
        store = 1;
7733
        break;
7734
    case OPC_SUXC1:
7735
        check_cp1_64bitmode(ctx);
7736
        tcg_gen_andi_tl(t0, t0, ~0x7);
7737
        {
7738
            TCGv_i64 fp0 = tcg_temp_new_i64();
7739

    
7740
            gen_load_fpr64(ctx, fp0, fs);
7741
            tcg_gen_qemu_st64(fp0, t0, ctx->mem_idx);
7742
            tcg_temp_free_i64(fp0);
7743
        }
7744
        opn = "suxc1";
7745
        store = 1;
7746
        break;
7747
    }
7748
    tcg_temp_free(t0);
7749
    (void)opn; (void)store; /* avoid compiler warnings */
7750
    MIPS_DEBUG("%s %s, %s(%s)", opn, fregnames[store ? fs : fd],
7751
               regnames[index], regnames[base]);
7752
}
7753

    
7754
static void gen_flt3_arith (DisasContext *ctx, uint32_t opc,
7755
                            int fd, int fr, int fs, int ft)
7756
{
7757
    const char *opn = "flt3_arith";
7758

    
7759
    switch (opc) {
7760
    case OPC_ALNV_PS:
7761
        check_cp1_64bitmode(ctx);
7762
        {
7763
            TCGv t0 = tcg_temp_local_new();
7764
            TCGv_i32 fp = tcg_temp_new_i32();
7765
            TCGv_i32 fph = tcg_temp_new_i32();
7766
            int l1 = gen_new_label();
7767
            int l2 = gen_new_label();
7768

    
7769
            gen_load_gpr(t0, fr);
7770
            tcg_gen_andi_tl(t0, t0, 0x7);
7771

    
7772
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
7773
            gen_load_fpr32(fp, fs);
7774
            gen_load_fpr32h(fph, fs);
7775
            gen_store_fpr32(fp, fd);
7776
            gen_store_fpr32h(fph, fd);
7777
            tcg_gen_br(l2);
7778
            gen_set_label(l1);
7779
            tcg_gen_brcondi_tl(TCG_COND_NE, t0, 4, l2);
7780
            tcg_temp_free(t0);
7781
#ifdef TARGET_WORDS_BIGENDIAN
7782
            gen_load_fpr32(fp, fs);
7783
            gen_load_fpr32h(fph, ft);
7784
            gen_store_fpr32h(fp, fd);
7785
            gen_store_fpr32(fph, fd);
7786
#else
7787
            gen_load_fpr32h(fph, fs);
7788
            gen_load_fpr32(fp, ft);
7789
            gen_store_fpr32(fph, fd);
7790
            gen_store_fpr32h(fp, fd);
7791
#endif
7792
            gen_set_label(l2);
7793
            tcg_temp_free_i32(fp);
7794
            tcg_temp_free_i32(fph);
7795
        }
7796
        opn = "alnv.ps";
7797
        break;
7798
    case OPC_MADD_S:
7799
        check_cop1x(ctx);
7800
        {
7801
            TCGv_i32 fp0 = tcg_temp_new_i32();
7802
            TCGv_i32 fp1 = tcg_temp_new_i32();
7803
            TCGv_i32 fp2 = tcg_temp_new_i32();
7804

    
7805
            gen_load_fpr32(fp0, fs);
7806
            gen_load_fpr32(fp1, ft);
7807
            gen_load_fpr32(fp2, fr);
7808
            gen_helper_float_muladd_s(fp2, fp0, fp1, fp2);
7809
            tcg_temp_free_i32(fp0);
7810
            tcg_temp_free_i32(fp1);
7811
            gen_store_fpr32(fp2, fd);
7812
            tcg_temp_free_i32(fp2);
7813
        }
7814
        opn = "madd.s";
7815
        break;
7816
    case OPC_MADD_D:
7817
        check_cop1x(ctx);
7818
        check_cp1_registers(ctx, fd | fs | ft | fr);
7819
        {
7820
            TCGv_i64 fp0 = tcg_temp_new_i64();
7821
            TCGv_i64 fp1 = tcg_temp_new_i64();
7822
            TCGv_i64 fp2 = tcg_temp_new_i64();
7823

    
7824
            gen_load_fpr64(ctx, fp0, fs);
7825
            gen_load_fpr64(ctx, fp1, ft);
7826
            gen_load_fpr64(ctx, fp2, fr);
7827
            gen_helper_float_muladd_d(fp2, fp0, fp1, fp2);
7828
            tcg_temp_free_i64(fp0);
7829
            tcg_temp_free_i64(fp1);
7830
            gen_store_fpr64(ctx, fp2, fd);
7831
            tcg_temp_free_i64(fp2);
7832
        }
7833
        opn = "madd.d";
7834
        break;
7835
    case OPC_MADD_PS:
7836
        check_cp1_64bitmode(ctx);
7837
        {
7838
            TCGv_i64 fp0 = tcg_temp_new_i64();
7839
            TCGv_i64 fp1 = tcg_temp_new_i64();
7840
            TCGv_i64 fp2 = tcg_temp_new_i64();
7841

    
7842
            gen_load_fpr64(ctx, fp0, fs);
7843
            gen_load_fpr64(ctx, fp1, ft);
7844
            gen_load_fpr64(ctx, fp2, fr);
7845
            gen_helper_float_muladd_ps(fp2, fp0, fp1, fp2);
7846
            tcg_temp_free_i64(fp0);
7847
            tcg_temp_free_i64(fp1);
7848
            gen_store_fpr64(ctx, fp2, fd);
7849
            tcg_temp_free_i64(fp2);
7850
        }
7851
        opn = "madd.ps";
7852
        break;
7853
    case OPC_MSUB_S:
7854
        check_cop1x(ctx);
7855
        {
7856
            TCGv_i32 fp0 = tcg_temp_new_i32();
7857
            TCGv_i32 fp1 = tcg_temp_new_i32();
7858
            TCGv_i32 fp2 = tcg_temp_new_i32();
7859

    
7860
            gen_load_fpr32(fp0, fs);
7861
            gen_load_fpr32(fp1, ft);
7862
            gen_load_fpr32(fp2, fr);
7863
            gen_helper_float_mulsub_s(fp2, fp0, fp1, fp2);
7864
            tcg_temp_free_i32(fp0);
7865
            tcg_temp_free_i32(fp1);
7866
            gen_store_fpr32(fp2, fd);
7867
            tcg_temp_free_i32(fp2);
7868
        }
7869
        opn = "msub.s";
7870
        break;
7871
    case OPC_MSUB_D:
7872
        check_cop1x(ctx);
7873
        check_cp1_registers(ctx, fd | fs | ft | fr);
7874
        {
7875
            TCGv_i64 fp0 = tcg_temp_new_i64();
7876
            TCGv_i64 fp1 = tcg_temp_new_i64();
7877
            TCGv_i64 fp2 = tcg_temp_new_i64();
7878

    
7879
            gen_load_fpr64(ctx, fp0, fs);
7880
            gen_load_fpr64(ctx, fp1, ft);
7881
            gen_load_fpr64(ctx, fp2, fr);
7882
            gen_helper_float_mulsub_d(fp2, fp0, fp1, fp2);
7883
            tcg_temp_free_i64(fp0);
7884
            tcg_temp_free_i64(fp1);
7885
            gen_store_fpr64(ctx, fp2, fd);
7886
            tcg_temp_free_i64(fp2);
7887
        }
7888
        opn = "msub.d";
7889
        break;
7890
    case OPC_MSUB_PS:
7891
        check_cp1_64bitmode(ctx);
7892
        {
7893
            TCGv_i64 fp0 = tcg_temp_new_i64();
7894
            TCGv_i64 fp1 = tcg_temp_new_i64();
7895
            TCGv_i64 fp2 = tcg_temp_new_i64();
7896

    
7897
            gen_load_fpr64(ctx, fp0, fs);
7898
            gen_load_fpr64(ctx, fp1, ft);
7899
            gen_load_fpr64(ctx, fp2, fr);
7900
            gen_helper_float_mulsub_ps(fp2, fp0, fp1, fp2);
7901
            tcg_temp_free_i64(fp0);
7902
            tcg_temp_free_i64(fp1);
7903
            gen_store_fpr64(ctx, fp2, fd);
7904
            tcg_temp_free_i64(fp2);
7905
        }
7906
        opn = "msub.ps";
7907
        break;
7908
    case OPC_NMADD_S:
7909
        check_cop1x(ctx);
7910
        {
7911
            TCGv_i32 fp0 = tcg_temp_new_i32();
7912
            TCGv_i32 fp1 = tcg_temp_new_i32();
7913
            TCGv_i32 fp2 = tcg_temp_new_i32();
7914

    
7915
            gen_load_fpr32(fp0, fs);
7916
            gen_load_fpr32(fp1, ft);
7917
            gen_load_fpr32(fp2, fr);
7918
            gen_helper_float_nmuladd_s(fp2, fp0, fp1, fp2);
7919
            tcg_temp_free_i32(fp0);
7920
            tcg_temp_free_i32(fp1);
7921
            gen_store_fpr32(fp2, fd);
7922
            tcg_temp_free_i32(fp2);
7923
        }
7924
        opn = "nmadd.s";
7925
        break;
7926
    case OPC_NMADD_D:
7927
        check_cop1x(ctx);
7928
        check_cp1_registers(ctx, fd | fs | ft | fr);
7929
        {
7930
            TCGv_i64 fp0 = tcg_temp_new_i64();
7931
            TCGv_i64 fp1 = tcg_temp_new_i64();
7932
            TCGv_i64 fp2 = tcg_temp_new_i64();
7933

    
7934
            gen_load_fpr64(ctx, fp0, fs);
7935
            gen_load_fpr64(ctx, fp1, ft);
7936
            gen_load_fpr64(ctx, fp2, fr);
7937
            gen_helper_float_nmuladd_d(fp2, fp0, fp1, fp2);
7938
            tcg_temp_free_i64(fp0);
7939
            tcg_temp_free_i64(fp1);
7940
            gen_store_fpr64(ctx, fp2, fd);
7941
            tcg_temp_free_i64(fp2);
7942
        }
7943
        opn = "nmadd.d";
7944
        break;
7945
    case OPC_NMADD_PS:
7946
        check_cp1_64bitmode(ctx);
7947
        {
7948
            TCGv_i64 fp0 = tcg_temp_new_i64();
7949
            TCGv_i64 fp1 = tcg_temp_new_i64();
7950
            TCGv_i64 fp2 = tcg_temp_new_i64();
7951

    
7952
            gen_load_fpr64(ctx, fp0, fs);
7953
            gen_load_fpr64(ctx, fp1, ft);
7954
            gen_load_fpr64(ctx, fp2, fr);
7955
            gen_helper_float_nmuladd_ps(fp2, fp0, fp1, fp2);
7956
            tcg_temp_free_i64(fp0);
7957
            tcg_temp_free_i64(fp1);
7958
            gen_store_fpr64(ctx, fp2, fd);
7959
            tcg_temp_free_i64(fp2);
7960
        }
7961
        opn = "nmadd.ps";
7962
        break;
7963
    case OPC_NMSUB_S:
7964
        check_cop1x(ctx);
7965
        {
7966
            TCGv_i32 fp0 = tcg_temp_new_i32();
7967
            TCGv_i32 fp1 = tcg_temp_new_i32();
7968
            TCGv_i32 fp2 = tcg_temp_new_i32();
7969

    
7970
            gen_load_fpr32(fp0, fs);
7971
            gen_load_fpr32(fp1, ft);
7972
            gen_load_fpr32(fp2, fr);
7973
            gen_helper_float_nmulsub_s(fp2, fp0, fp1, fp2);
7974
            tcg_temp_free_i32(fp0);
7975
            tcg_temp_free_i32(fp1);
7976
            gen_store_fpr32(fp2, fd);
7977
            tcg_temp_free_i32(fp2);
7978
        }
7979
        opn = "nmsub.s";
7980
        break;
7981
    case OPC_NMSUB_D:
7982
        check_cop1x(ctx);
7983
        check_cp1_registers(ctx, fd | fs | ft | fr);
7984
        {
7985
            TCGv_i64 fp0 = tcg_temp_new_i64();
7986
            TCGv_i64 fp1 = tcg_temp_new_i64();
7987
            TCGv_i64 fp2 = tcg_temp_new_i64();
7988

    
7989
            gen_load_fpr64(ctx, fp0, fs);
7990
            gen_load_fpr64(ctx, fp1, ft);
7991
            gen_load_fpr64(ctx, fp2, fr);
7992
            gen_helper_float_nmulsub_d(fp2, fp0, fp1, fp2);
7993
            tcg_temp_free_i64(fp0);
7994
            tcg_temp_free_i64(fp1);
7995
            gen_store_fpr64(ctx, fp2, fd);
7996
            tcg_temp_free_i64(fp2);
7997
        }
7998
        opn = "nmsub.d";
7999
        break;
8000
    case OPC_NMSUB_PS:
8001
        check_cp1_64bitmode(ctx);
8002
        {
8003
            TCGv_i64 fp0 = tcg_temp_new_i64();
8004
            TCGv_i64 fp1 = tcg_temp_new_i64();
8005
            TCGv_i64 fp2 = tcg_temp_new_i64();
8006

    
8007
            gen_load_fpr64(ctx, fp0, fs);
8008
            gen_load_fpr64(ctx, fp1, ft);
8009
            gen_load_fpr64(ctx, fp2, fr);
8010
            gen_helper_float_nmulsub_ps(fp2, fp0, fp1, fp2);
8011
            tcg_temp_free_i64(fp0);
8012
            tcg_temp_free_i64(fp1);
8013
            gen_store_fpr64(ctx, fp2, fd);
8014
            tcg_temp_free_i64(fp2);
8015
        }
8016
        opn = "nmsub.ps";
8017
        break;
8018
    default:
8019
        MIPS_INVAL(opn);
8020
        generate_exception (ctx, EXCP_RI);
8021
        return;
8022
    }
8023
    (void)opn; /* avoid a compiler warning */
8024
    MIPS_DEBUG("%s %s, %s, %s, %s", opn, fregnames[fd], fregnames[fr],
8025
               fregnames[fs], fregnames[ft]);
8026
}
8027

    
8028
static void
8029
gen_rdhwr (CPUState *env, DisasContext *ctx, int rt, int rd)
8030
{
8031
    TCGv t0;
8032

    
8033
    check_insn(env, ctx, ISA_MIPS32R2);
8034
    t0 = tcg_temp_new();
8035

    
8036
    switch (rd) {
8037
    case 0:
8038
        save_cpu_state(ctx, 1);
8039
        gen_helper_rdhwr_cpunum(t0);
8040
        gen_store_gpr(t0, rt);
8041
        break;
8042
    case 1:
8043
        save_cpu_state(ctx, 1);
8044
        gen_helper_rdhwr_synci_step(t0);
8045
        gen_store_gpr(t0, rt);
8046
        break;
8047
    case 2:
8048
        save_cpu_state(ctx, 1);
8049
        gen_helper_rdhwr_cc(t0);
8050
        gen_store_gpr(t0, rt);
8051
        break;
8052
    case 3:
8053
        save_cpu_state(ctx, 1);
8054
        gen_helper_rdhwr_ccres(t0);
8055
        gen_store_gpr(t0, rt);
8056
        break;
8057
    case 29:
8058
#if defined(CONFIG_USER_ONLY)
8059
        tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, tls_value));
8060
        gen_store_gpr(t0, rt);
8061
        break;
8062
#else
8063
        /* XXX: Some CPUs implement this in hardware.
8064
           Not supported yet. */
8065
#endif
8066
    default:            /* Invalid */
8067
        MIPS_INVAL("rdhwr");
8068
        generate_exception(ctx, EXCP_RI);
8069
        break;
8070
    }
8071
    tcg_temp_free(t0);
8072
}
8073

    
8074
static void handle_delay_slot (CPUState *env, DisasContext *ctx,
8075
                               int insn_bytes)
8076
{
8077
    if (ctx->hflags & MIPS_HFLAG_BMASK) {
8078
        int proc_hflags = ctx->hflags & MIPS_HFLAG_BMASK;
8079
        /* Branches completion */
8080
        ctx->hflags &= ~MIPS_HFLAG_BMASK;
8081
        ctx->bstate = BS_BRANCH;
8082
        save_cpu_state(ctx, 0);
8083
        /* FIXME: Need to clear can_do_io.  */
8084
        switch (proc_hflags & MIPS_HFLAG_BMASK_BASE) {
8085
        case MIPS_HFLAG_B:
8086
            /* unconditional branch */
8087
            MIPS_DEBUG("unconditional branch");
8088
            if (proc_hflags & MIPS_HFLAG_BX) {
8089
                tcg_gen_xori_i32(hflags, hflags, MIPS_HFLAG_M16);
8090
            }
8091
            gen_goto_tb(ctx, 0, ctx->btarget);
8092
            break;
8093
        case MIPS_HFLAG_BL:
8094
            /* blikely taken case */
8095
            MIPS_DEBUG("blikely branch taken");
8096
            gen_goto_tb(ctx, 0, ctx->btarget);
8097
            break;
8098
        case MIPS_HFLAG_BC:
8099
            /* Conditional branch */
8100
            MIPS_DEBUG("conditional branch");
8101
            {
8102
                int l1 = gen_new_label();
8103

    
8104
                tcg_gen_brcondi_tl(TCG_COND_NE, bcond, 0, l1);
8105
                gen_goto_tb(ctx, 1, ctx->pc + insn_bytes);
8106
                gen_set_label(l1);
8107
                gen_goto_tb(ctx, 0, ctx->btarget);
8108
            }
8109
            break;
8110
        case MIPS_HFLAG_BR:
8111
            /* unconditional branch to register */
8112
            MIPS_DEBUG("branch to register");
8113
            if (env->insn_flags & (ASE_MIPS16 | ASE_MICROMIPS)) {
8114
                TCGv t0 = tcg_temp_new();
8115
                TCGv_i32 t1 = tcg_temp_new_i32();
8116

    
8117
                tcg_gen_andi_tl(t0, btarget, 0x1);
8118
                tcg_gen_trunc_tl_i32(t1, t0);
8119
                tcg_temp_free(t0);
8120
                tcg_gen_andi_i32(hflags, hflags, ~(uint32_t)MIPS_HFLAG_M16);
8121
                tcg_gen_shli_i32(t1, t1, MIPS_HFLAG_M16_SHIFT);
8122
                tcg_gen_or_i32(hflags, hflags, t1);
8123
                tcg_temp_free_i32(t1);
8124

    
8125
                tcg_gen_andi_tl(cpu_PC, btarget, ~(target_ulong)0x1);
8126
            } else {
8127
                tcg_gen_mov_tl(cpu_PC, btarget);
8128
            }
8129
            if (ctx->singlestep_enabled) {
8130
                save_cpu_state(ctx, 0);
8131
                gen_helper_0i(raise_exception, EXCP_DEBUG);
8132
            }
8133
            tcg_gen_exit_tb(0);
8134
            break;
8135
        default:
8136
            MIPS_DEBUG("unknown branch");
8137
            break;
8138
        }
8139
    }
8140
}
8141

    
8142
/* ISA extensions (ASEs) */
8143
/* MIPS16 extension to MIPS32 */
8144

    
8145
/* MIPS16 major opcodes */
8146
enum {
8147
  M16_OPC_ADDIUSP = 0x00,
8148
  M16_OPC_ADDIUPC = 0x01,
8149
  M16_OPC_B = 0x02,
8150
  M16_OPC_JAL = 0x03,
8151
  M16_OPC_BEQZ = 0x04,
8152
  M16_OPC_BNEQZ = 0x05,
8153
  M16_OPC_SHIFT = 0x06,
8154
  M16_OPC_LD = 0x07,
8155
  M16_OPC_RRIA = 0x08,
8156
  M16_OPC_ADDIU8 = 0x09,
8157
  M16_OPC_SLTI = 0x0a,
8158
  M16_OPC_SLTIU = 0x0b,
8159
  M16_OPC_I8 = 0x0c,
8160
  M16_OPC_LI = 0x0d,
8161
  M16_OPC_CMPI = 0x0e,
8162
  M16_OPC_SD = 0x0f,
8163
  M16_OPC_LB = 0x10,
8164
  M16_OPC_LH = 0x11,
8165
  M16_OPC_LWSP = 0x12,
8166
  M16_OPC_LW = 0x13,
8167
  M16_OPC_LBU = 0x14,
8168
  M16_OPC_LHU = 0x15,
8169
  M16_OPC_LWPC = 0x16,
8170
  M16_OPC_LWU = 0x17,
8171
  M16_OPC_SB = 0x18,
8172
  M16_OPC_SH = 0x19,
8173
  M16_OPC_SWSP = 0x1a,
8174
  M16_OPC_SW = 0x1b,
8175
  M16_OPC_RRR = 0x1c,
8176
  M16_OPC_RR = 0x1d,
8177
  M16_OPC_EXTEND = 0x1e,
8178
  M16_OPC_I64 = 0x1f
8179
};
8180

    
8181
/* I8 funct field */
8182
enum {
8183
  I8_BTEQZ = 0x0,
8184
  I8_BTNEZ = 0x1,
8185
  I8_SWRASP = 0x2,
8186
  I8_ADJSP = 0x3,
8187
  I8_SVRS = 0x4,
8188
  I8_MOV32R = 0x5,
8189
  I8_MOVR32 = 0x7
8190
};
8191

    
8192
/* RRR f field */
8193
enum {
8194
  RRR_DADDU = 0x0,
8195
  RRR_ADDU = 0x1,
8196
  RRR_DSUBU = 0x2,
8197
  RRR_SUBU = 0x3
8198
};
8199

    
8200
/* RR funct field */
8201
enum {
8202
  RR_JR = 0x00,
8203
  RR_SDBBP = 0x01,
8204
  RR_SLT = 0x02,
8205
  RR_SLTU = 0x03,
8206
  RR_SLLV = 0x04,
8207
  RR_BREAK = 0x05,
8208
  RR_SRLV = 0x06,
8209
  RR_SRAV = 0x07,
8210
  RR_DSRL = 0x08,
8211
  RR_CMP = 0x0a,
8212
  RR_NEG = 0x0b,
8213
  RR_AND = 0x0c,
8214
  RR_OR = 0x0d,
8215
  RR_XOR = 0x0e,
8216
  RR_NOT = 0x0f,
8217
  RR_MFHI = 0x10,
8218
  RR_CNVT = 0x11,
8219
  RR_MFLO = 0x12,
8220
  RR_DSRA = 0x13,
8221
  RR_DSLLV = 0x14,
8222
  RR_DSRLV = 0x16,
8223
  RR_DSRAV = 0x17,
8224
  RR_MULT = 0x18,
8225
  RR_MULTU = 0x19,
8226
  RR_DIV = 0x1a,
8227
  RR_DIVU = 0x1b,
8228
  RR_DMULT = 0x1c,
8229
  RR_DMULTU = 0x1d,
8230
  RR_DDIV = 0x1e,
8231
  RR_DDIVU = 0x1f
8232
};
8233

    
8234
/* I64 funct field */
8235
enum {
8236
  I64_LDSP = 0x0,
8237
  I64_SDSP = 0x1,
8238
  I64_SDRASP = 0x2,
8239
  I64_DADJSP = 0x3,
8240
  I64_LDPC = 0x4,
8241
  I64_DADDIU5 = 0x5,
8242
  I64_DADDIUPC = 0x6,
8243
  I64_DADDIUSP = 0x7
8244
};
8245

    
8246
/* RR ry field for CNVT */
8247
enum {
8248
  RR_RY_CNVT_ZEB = 0x0,
8249
  RR_RY_CNVT_ZEH = 0x1,
8250
  RR_RY_CNVT_ZEW = 0x2,
8251
  RR_RY_CNVT_SEB = 0x4,
8252
  RR_RY_CNVT_SEH = 0x5,
8253
  RR_RY_CNVT_SEW = 0x6,
8254
};
8255

    
8256
static int xlat (int r)
8257
{
8258
  static int map[] = { 16, 17, 2, 3, 4, 5, 6, 7 };
8259

    
8260
  return map[r];
8261
}
8262

    
8263
static void gen_mips16_save (DisasContext *ctx,
8264
                             int xsregs, int aregs,
8265
                             int do_ra, int do_s0, int do_s1,
8266
                             int framesize)
8267
{
8268
    TCGv t0 = tcg_temp_new();
8269
    TCGv t1 = tcg_temp_new();
8270
    int args, astatic;
8271

    
8272
    switch (aregs) {
8273
    case 0:
8274
    case 1:
8275
    case 2:
8276
    case 3:
8277
    case 11:
8278
        args = 0;
8279
        break;
8280
    case 4:
8281
    case 5:
8282
    case 6:
8283
    case 7:
8284
        args = 1;
8285
        break;
8286
    case 8:
8287
    case 9:
8288
    case 10:
8289
        args = 2;
8290
        break;
8291
    case 12:
8292
    case 13:
8293
        args = 3;
8294
        break;
8295
    case 14:
8296
        args = 4;
8297
        break;
8298
    default:
8299
        generate_exception(ctx, EXCP_RI);
8300
        return;
8301
    }
8302

    
8303
    switch (args) {
8304
    case 4:
8305
        gen_base_offset_addr(ctx, t0, 29, 12);
8306
        gen_load_gpr(t1, 7);
8307
        op_st_sw(t1, t0, ctx);
8308
        /* Fall through */
8309
    case 3:
8310
        gen_base_offset_addr(ctx, t0, 29, 8);
8311
        gen_load_gpr(t1, 6);
8312
        op_st_sw(t1, t0, ctx);
8313
        /* Fall through */
8314
    case 2:
8315
        gen_base_offset_addr(ctx, t0, 29, 4);
8316
        gen_load_gpr(t1, 5);
8317
        op_st_sw(t1, t0, ctx);
8318
        /* Fall through */
8319
    case 1:
8320
        gen_base_offset_addr(ctx, t0, 29, 0);
8321
        gen_load_gpr(t1, 4);
8322
        op_st_sw(t1, t0, ctx);
8323
    }
8324

    
8325
    gen_load_gpr(t0, 29);
8326

    
8327
#define DECR_AND_STORE(reg) do {                \
8328
        tcg_gen_subi_tl(t0, t0, 4);             \
8329
        gen_load_gpr(t1, reg);                  \
8330
        op_st_sw(t1, t0, ctx);                  \
8331
    } while (0)
8332

    
8333
    if (do_ra) {
8334
        DECR_AND_STORE(31);
8335
    }
8336

    
8337
    switch (xsregs) {
8338
    case 7:
8339
        DECR_AND_STORE(30);
8340
        /* Fall through */
8341
    case 6:
8342
        DECR_AND_STORE(23);
8343
        /* Fall through */
8344
    case 5:
8345
        DECR_AND_STORE(22);
8346
        /* Fall through */
8347
    case 4:
8348
        DECR_AND_STORE(21);
8349
        /* Fall through */
8350
    case 3:
8351
        DECR_AND_STORE(20);
8352
        /* Fall through */
8353
    case 2:
8354
        DECR_AND_STORE(19);
8355
        /* Fall through */
8356
    case 1:
8357
        DECR_AND_STORE(18);
8358
    }
8359

    
8360
    if (do_s1) {
8361
        DECR_AND_STORE(17);
8362
    }
8363
    if (do_s0) {
8364
        DECR_AND_STORE(16);
8365
    }
8366

    
8367
    switch (aregs) {
8368
    case 0:
8369
    case 4:
8370
    case 8:
8371
    case 12:
8372
    case 14:
8373
        astatic = 0;
8374
        break;
8375
    case 1:
8376
    case 5:
8377
    case 9:
8378
    case 13:
8379
        astatic = 1;
8380
        break;
8381
    case 2:
8382
    case 6:
8383
    case 10:
8384
        astatic = 2;
8385
        break;
8386
    case 3:
8387
    case 7:
8388
        astatic = 3;
8389
        break;
8390
    case 11:
8391
        astatic = 4;
8392
        break;
8393
    default:
8394
        generate_exception(ctx, EXCP_RI);
8395
        return;
8396
    }
8397

    
8398
    if (astatic > 0) {
8399
        DECR_AND_STORE(7);
8400
        if (astatic > 1) {
8401
            DECR_AND_STORE(6);
8402
            if (astatic > 2) {
8403
                DECR_AND_STORE(5);
8404
                if (astatic > 3) {
8405
                    DECR_AND_STORE(4);
8406
                }
8407
            }
8408
        }
8409
    }
8410
#undef DECR_AND_STORE
8411

    
8412
    tcg_gen_subi_tl(cpu_gpr[29], cpu_gpr[29], framesize);
8413
    tcg_temp_free(t0);
8414
    tcg_temp_free(t1);
8415
}
8416

    
8417
static void gen_mips16_restore (DisasContext *ctx,
8418
                                int xsregs, int aregs,
8419
                                int do_ra, int do_s0, int do_s1,
8420
                                int framesize)
8421
{
8422
    int astatic;
8423
    TCGv t0 = tcg_temp_new();
8424
    TCGv t1 = tcg_temp_new();
8425

    
8426
    tcg_gen_addi_tl(t0, cpu_gpr[29], framesize);
8427

    
8428
#define DECR_AND_LOAD(reg) do {                 \
8429
        tcg_gen_subi_tl(t0, t0, 4);             \
8430
        op_ld_lw(t1, t0, ctx);                  \
8431
        gen_store_gpr(t1, reg);                 \
8432
    } while (0)
8433

    
8434
    if (do_ra) {
8435
        DECR_AND_LOAD(31);
8436
    }
8437

    
8438
    switch (xsregs) {
8439
    case 7:
8440
        DECR_AND_LOAD(30);
8441
        /* Fall through */
8442
    case 6:
8443
        DECR_AND_LOAD(23);
8444
        /* Fall through */
8445
    case 5:
8446
        DECR_AND_LOAD(22);
8447
        /* Fall through */
8448
    case 4:
8449
        DECR_AND_LOAD(21);
8450
        /* Fall through */
8451
    case 3:
8452
        DECR_AND_LOAD(20);
8453
        /* Fall through */
8454
    case 2:
8455
        DECR_AND_LOAD(19);
8456
        /* Fall through */
8457
    case 1:
8458
        DECR_AND_LOAD(18);
8459
    }
8460

    
8461
    if (do_s1) {
8462
        DECR_AND_LOAD(17);
8463
    }
8464
    if (do_s0) {
8465
        DECR_AND_LOAD(16);
8466
    }
8467

    
8468
    switch (aregs) {
8469
    case 0:
8470
    case 4:
8471
    case 8:
8472
    case 12:
8473
    case 14:
8474
        astatic = 0;
8475
        break;
8476
    case 1:
8477
    case 5:
8478
    case 9:
8479
    case 13:
8480
        astatic = 1;
8481
        break;
8482
    case 2:
8483
    case 6:
8484
    case 10:
8485
        astatic = 2;
8486
        break;
8487
    case 3:
8488
    case 7:
8489
        astatic = 3;
8490
        break;
8491
    case 11:
8492
        astatic = 4;
8493
        break;
8494
    default:
8495
        generate_exception(ctx, EXCP_RI);
8496
        return;
8497
    }
8498

    
8499
    if (astatic > 0) {
8500
        DECR_AND_LOAD(7);
8501
        if (astatic > 1) {
8502
            DECR_AND_LOAD(6);
8503
            if (astatic > 2) {
8504
                DECR_AND_LOAD(5);
8505
                if (astatic > 3) {
8506
                    DECR_AND_LOAD(4);
8507
                }
8508
            }
8509
        }
8510
    }
8511
#undef DECR_AND_LOAD
8512

    
8513
    tcg_gen_addi_tl(cpu_gpr[29], cpu_gpr[29], framesize);
8514
    tcg_temp_free(t0);
8515
    tcg_temp_free(t1);
8516
}
8517

    
8518
static void gen_addiupc (DisasContext *ctx, int rx, int imm,
8519
                         int is_64_bit, int extended)
8520
{
8521
    TCGv t0;
8522

    
8523
    if (extended && (ctx->hflags & MIPS_HFLAG_BMASK)) {
8524
        generate_exception(ctx, EXCP_RI);
8525
        return;
8526
    }
8527

    
8528
    t0 = tcg_temp_new();
8529

    
8530
    tcg_gen_movi_tl(t0, pc_relative_pc(ctx));
8531
    tcg_gen_addi_tl(cpu_gpr[rx], t0, imm);
8532
    if (!is_64_bit) {
8533
        tcg_gen_ext32s_tl(cpu_gpr[rx], cpu_gpr[rx]);
8534
    }
8535

    
8536
    tcg_temp_free(t0);
8537
}
8538

    
8539
#if defined(TARGET_MIPS64)
8540
static void decode_i64_mips16 (CPUState *env, DisasContext *ctx,
8541
                               int ry, int funct, int16_t offset,
8542
                               int extended)
8543
{
8544
    switch (funct) {
8545
    case I64_LDSP:
8546
        check_mips_64(ctx);
8547
        offset = extended ? offset : offset << 3;
8548
        gen_ld(env, ctx, OPC_LD, ry, 29, offset);
8549
        break;
8550
    case I64_SDSP:
8551
        check_mips_64(ctx);
8552
        offset = extended ? offset : offset << 3;
8553
        gen_st(ctx, OPC_SD, ry, 29, offset);
8554
        break;
8555
    case I64_SDRASP:
8556
        check_mips_64(ctx);
8557
        offset = extended ? offset : (ctx->opcode & 0xff) << 3;
8558
        gen_st(ctx, OPC_SD, 31, 29, offset);
8559
        break;
8560
    case I64_DADJSP:
8561
        check_mips_64(ctx);
8562
        offset = extended ? offset : ((int8_t)ctx->opcode) << 3;
8563
        gen_arith_imm(env, ctx, OPC_DADDIU, 29, 29, offset);
8564
        break;
8565
    case I64_LDPC:
8566
        if (extended && (ctx->hflags & MIPS_HFLAG_BMASK)) {
8567
            generate_exception(ctx, EXCP_RI);
8568
        } else {
8569
            offset = extended ? offset : offset << 3;
8570
            gen_ld(env, ctx, OPC_LDPC, ry, 0, offset);
8571
        }
8572
        break;
8573
    case I64_DADDIU5:
8574
        check_mips_64(ctx);
8575
        offset = extended ? offset : ((int8_t)(offset << 3)) >> 3;
8576
        gen_arith_imm(env, ctx, OPC_DADDIU, ry, ry, offset);
8577
        break;
8578
    case I64_DADDIUPC:
8579
        check_mips_64(ctx);
8580
        offset = extended ? offset : offset << 2;
8581
        gen_addiupc(ctx, ry, offset, 1, extended);
8582
        break;
8583
    case I64_DADDIUSP:
8584
        check_mips_64(ctx);
8585
        offset = extended ? offset : offset << 2;
8586
        gen_arith_imm(env, ctx, OPC_DADDIU, ry, 29, offset);
8587
        break;
8588
    }
8589
}
8590
#endif
8591

    
8592
static int decode_extended_mips16_opc (CPUState *env, DisasContext *ctx,
8593
                                       int *is_branch)
8594
{
8595
    int extend = lduw_code(ctx->pc + 2);
8596
    int op, rx, ry, funct, sa;
8597
    int16_t imm, offset;
8598

    
8599
    ctx->opcode = (ctx->opcode << 16) | extend;
8600
    op = (ctx->opcode >> 11) & 0x1f;
8601
    sa = (ctx->opcode >> 22) & 0x1f;
8602
    funct = (ctx->opcode >> 8) & 0x7;
8603
    rx = xlat((ctx->opcode >> 8) & 0x7);
8604
    ry = xlat((ctx->opcode >> 5) & 0x7);
8605
    offset = imm = (int16_t) (((ctx->opcode >> 16) & 0x1f) << 11
8606
                              | ((ctx->opcode >> 21) & 0x3f) << 5
8607
                              | (ctx->opcode & 0x1f));
8608

    
8609
    /* The extended opcodes cleverly reuse the opcodes from their 16-bit
8610
       counterparts.  */
8611
    switch (op) {
8612
    case M16_OPC_ADDIUSP:
8613
        gen_arith_imm(env, ctx, OPC_ADDIU, rx, 29, imm);
8614
        break;
8615
    case M16_OPC_ADDIUPC:
8616
        gen_addiupc(ctx, rx, imm, 0, 1);
8617
        break;
8618
    case M16_OPC_B:
8619
        gen_compute_branch(ctx, OPC_BEQ, 4, 0, 0, offset << 1);
8620
        /* No delay slot, so just process as a normal instruction */
8621
        break;
8622
    case M16_OPC_BEQZ:
8623
        gen_compute_branch(ctx, OPC_BEQ, 4, rx, 0, offset << 1);
8624
        /* No delay slot, so just process as a normal instruction */
8625
        break;
8626
    case M16_OPC_BNEQZ:
8627
        gen_compute_branch(ctx, OPC_BNE, 4, rx, 0, offset << 1);
8628
        /* No delay slot, so just process as a normal instruction */
8629
        break;
8630
    case M16_OPC_SHIFT:
8631
        switch (ctx->opcode & 0x3) {
8632
        case 0x0:
8633
            gen_shift_imm(env, ctx, OPC_SLL, rx, ry, sa);
8634
            break;
8635
        case 0x1:
8636
#if defined(TARGET_MIPS64)
8637
            check_mips_64(ctx);
8638
            gen_shift_imm(env, ctx, OPC_DSLL, rx, ry, sa);
8639
#else
8640
            generate_exception(ctx, EXCP_RI);
8641
#endif
8642
            break;
8643
        case 0x2:
8644
            gen_shift_imm(env, ctx, OPC_SRL, rx, ry, sa);
8645
            break;
8646
        case 0x3:
8647
            gen_shift_imm(env, ctx, OPC_SRA, rx, ry, sa);
8648
            break;
8649
        }
8650
        break;
8651
#if defined(TARGET_MIPS64)
8652
    case M16_OPC_LD:
8653
            check_mips_64(ctx);
8654
        gen_ld(env, ctx, OPC_LD, ry, rx, offset);
8655
        break;
8656
#endif
8657
    case M16_OPC_RRIA:
8658
        imm = ctx->opcode & 0xf;
8659
        imm = imm | ((ctx->opcode >> 20) & 0x7f) << 4;
8660
        imm = imm | ((ctx->opcode >> 16) & 0xf) << 11;
8661
        imm = (int16_t) (imm << 1) >> 1;
8662
        if ((ctx->opcode >> 4) & 0x1) {
8663
#if defined(TARGET_MIPS64)
8664
            check_mips_64(ctx);
8665
            gen_arith_imm(env, ctx, OPC_DADDIU, ry, rx, imm);
8666
#else
8667
            generate_exception(ctx, EXCP_RI);
8668
#endif
8669
        } else {
8670
            gen_arith_imm(env, ctx, OPC_ADDIU, ry, rx, imm);
8671
        }
8672
        break;
8673
    case M16_OPC_ADDIU8:
8674
        gen_arith_imm(env, ctx, OPC_ADDIU, rx, rx, imm);
8675
        break;
8676
    case M16_OPC_SLTI:
8677
        gen_slt_imm(env, OPC_SLTI, 24, rx, imm);
8678
        break;
8679
    case M16_OPC_SLTIU:
8680
        gen_slt_imm(env, OPC_SLTIU, 24, rx, imm);
8681
        break;
8682
    case M16_OPC_I8:
8683
        switch (funct) {
8684
        case I8_BTEQZ:
8685
            gen_compute_branch(ctx, OPC_BEQ, 4, 24, 0, offset << 1);
8686
            break;
8687
        case I8_BTNEZ:
8688
            gen_compute_branch(ctx, OPC_BNE, 4, 24, 0, offset << 1);
8689
            break;
8690
        case I8_SWRASP:
8691
            gen_st(ctx, OPC_SW, 31, 29, imm);
8692
            break;
8693
        case I8_ADJSP:
8694
            gen_arith_imm(env, ctx, OPC_ADDIU, 29, 29, imm);
8695
            break;
8696
        case I8_SVRS:
8697
            {
8698
                int xsregs = (ctx->opcode >> 24) & 0x7;
8699
                int aregs = (ctx->opcode >> 16) & 0xf;
8700
                int do_ra = (ctx->opcode >> 6) & 0x1;
8701
                int do_s0 = (ctx->opcode >> 5) & 0x1;
8702
                int do_s1 = (ctx->opcode >> 4) & 0x1;
8703
                int framesize = (((ctx->opcode >> 20) & 0xf) << 4
8704
                                 | (ctx->opcode & 0xf)) << 3;
8705

    
8706
                if (ctx->opcode & (1 << 7)) {
8707
                    gen_mips16_save(ctx, xsregs, aregs,
8708
                                    do_ra, do_s0, do_s1,
8709
                                    framesize);
8710
                } else {
8711
                    gen_mips16_restore(ctx, xsregs, aregs,
8712
                                       do_ra, do_s0, do_s1,
8713
                                       framesize);
8714
                }
8715
            }
8716
            break;
8717
        default:
8718
            generate_exception(ctx, EXCP_RI);
8719
            break;
8720
        }
8721
        break;
8722
    case M16_OPC_LI:
8723
        tcg_gen_movi_tl(cpu_gpr[rx], (uint16_t) imm);
8724
        break;
8725
    case M16_OPC_CMPI:
8726
        tcg_gen_xori_tl(cpu_gpr[24], cpu_gpr[rx], (uint16_t) imm);
8727
        break;
8728
#if defined(TARGET_MIPS64)
8729
    case M16_OPC_SD:
8730
        gen_st(ctx, OPC_SD, ry, rx, offset);
8731
        break;
8732
#endif
8733
    case M16_OPC_LB:
8734
        gen_ld(env, ctx, OPC_LB, ry, rx, offset);
8735
        break;
8736
    case M16_OPC_LH:
8737
        gen_ld(env, ctx, OPC_LH, ry, rx, offset);
8738
        break;
8739
    case M16_OPC_LWSP:
8740
        gen_ld(env, ctx, OPC_LW, rx, 29, offset);
8741
        break;
8742
    case M16_OPC_LW:
8743
        gen_ld(env, ctx, OPC_LW, ry, rx, offset);
8744
        break;
8745
    case M16_OPC_LBU:
8746
        gen_ld(env, ctx, OPC_LBU, ry, rx, offset);
8747
        break;
8748
    case M16_OPC_LHU:
8749
        gen_ld(env, ctx, OPC_LHU, ry, rx, offset);
8750
        break;
8751
    case M16_OPC_LWPC:
8752
        gen_ld(env, ctx, OPC_LWPC, rx, 0, offset);
8753
        break;
8754
#if defined(TARGET_MIPS64)
8755
    case M16_OPC_LWU:
8756
        gen_ld(env, ctx, OPC_LWU, ry, rx, offset);
8757
        break;
8758
#endif
8759
    case M16_OPC_SB:
8760
        gen_st(ctx, OPC_SB, ry, rx, offset);
8761
        break;
8762
    case M16_OPC_SH:
8763
        gen_st(ctx, OPC_SH, ry, rx, offset);
8764
        break;
8765
    case M16_OPC_SWSP:
8766
        gen_st(ctx, OPC_SW, rx, 29, offset);
8767
        break;
8768
    case M16_OPC_SW:
8769
        gen_st(ctx, OPC_SW, ry, rx, offset);
8770
        break;
8771
#if defined(TARGET_MIPS64)
8772
    case M16_OPC_I64:
8773
        decode_i64_mips16(env, ctx, ry, funct, offset, 1);
8774
        break;
8775
#endif
8776
    default:
8777
        generate_exception(ctx, EXCP_RI);
8778
        break;
8779
    }
8780

    
8781
    return 4;
8782
}
8783

    
8784
static int decode_mips16_opc (CPUState *env, DisasContext *ctx,
8785
                              int *is_branch)
8786
{
8787
    int rx, ry;
8788
    int sa;
8789
    int op, cnvt_op, op1, offset;
8790
    int funct;
8791
    int n_bytes;
8792

    
8793
    op = (ctx->opcode >> 11) & 0x1f;
8794
    sa = (ctx->opcode >> 2) & 0x7;
8795
    sa = sa == 0 ? 8 : sa;
8796
    rx = xlat((ctx->opcode >> 8) & 0x7);
8797
    cnvt_op = (ctx->opcode >> 5) & 0x7;
8798
    ry = xlat((ctx->opcode >> 5) & 0x7);
8799
    op1 = offset = ctx->opcode & 0x1f;
8800

    
8801
    n_bytes = 2;
8802

    
8803
    switch (op) {
8804
    case M16_OPC_ADDIUSP:
8805
        {
8806
            int16_t imm = ((uint8_t) ctx->opcode) << 2;
8807

    
8808
            gen_arith_imm(env, ctx, OPC_ADDIU, rx, 29, imm);
8809
        }
8810
        break;
8811
    case M16_OPC_ADDIUPC:
8812
        gen_addiupc(ctx, rx, ((uint8_t) ctx->opcode) << 2, 0, 0);
8813
        break;
8814
    case M16_OPC_B:
8815
        offset = (ctx->opcode & 0x7ff) << 1;
8816
        offset = (int16_t)(offset << 4) >> 4;
8817
        gen_compute_branch(ctx, OPC_BEQ, 2, 0, 0, offset);
8818
        /* No delay slot, so just process as a normal instruction */
8819
        break;
8820
    case M16_OPC_JAL:
8821
        offset = lduw_code(ctx->pc + 2);
8822
        offset = (((ctx->opcode & 0x1f) << 21)
8823
                  | ((ctx->opcode >> 5) & 0x1f) << 16
8824
                  | offset) << 2;
8825
        op = ((ctx->opcode >> 10) & 0x1) ? OPC_JALXS : OPC_JALS;
8826
        gen_compute_branch(ctx, op, 4, rx, ry, offset);
8827
        n_bytes = 4;
8828
        *is_branch = 1;
8829
        break;
8830
    case M16_OPC_BEQZ:
8831
        gen_compute_branch(ctx, OPC_BEQ, 2, rx, 0, ((int8_t)ctx->opcode) << 1);
8832
        /* No delay slot, so just process as a normal instruction */
8833
        break;
8834
    case M16_OPC_BNEQZ:
8835
        gen_compute_branch(ctx, OPC_BNE, 2, rx, 0, ((int8_t)ctx->opcode) << 1);
8836
        /* No delay slot, so just process as a normal instruction */
8837
        break;
8838
    case M16_OPC_SHIFT:
8839
        switch (ctx->opcode & 0x3) {
8840
        case 0x0:
8841
            gen_shift_imm(env, ctx, OPC_SLL, rx, ry, sa);
8842
            break;
8843
        case 0x1:
8844
#if defined(TARGET_MIPS64)
8845
            check_mips_64(ctx);
8846
            gen_shift_imm(env, ctx, OPC_DSLL, rx, ry, sa);
8847
#else
8848
            generate_exception(ctx, EXCP_RI);
8849
#endif
8850
            break;
8851
        case 0x2:
8852
            gen_shift_imm(env, ctx, OPC_SRL, rx, ry, sa);
8853
            break;
8854
        case 0x3:
8855
            gen_shift_imm(env, ctx, OPC_SRA, rx, ry, sa);
8856
            break;
8857
        }
8858
        break;
8859
#if defined(TARGET_MIPS64)
8860
    case M16_OPC_LD:
8861
        check_mips_64(ctx);
8862
        gen_ld(env, ctx, OPC_LD, ry, rx, offset << 3);
8863
        break;
8864
#endif
8865
    case M16_OPC_RRIA:
8866
        {
8867
            int16_t imm = (int8_t)((ctx->opcode & 0xf) << 4) >> 4;
8868

    
8869
            if ((ctx->opcode >> 4) & 1) {
8870
#if defined(TARGET_MIPS64)
8871
                check_mips_64(ctx);
8872
                gen_arith_imm(env, ctx, OPC_DADDIU, ry, rx, imm);
8873
#else
8874
                generate_exception(ctx, EXCP_RI);
8875
#endif
8876
            } else {
8877
                gen_arith_imm(env, ctx, OPC_ADDIU, ry, rx, imm);
8878
            }
8879
        }
8880
        break;
8881
    case M16_OPC_ADDIU8:
8882
        {
8883
            int16_t imm = (int8_t) ctx->opcode;
8884

    
8885
            gen_arith_imm(env, ctx, OPC_ADDIU, rx, rx, imm);
8886
        }
8887
        break;
8888
    case M16_OPC_SLTI:
8889
        {
8890
            int16_t imm = (uint8_t) ctx->opcode;
8891

    
8892
            gen_slt_imm(env, OPC_SLTI, 24, rx, imm);
8893
        }
8894
        break;
8895
    case M16_OPC_SLTIU:
8896
        {
8897
            int16_t imm = (uint8_t) ctx->opcode;
8898

    
8899
            gen_slt_imm(env, OPC_SLTIU, 24, rx, imm);
8900
        }
8901
        break;
8902
    case M16_OPC_I8:
8903
        {
8904
            int reg32;
8905

    
8906
            funct = (ctx->opcode >> 8) & 0x7;
8907
            switch (funct) {
8908
            case I8_BTEQZ:
8909
                gen_compute_branch(ctx, OPC_BEQ, 2, 24, 0,
8910
                                   ((int8_t)ctx->opcode) << 1);
8911
                break;
8912
            case I8_BTNEZ:
8913
                gen_compute_branch(ctx, OPC_BNE, 2, 24, 0,
8914
                                   ((int8_t)ctx->opcode) << 1);
8915
                break;
8916
            case I8_SWRASP:
8917
                gen_st(ctx, OPC_SW, 31, 29, (ctx->opcode & 0xff) << 2);
8918
                break;
8919
            case I8_ADJSP:
8920
                gen_arith_imm(env, ctx, OPC_ADDIU, 29, 29,
8921
                              ((int8_t)ctx->opcode) << 3);
8922
                break;
8923
            case I8_SVRS:
8924
                {
8925
                    int do_ra = ctx->opcode & (1 << 6);
8926
                    int do_s0 = ctx->opcode & (1 << 5);
8927
                    int do_s1 = ctx->opcode & (1 << 4);
8928
                    int framesize = ctx->opcode & 0xf;
8929

    
8930
                    if (framesize == 0) {
8931
                        framesize = 128;
8932
                    } else {
8933
                        framesize = framesize << 3;
8934
                    }
8935

    
8936
                    if (ctx->opcode & (1 << 7)) {
8937
                        gen_mips16_save(ctx, 0, 0,
8938
                                        do_ra, do_s0, do_s1, framesize);
8939
                    } else {
8940
                        gen_mips16_restore(ctx, 0, 0,
8941
                                           do_ra, do_s0, do_s1, framesize);
8942
                    }
8943
                }
8944
                break;
8945
            case I8_MOV32R:
8946
                {
8947
                    int rz = xlat(ctx->opcode & 0x7);
8948

    
8949
                    reg32 = (((ctx->opcode >> 3) & 0x3) << 3) |
8950
                        ((ctx->opcode >> 5) & 0x7);
8951
                    gen_arith(env, ctx, OPC_ADDU, reg32, rz, 0);
8952
                }
8953
                break;
8954
            case I8_MOVR32:
8955
                reg32 = ctx->opcode & 0x1f;
8956
                gen_arith(env, ctx, OPC_ADDU, ry, reg32, 0);
8957
                break;
8958
            default:
8959
                generate_exception(ctx, EXCP_RI);
8960
                break;
8961
            }
8962
        }
8963
        break;
8964
    case M16_OPC_LI:
8965
        {
8966
            int16_t imm = (uint8_t) ctx->opcode;
8967

    
8968
            gen_arith_imm(env, ctx, OPC_ADDIU, rx, 0, imm);
8969
        }
8970
        break;
8971
    case M16_OPC_CMPI:
8972
        {
8973
            int16_t imm = (uint8_t) ctx->opcode;
8974

    
8975
            gen_logic_imm(env, OPC_XORI, 24, rx, imm);
8976
        }
8977
        break;
8978
#if defined(TARGET_MIPS64)
8979
    case M16_OPC_SD:
8980
        check_mips_64(ctx);
8981
        gen_st(ctx, OPC_SD, ry, rx, offset << 3);
8982
        break;
8983
#endif
8984
    case M16_OPC_LB:
8985
        gen_ld(env, ctx, OPC_LB, ry, rx, offset);
8986
        break;
8987
    case M16_OPC_LH:
8988
        gen_ld(env, ctx, OPC_LH, ry, rx, offset << 1);
8989
        break;
8990
    case M16_OPC_LWSP:
8991
        gen_ld(env, ctx, OPC_LW, rx, 29, ((uint8_t)ctx->opcode) << 2);
8992
        break;
8993
    case M16_OPC_LW:
8994
        gen_ld(env, ctx, OPC_LW, ry, rx, offset << 2);
8995
        break;
8996
    case M16_OPC_LBU:
8997
        gen_ld(env, ctx, OPC_LBU, ry, rx, offset);
8998
        break;
8999
    case M16_OPC_LHU:
9000
        gen_ld(env, ctx, OPC_LHU, ry, rx, offset << 1);
9001
        break;
9002
    case M16_OPC_LWPC:
9003
        gen_ld(env, ctx, OPC_LWPC, rx, 0, ((uint8_t)ctx->opcode) << 2);
9004
        break;
9005
#if defined (TARGET_MIPS64)
9006
    case M16_OPC_LWU:
9007
        check_mips_64(ctx);
9008
        gen_ld(env, ctx, OPC_LWU, ry, rx, offset << 2);
9009
        break;
9010
#endif
9011
    case M16_OPC_SB:
9012
        gen_st(ctx, OPC_SB, ry, rx, offset);
9013
        break;
9014
    case M16_OPC_SH:
9015
        gen_st(ctx, OPC_SH, ry, rx, offset << 1);
9016
        break;
9017
    case M16_OPC_SWSP:
9018
        gen_st(ctx, OPC_SW, rx, 29, ((uint8_t)ctx->opcode) << 2);
9019
        break;
9020
    case M16_OPC_SW:
9021
        gen_st(ctx, OPC_SW, ry, rx, offset << 2);
9022
        break;
9023
    case M16_OPC_RRR:
9024
        {
9025
            int rz = xlat((ctx->opcode >> 2) & 0x7);
9026
            int mips32_op;
9027

    
9028
            switch (ctx->opcode & 0x3) {
9029
            case RRR_ADDU:
9030
                mips32_op = OPC_ADDU;
9031
                break;
9032
            case RRR_SUBU:
9033
                mips32_op = OPC_SUBU;
9034
                break;
9035
#if defined(TARGET_MIPS64)
9036
            case RRR_DADDU:
9037
                mips32_op = OPC_DADDU;
9038
                check_mips_64(ctx);
9039
                break;
9040
            case RRR_DSUBU:
9041
                mips32_op = OPC_DSUBU;
9042
                check_mips_64(ctx);
9043
                break;
9044
#endif
9045
            default:
9046
                generate_exception(ctx, EXCP_RI);
9047
                goto done;
9048
            }
9049

    
9050
            gen_arith(env, ctx, mips32_op, rz, rx, ry);
9051
        done:
9052
            ;
9053
        }
9054
        break;
9055
    case M16_OPC_RR:
9056
        switch (op1) {
9057
        case RR_JR:
9058
            {
9059
                int nd = (ctx->opcode >> 7) & 0x1;
9060
                int link = (ctx->opcode >> 6) & 0x1;
9061
                int ra = (ctx->opcode >> 5) & 0x1;
9062

    
9063
                if (link) {
9064
                    op = nd ? OPC_JALRC : OPC_JALRS;
9065
                } else {
9066
                    op = OPC_JR;
9067
                }
9068

    
9069
                gen_compute_branch(ctx, op, 2, ra ? 31 : rx, 31, 0);
9070
                if (!nd) {
9071
                    *is_branch = 1;
9072
                }
9073
            }
9074
            break;
9075
        case RR_SDBBP:
9076
            /* XXX: not clear which exception should be raised
9077
             *      when in debug mode...
9078
             */
9079
            check_insn(env, ctx, ISA_MIPS32);
9080
            if (!(ctx->hflags & MIPS_HFLAG_DM)) {
9081
                generate_exception(ctx, EXCP_DBp);
9082
            } else {
9083
                generate_exception(ctx, EXCP_DBp);
9084
            }
9085
            break;
9086
        case RR_SLT:
9087
            gen_slt(env, OPC_SLT, 24, rx, ry);
9088
            break;
9089
        case RR_SLTU:
9090
            gen_slt(env, OPC_SLTU, 24, rx, ry);
9091
            break;
9092
        case RR_BREAK:
9093
            generate_exception(ctx, EXCP_BREAK);
9094
            break;
9095
        case RR_SLLV:
9096
            gen_shift(env, ctx, OPC_SLLV, ry, rx, ry);
9097
            break;
9098
        case RR_SRLV:
9099
            gen_shift(env, ctx, OPC_SRLV, ry, rx, ry);
9100
            break;
9101
        case RR_SRAV:
9102
            gen_shift(env, ctx, OPC_SRAV, ry, rx, ry);
9103
            break;
9104
#if defined (TARGET_MIPS64)
9105
        case RR_DSRL:
9106
            check_mips_64(ctx);
9107
            gen_shift_imm(env, ctx, OPC_DSRL, ry, ry, sa);
9108
            break;
9109
#endif
9110
        case RR_CMP:
9111
            gen_logic(env, OPC_XOR, 24, rx, ry);
9112
            break;
9113
        case RR_NEG:
9114
            gen_arith(env, ctx, OPC_SUBU, rx, 0, ry);
9115
            break;
9116
        case RR_AND:
9117
            gen_logic(env, OPC_AND, rx, rx, ry);
9118
            break;
9119
        case RR_OR:
9120
            gen_logic(env, OPC_OR, rx, rx, ry);
9121
            break;
9122
        case RR_XOR:
9123
            gen_logic(env, OPC_XOR, rx, rx, ry);
9124
            break;
9125
        case RR_NOT:
9126
            gen_logic(env, OPC_NOR, rx, ry, 0);
9127
            break;
9128
        case RR_MFHI:
9129
            gen_HILO(ctx, OPC_MFHI, rx);
9130
            break;
9131
        case RR_CNVT:
9132
            switch (cnvt_op) {
9133
            case RR_RY_CNVT_ZEB:
9134
                tcg_gen_ext8u_tl(cpu_gpr[rx], cpu_gpr[rx]);
9135
                break;
9136
            case RR_RY_CNVT_ZEH:
9137
                tcg_gen_ext16u_tl(cpu_gpr[rx], cpu_gpr[rx]);
9138
                break;
9139
            case RR_RY_CNVT_SEB:
9140
                tcg_gen_ext8s_tl(cpu_gpr[rx], cpu_gpr[rx]);
9141
                break;
9142
            case RR_RY_CNVT_SEH:
9143
                tcg_gen_ext16s_tl(cpu_gpr[rx], cpu_gpr[rx]);
9144
                break;
9145
#if defined (TARGET_MIPS64)
9146
            case RR_RY_CNVT_ZEW:
9147
                check_mips_64(ctx);
9148
                tcg_gen_ext32u_tl(cpu_gpr[rx], cpu_gpr[rx]);
9149
                break;
9150
            case RR_RY_CNVT_SEW:
9151
                check_mips_64(ctx);
9152
                tcg_gen_ext32s_tl(cpu_gpr[rx], cpu_gpr[rx]);
9153
                break;
9154
#endif
9155
            default:
9156
                generate_exception(ctx, EXCP_RI);
9157
                break;
9158
            }
9159
            break;
9160
        case RR_MFLO:
9161
            gen_HILO(ctx, OPC_MFLO, rx);
9162
            break;
9163
#if defined (TARGET_MIPS64)
9164
        case RR_DSRA:
9165
            check_mips_64(ctx);
9166
            gen_shift_imm(env, ctx, OPC_DSRA, ry, ry, sa);
9167
            break;
9168
        case RR_DSLLV:
9169
            check_mips_64(ctx);
9170
            gen_shift(env, ctx, OPC_DSLLV, ry, rx, ry);
9171
            break;
9172
        case RR_DSRLV:
9173
            check_mips_64(ctx);
9174
            gen_shift(env, ctx, OPC_DSRLV, ry, rx, ry);
9175
            break;
9176
        case RR_DSRAV:
9177
            check_mips_64(ctx);
9178
            gen_shift(env, ctx, OPC_DSRAV, ry, rx, ry);
9179
            break;
9180
#endif
9181
        case RR_MULT:
9182
            gen_muldiv(ctx, OPC_MULT, rx, ry);
9183
            break;
9184
        case RR_MULTU:
9185
            gen_muldiv(ctx, OPC_MULTU, rx, ry);
9186
            break;
9187
        case RR_DIV:
9188
            gen_muldiv(ctx, OPC_DIV, rx, ry);
9189
            break;
9190
        case RR_DIVU:
9191
            gen_muldiv(ctx, OPC_DIVU, rx, ry);
9192
            break;
9193
#if defined (TARGET_MIPS64)
9194
        case RR_DMULT:
9195
            check_mips_64(ctx);
9196
            gen_muldiv(ctx, OPC_DMULT, rx, ry);
9197
            break;
9198
        case RR_DMULTU:
9199
            check_mips_64(ctx);
9200
            gen_muldiv(ctx, OPC_DMULTU, rx, ry);
9201
            break;
9202
        case RR_DDIV:
9203
            check_mips_64(ctx);
9204
            gen_muldiv(ctx, OPC_DDIV, rx, ry);
9205
            break;
9206
        case RR_DDIVU:
9207
            check_mips_64(ctx);
9208
            gen_muldiv(ctx, OPC_DDIVU, rx, ry);
9209
            break;
9210
#endif
9211
        default:
9212
            generate_exception(ctx, EXCP_RI);
9213
            break;
9214
        }
9215
        break;
9216
    case M16_OPC_EXTEND:
9217
        decode_extended_mips16_opc(env, ctx, is_branch);
9218
        n_bytes = 4;
9219
        break;
9220
#if defined(TARGET_MIPS64)
9221
    case M16_OPC_I64:
9222
        funct = (ctx->opcode >> 8) & 0x7;
9223
        decode_i64_mips16(env, ctx, ry, funct, offset, 0);
9224
        break;
9225
#endif
9226
    default:
9227
        generate_exception(ctx, EXCP_RI);
9228
        break;
9229
    }
9230

    
9231
    return n_bytes;
9232
}
9233

    
9234
/* microMIPS extension to MIPS32 */
9235

    
9236
/* microMIPS32 major opcodes */
9237

    
9238
enum {
9239
    POOL32A = 0x00,
9240
    POOL16A = 0x01,
9241
    LBU16 = 0x02,
9242
    MOVE16 = 0x03,
9243
    ADDI32 = 0x04,
9244
    LBU32 = 0x05,
9245
    SB32 = 0x06,
9246
    LB32 = 0x07,
9247

    
9248
    POOL32B = 0x08,
9249
    POOL16B = 0x09,
9250
    LHU16 = 0x0a,
9251
    ANDI16 = 0x0b,
9252
    ADDIU32 = 0x0c,
9253
    LHU32 = 0x0d,
9254
    SH32 = 0x0e,
9255
    LH32 = 0x0f,
9256

    
9257
    POOL32I = 0x10,
9258
    POOL16C = 0x11,
9259
    LWSP16 = 0x12,
9260
    POOL16D = 0x13,
9261
    ORI32 = 0x14,
9262
    POOL32F = 0x15,
9263
    POOL32S = 0x16,
9264
    DADDIU32 = 0x17,
9265

    
9266
    POOL32C = 0x18,
9267
    LWGP16 = 0x19,
9268
    LW16 = 0x1a,
9269
    POOL16E = 0x1b,
9270
    XORI32 = 0x1c,
9271
    JALS32 = 0x1d,
9272
    ADDIUPC = 0x1e,
9273
    POOL48A = 0x1f,
9274

    
9275
    /* 0x20 is reserved */
9276
    RES_20 = 0x20,
9277
    POOL16F = 0x21,
9278
    SB16 = 0x22,
9279
    BEQZ16 = 0x23,
9280
    SLTI32 = 0x24,
9281
    BEQ32 = 0x25,
9282
    SWC132 = 0x26,
9283
    LWC132 = 0x27,
9284

    
9285
    /* 0x28 and 0x29 are reserved */
9286
    RES_28 = 0x28,
9287
    RES_29 = 0x29,
9288
    SH16 = 0x2a,
9289
    BNEZ16 = 0x2b,
9290
    SLTIU32 = 0x2c,
9291
    BNE32 = 0x2d,
9292
    SDC132 = 0x2e,
9293
    LDC132 = 0x2f,
9294

    
9295
    /* 0x30 and 0x31 are reserved */
9296
    RES_30 = 0x30,
9297
    RES_31 = 0x31,
9298
    SWSP16 = 0x32,
9299
    B16 = 0x33,
9300
    ANDI32 = 0x34,
9301
    J32 = 0x35,
9302
    SD32 = 0x36,
9303
    LD32 = 0x37,
9304

    
9305
    /* 0x38 and 0x39 are reserved */
9306
    RES_38 = 0x38,
9307
    RES_39 = 0x39,
9308
    SW16 = 0x3a,
9309
    LI16 = 0x3b,
9310
    JALX32 = 0x3c,
9311
    JAL32 = 0x3d,
9312
    SW32 = 0x3e,
9313
    LW32 = 0x3f
9314
};
9315

    
9316
/* POOL32A encoding of minor opcode field */
9317

    
9318
enum {
9319
    /* These opcodes are distinguished only by bits 9..6; those bits are
9320
     * what are recorded below. */
9321
    SLL32 = 0x0,
9322
    SRL32 = 0x1,
9323
    SRA = 0x2,
9324
    ROTR = 0x3,
9325

    
9326
    SLLV = 0x0,
9327
    SRLV = 0x1,
9328
    SRAV = 0x2,
9329
    ROTRV = 0x3,
9330
    ADD = 0x4,
9331
    ADDU32 = 0x5,
9332
    SUB = 0x6,
9333
    SUBU32 = 0x7,
9334
    MUL = 0x8,
9335
    AND = 0x9,
9336
    OR32 = 0xa,
9337
    NOR = 0xb,
9338
    XOR32 = 0xc,
9339
    SLT = 0xd,
9340
    SLTU = 0xe,
9341

    
9342
    MOVN = 0x0,
9343
    MOVZ = 0x1,
9344
    LWXS = 0x4,
9345

    
9346
    /* The following can be distinguished by their lower 6 bits. */
9347
    INS = 0x0c,
9348
    EXT = 0x2c,
9349
    POOL32AXF = 0x3c
9350
};
9351

    
9352
/* POOL32AXF encoding of minor opcode field extension */
9353

    
9354
enum {
9355
    /* bits 11..6 */
9356
    TEQ = 0x00,
9357
    TGE = 0x08,
9358
    TGEU = 0x10,
9359
    TLT = 0x20,
9360
    TLTU = 0x28,
9361
    TNE = 0x30,
9362

    
9363
    MFC0 = 0x03,
9364
    MTC0 = 0x0b,
9365

    
9366
    /* bits 13..12 for 0x01 */
9367
    MFHI_ACC = 0x0,
9368
    MFLO_ACC = 0x1,
9369
    MTHI_ACC = 0x2,
9370
    MTLO_ACC = 0x3,
9371

    
9372
    /* bits 13..12 for 0x2a */
9373
    MADD_ACC = 0x0,
9374
    MADDU_ACC = 0x1,
9375
    MSUB_ACC = 0x2,
9376
    MSUBU_ACC = 0x3,
9377

    
9378
    /* bits 13..12 for 0x32 */
9379
    MULT_ACC = 0x0,
9380
    MULTU_ACC = 0x0,
9381

    
9382
    /* bits 15..12 for 0x2c */
9383
    SEB = 0x2,
9384
    SEH = 0x3,
9385
    CLO = 0x4,
9386
    CLZ = 0x5,
9387
    RDHWR = 0x6,
9388
    WSBH = 0x7,
9389
    MULT = 0x8,
9390
    MULTU = 0x9,
9391
    DIV = 0xa,
9392
    DIVU = 0xb,
9393
    MADD = 0xc,
9394
    MADDU = 0xd,
9395
    MSUB = 0xe,
9396
    MSUBU = 0xf,
9397

    
9398
    /* bits 15..12 for 0x34 */
9399
    MFC2 = 0x4,
9400
    MTC2 = 0x5,
9401
    MFHC2 = 0x8,
9402
    MTHC2 = 0x9,
9403
    CFC2 = 0xc,
9404
    CTC2 = 0xd,
9405

    
9406
    /* bits 15..12 for 0x3c */
9407
    JALR = 0x0,
9408
    JR = 0x0,                   /* alias */
9409
    JALR_HB = 0x1,
9410
    JALRS = 0x4,
9411
    JALRS_HB = 0x5,
9412

    
9413
    /* bits 15..12 for 0x05 */
9414
    RDPGPR = 0xe,
9415
    WRPGPR = 0xf,
9416

    
9417
    /* bits 15..12 for 0x0d */
9418
    TLBP = 0x0,
9419
    TLBR = 0x1,
9420
    TLBWI = 0x2,
9421
    TLBWR = 0x3,
9422
    WAIT = 0x9,
9423
    IRET = 0xd,
9424
    DERET = 0xe,
9425
    ERET = 0xf,
9426

    
9427
    /* bits 15..12 for 0x15 */
9428
    DMT = 0x0,
9429
    DVPE = 0x1,
9430
    EMT = 0x2,
9431
    EVPE = 0x3,
9432

    
9433
    /* bits 15..12 for 0x1d */
9434
    DI = 0x4,
9435
    EI = 0x5,
9436

    
9437
    /* bits 15..12 for 0x2d */
9438
    SYNC = 0x6,
9439
    SYSCALL = 0x8,
9440
    SDBBP = 0xd,
9441

    
9442
    /* bits 15..12 for 0x35 */
9443
    MFHI32 = 0x0,
9444
    MFLO32 = 0x1,
9445
    MTHI32 = 0x2,
9446
    MTLO32 = 0x3,
9447
};
9448

    
9449
/* POOL32B encoding of minor opcode field (bits 15..12) */
9450

    
9451
enum {
9452
    LWC2 = 0x0,
9453
    LWP = 0x1,
9454
    LDP = 0x4,
9455
    LWM32 = 0x5,
9456
    CACHE = 0x6,
9457
    LDM = 0x7,
9458
    SWC2 = 0x8,
9459
    SWP = 0x9,
9460
    SDP = 0xc,
9461
    SWM32 = 0xd,
9462
    SDM = 0xf
9463
};
9464

    
9465
/* POOL32C encoding of minor opcode field (bits 15..12) */
9466

    
9467
enum {
9468
    LWL = 0x0,
9469
    SWL = 0x8,
9470
    LWR = 0x1,
9471
    SWR = 0x9,
9472
    PREF = 0x2,
9473
    /* 0xa is reserved */
9474
    LL = 0x3,
9475
    SC = 0xb,
9476
    LDL = 0x4,
9477
    SDL = 0xc,
9478
    LDR = 0x5,
9479
    SDR = 0xd,
9480
    /* 0x6 is reserved */
9481
    LWU = 0xe,
9482
    LLD = 0x7,
9483
    SCD = 0xf
9484
};
9485

    
9486
/* POOL32F encoding of minor opcode field (bits 5..0) */
9487

    
9488
enum {
9489
    /* These are the bit 7..6 values */
9490
    ADD_FMT = 0x0,
9491
    MOVN_FMT = 0x0,
9492

    
9493
    SUB_FMT = 0x1,
9494
    MOVZ_FMT = 0x1,
9495

    
9496
    MUL_FMT = 0x2,
9497

    
9498
    DIV_FMT = 0x3,
9499

    
9500
    /* These are the bit 8..6 values */
9501
    RSQRT2_FMT = 0x0,
9502
    MOVF_FMT = 0x0,
9503

    
9504
    LWXC1 = 0x1,
9505
    MOVT_FMT = 0x1,
9506

    
9507
    PLL_PS = 0x2,
9508
    SWXC1 = 0x2,
9509

    
9510
    PLU_PS = 0x3,
9511
    LDXC1 = 0x3,
9512

    
9513
    PUL_PS = 0x4,
9514
    SDXC1 = 0x4,
9515
    RECIP2_FMT = 0x4,
9516

    
9517
    PUU_PS = 0x5,
9518
    LUXC1 = 0x5,
9519

    
9520
    CVT_PS_S = 0x6,
9521
    SUXC1 = 0x6,
9522
    ADDR_PS = 0x6,
9523
    PREFX = 0x6,
9524

    
9525
    MULR_PS = 0x7,
9526

    
9527
    MADD_S = 0x01,
9528
    MADD_D = 0x09,
9529
    MADD_PS = 0x11,
9530
    ALNV_PS = 0x19,
9531
    MSUB_S = 0x21,
9532
    MSUB_D = 0x29,
9533
    MSUB_PS = 0x31,
9534

    
9535
    NMADD_S = 0x02,
9536
    NMADD_D = 0x0a,
9537
    NMADD_PS = 0x12,
9538
    NMSUB_S = 0x22,
9539
    NMSUB_D = 0x2a,
9540
    NMSUB_PS = 0x32,
9541

    
9542
    POOL32FXF = 0x3b,
9543

    
9544
    CABS_COND_FMT = 0x1c,              /* MIPS3D */
9545
    C_COND_FMT = 0x3c
9546
};
9547

    
9548
/* POOL32Fxf encoding of minor opcode extension field */
9549

    
9550
enum {
9551
    CVT_L = 0x04,
9552
    RSQRT_FMT = 0x08,
9553
    FLOOR_L = 0x0c,
9554
    CVT_PW_PS = 0x1c,
9555
    CVT_W = 0x24,
9556
    SQRT_FMT = 0x28,
9557
    FLOOR_W = 0x2c,
9558
    CVT_PS_PW = 0x3c,
9559
    CFC1 = 0x40,
9560
    RECIP_FMT = 0x48,
9561
    CEIL_L = 0x4c,
9562
    CTC1 = 0x60,
9563
    CEIL_W = 0x6c,
9564
    MFC1 = 0x80,
9565
    CVT_S_PL = 0x84,
9566
    TRUNC_L = 0x8c,
9567
    MTC1 = 0xa0,
9568
    CVT_S_PU = 0xa4,
9569
    TRUNC_W = 0xac,
9570
    MFHC1 = 0xc0,
9571
    ROUND_L = 0xcc,
9572
    MTHC1 = 0xe0,
9573
    ROUND_W = 0xec,
9574

    
9575
    MOV_FMT = 0x01,
9576
    MOVF = 0x05,
9577
    ABS_FMT = 0x0d,
9578
    RSQRT1_FMT = 0x1d,
9579
    MOVT = 0x25,
9580
    NEG_FMT = 0x2d,
9581
    CVT_D = 0x4d,
9582
    RECIP1_FMT = 0x5d,
9583
    CVT_S = 0x6d
9584
};
9585

    
9586
/* POOL32I encoding of minor opcode field (bits 25..21) */
9587

    
9588
enum {
9589
    BLTZ = 0x00,
9590
    BLTZAL = 0x01,
9591
    BGEZ = 0x02,
9592
    BGEZAL = 0x03,
9593
    BLEZ = 0x04,
9594
    BNEZC = 0x05,
9595
    BGTZ = 0x06,
9596
    BEQZC = 0x07,
9597
    TLTI = 0x08,
9598
    TGEI = 0x09,
9599
    TLTIU = 0x0a,
9600
    TGEIU = 0x0b,
9601
    TNEI = 0x0c,
9602
    LUI = 0x0d,
9603
    TEQI = 0x0e,
9604
    SYNCI = 0x10,
9605
    BLTZALS = 0x11,
9606
    BGEZALS = 0x13,
9607
    BC2F = 0x14,
9608
    BC2T = 0x15,
9609
    BPOSGE64 = 0x1a,
9610
    BPOSGE32 = 0x1b,
9611
    /* These overlap and are distinguished by bit16 of the instruction */
9612
    BC1F = 0x1c,
9613
    BC1T = 0x1d,
9614
    BC1ANY2F = 0x1c,
9615
    BC1ANY2T = 0x1d,
9616
    BC1ANY4F = 0x1e,
9617
    BC1ANY4T = 0x1f
9618
};
9619

    
9620
/* POOL16A encoding of minor opcode field */
9621

    
9622
enum {
9623
    ADDU16 = 0x0,
9624
    SUBU16 = 0x1
9625
};
9626

    
9627
/* POOL16B encoding of minor opcode field */
9628

    
9629
enum {
9630
    SLL16 = 0x0,
9631
    SRL16 = 0x1
9632
};
9633

    
9634
/* POOL16C encoding of minor opcode field */
9635

    
9636
enum {
9637
    NOT16 = 0x00,
9638
    XOR16 = 0x04,
9639
    AND16 = 0x08,
9640
    OR16 = 0x0c,
9641
    LWM16 = 0x10,
9642
    SWM16 = 0x14,
9643
    JR16 = 0x18,
9644
    JRC16 = 0x1a,
9645
    JALR16 = 0x1c,
9646
    JALR16S = 0x1e,
9647
    MFHI16 = 0x20,
9648
    MFLO16 = 0x24,
9649
    BREAK16 = 0x28,
9650
    SDBBP16 = 0x2c,
9651
    JRADDIUSP = 0x30
9652
};
9653

    
9654
/* POOL16D encoding of minor opcode field */
9655

    
9656
enum {
9657
    ADDIUS5 = 0x0,
9658
    ADDIUSP = 0x1
9659
};
9660

    
9661
/* POOL16E encoding of minor opcode field */
9662

    
9663
enum {
9664
    ADDIUR2 = 0x0,
9665
    ADDIUR1SP = 0x1
9666
};
9667

    
9668
static int mmreg (int r)
9669
{
9670
    static const int map[] = { 16, 17, 2, 3, 4, 5, 6, 7 };
9671

    
9672
    return map[r];
9673
}
9674

    
9675
/* Used for 16-bit store instructions.  */
9676
static int mmreg2 (int r)
9677
{
9678
    static const int map[] = { 0, 17, 2, 3, 4, 5, 6, 7 };
9679

    
9680
    return map[r];
9681
}
9682

    
9683
#define uMIPS_RD(op) ((op >> 7) & 0x7)
9684
#define uMIPS_RS(op) ((op >> 4) & 0x7)
9685
#define uMIPS_RS2(op) uMIPS_RS(op)
9686
#define uMIPS_RS1(op) ((op >> 1) & 0x7)
9687
#define uMIPS_RD5(op) ((op >> 5) & 0x1f)
9688
#define uMIPS_RS5(op) (op & 0x1f)
9689

    
9690
/* Signed immediate */
9691
#define SIMM(op, start, width)                                          \
9692
    ((int32_t)(((op >> start) & ((~0U) >> (32-width)))                 \
9693
               << (32-width))                                           \
9694
     >> (32-width))
9695
/* Zero-extended immediate */
9696
#define ZIMM(op, start, width) ((op >> start) & ((~0U) >> (32-width)))
9697

    
9698
static void gen_addiur1sp (CPUState *env, DisasContext *ctx)
9699
{
9700
    int rd = mmreg(uMIPS_RD(ctx->opcode));
9701

    
9702
    gen_arith_imm(env, ctx, OPC_ADDIU, rd, 29, ((ctx->opcode >> 1) & 0x3f) << 2);
9703
}
9704

    
9705
static void gen_addiur2 (CPUState *env, DisasContext *ctx)
9706
{
9707
    static const int decoded_imm[] = { 1, 4, 8, 12, 16, 20, 24, -1 };
9708
    int rd = mmreg(uMIPS_RD(ctx->opcode));
9709
    int rs = mmreg(uMIPS_RS(ctx->opcode));
9710

    
9711
    gen_arith_imm(env, ctx, OPC_ADDIU, rd, rs, decoded_imm[ZIMM(ctx->opcode, 1, 3)]);
9712
}
9713

    
9714
static void gen_addiusp (CPUState *env, DisasContext *ctx)
9715
{
9716
    int encoded = ZIMM(ctx->opcode, 1, 9);
9717
    int decoded;
9718

    
9719
    if (encoded <= 1) {
9720
        decoded = 256 + encoded;
9721
    } else if (encoded <= 255) {
9722
        decoded = encoded;
9723
    } else if (encoded <= 509) {
9724
        decoded = encoded - 512;
9725
    } else {
9726
        decoded = encoded - 768;
9727
    }
9728

    
9729
    gen_arith_imm(env, ctx, OPC_ADDIU, 29, 29, decoded << 2);
9730
}
9731

    
9732
static void gen_addius5 (CPUState *env, DisasContext *ctx)
9733
{
9734
    int imm = SIMM(ctx->opcode, 1, 4);
9735
    int rd = (ctx->opcode >> 5) & 0x1f;
9736

    
9737
    gen_arith_imm(env, ctx, OPC_ADDIU, rd, rd, imm);
9738
}
9739

    
9740
static void gen_andi16 (CPUState *env, DisasContext *ctx)
9741
{
9742
    static const int decoded_imm[] = { 128, 1, 2, 3, 4, 7, 8, 15, 16,
9743
                                 31, 32, 63, 64, 255, 32768, 65535 };
9744
    int rd = mmreg(uMIPS_RD(ctx->opcode));
9745
    int rs = mmreg(uMIPS_RS(ctx->opcode));
9746
    int encoded = ZIMM(ctx->opcode, 0, 4);
9747

    
9748
    gen_logic_imm(env, OPC_ANDI, rd, rs, decoded_imm[encoded]);
9749
}
9750

    
9751
static void gen_ldst_multiple (DisasContext *ctx, uint32_t opc, int reglist,
9752
                               int base, int16_t offset)
9753
{
9754
    TCGv t0, t1;
9755
    TCGv_i32 t2;
9756

    
9757
    if (ctx->hflags & MIPS_HFLAG_BMASK) {
9758
        generate_exception(ctx, EXCP_RI);
9759
        return;
9760
    }
9761

    
9762
    t0 = tcg_temp_new();
9763

    
9764
    gen_base_offset_addr(ctx, t0, base, offset);
9765

    
9766
    t1 = tcg_const_tl(reglist);
9767
    t2 = tcg_const_i32(ctx->mem_idx);
9768

    
9769
    save_cpu_state(ctx, 1);
9770
    switch (opc) {
9771
    case LWM32:
9772
        gen_helper_lwm(t0, t1, t2);
9773
        break;
9774
    case SWM32:
9775
        gen_helper_swm(t0, t1, t2);
9776
        break;
9777
#ifdef TARGET_MIPS64
9778
    case LDM:
9779
        gen_helper_ldm(t0, t1, t2);
9780
        break;
9781
    case SDM:
9782
        gen_helper_sdm(t0, t1, t2);
9783
        break;
9784
#endif
9785
    }
9786
    MIPS_DEBUG("%s, %x, %d(%s)", opn, reglist, offset, regnames[base]);
9787
    tcg_temp_free(t0);
9788
    tcg_temp_free(t1);
9789
    tcg_temp_free_i32(t2);
9790
}
9791

    
9792

    
9793
static void gen_pool16c_insn (CPUState *env, DisasContext *ctx, int *is_branch)
9794
{
9795
    int rd = mmreg((ctx->opcode >> 3) & 0x7);
9796
    int rs = mmreg(ctx->opcode & 0x7);
9797
    int opc;
9798

    
9799
    switch (((ctx->opcode) >> 4) & 0x3f) {
9800
    case NOT16 + 0:
9801
    case NOT16 + 1:
9802
    case NOT16 + 2:
9803
    case NOT16 + 3:
9804
        gen_logic(env, OPC_NOR, rd, rs, 0);
9805
        break;
9806
    case XOR16 + 0:
9807
    case XOR16 + 1:
9808
    case XOR16 + 2:
9809
    case XOR16 + 3:
9810
        gen_logic(env, OPC_XOR, rd, rd, rs);
9811
        break;
9812
    case AND16 + 0:
9813
    case AND16 + 1:
9814
    case AND16 + 2:
9815
    case AND16 + 3:
9816
        gen_logic(env, OPC_AND, rd, rd, rs);
9817
        break;
9818
    case OR16 + 0:
9819
    case OR16 + 1:
9820
    case OR16 + 2:
9821
    case OR16 + 3:
9822
        gen_logic(env, OPC_OR, rd, rd, rs);
9823
        break;
9824
    case LWM16 + 0:
9825
    case LWM16 + 1:
9826
    case LWM16 + 2:
9827
    case LWM16 + 3:
9828
        {
9829
            static const int lwm_convert[] = { 0x11, 0x12, 0x13, 0x14 };
9830
            int offset = ZIMM(ctx->opcode, 0, 4);
9831

    
9832
            gen_ldst_multiple(ctx, LWM32, lwm_convert[(ctx->opcode >> 4) & 0x3],
9833
                              29, offset << 2);
9834
        }
9835
        break;
9836
    case SWM16 + 0:
9837
    case SWM16 + 1:
9838
    case SWM16 + 2:
9839
    case SWM16 + 3:
9840
        {
9841
            static const int swm_convert[] = { 0x11, 0x12, 0x13, 0x14 };
9842
            int offset = ZIMM(ctx->opcode, 0, 4);
9843

    
9844
            gen_ldst_multiple(ctx, SWM32, swm_convert[(ctx->opcode >> 4) & 0x3],
9845
                              29, offset << 2);
9846
        }
9847
        break;
9848
    case JR16 + 0:
9849
    case JR16 + 1:
9850
        {
9851
            int reg = ctx->opcode & 0x1f;
9852

    
9853
            gen_compute_branch(ctx, OPC_JR, 2, reg, 0, 0);
9854
        }
9855
        *is_branch = 1;
9856
        break;
9857
    case JRC16 + 0:
9858
    case JRC16 + 1:
9859
        {
9860
            int reg = ctx->opcode & 0x1f;
9861

    
9862
            gen_compute_branch(ctx, OPC_JR, 2, reg, 0, 0);
9863
            /* Let normal delay slot handling in our caller take us
9864
               to the branch target.  */
9865
        }
9866
        break;
9867
    case JALR16 + 0:
9868
    case JALR16 + 1:
9869
        opc = OPC_JALR;
9870
        goto do_jalr;
9871
    case JALR16S + 0:
9872
    case JALR16S + 1:
9873
        opc = OPC_JALRS;
9874
    do_jalr:
9875
        {
9876
            int reg = ctx->opcode & 0x1f;
9877

    
9878
            gen_compute_branch(ctx, opc, 2, reg, 31, 0);
9879
        }
9880
        *is_branch = 1;
9881
        break;
9882
    case MFHI16 + 0:
9883
    case MFHI16 + 1:
9884
        gen_HILO(ctx, OPC_MFHI, uMIPS_RS5(ctx->opcode));
9885
        break;
9886
    case MFLO16 + 0:
9887
    case MFLO16 + 1:
9888
        gen_HILO(ctx, OPC_MFLO, uMIPS_RS5(ctx->opcode));
9889
        break;
9890
    case BREAK16:
9891
        generate_exception(ctx, EXCP_BREAK);
9892
        break;
9893
    case SDBBP16:
9894
        /* XXX: not clear which exception should be raised
9895
         *      when in debug mode...
9896
         */
9897
        check_insn(env, ctx, ISA_MIPS32);
9898
        if (!(ctx->hflags & MIPS_HFLAG_DM)) {
9899
            generate_exception(ctx, EXCP_DBp);
9900
        } else {
9901
            generate_exception(ctx, EXCP_DBp);
9902
        }
9903
        break;
9904
    case JRADDIUSP + 0:
9905
    case JRADDIUSP + 1:
9906
        {
9907
            int imm = ZIMM(ctx->opcode, 0, 5);
9908

    
9909
            gen_compute_branch(ctx, OPC_JR, 2, 31, 0, 0);
9910
            gen_arith_imm(env, ctx, OPC_ADDIU, 29, 29, imm << 2);
9911
            /* Let normal delay slot handling in our caller take us
9912
               to the branch target.  */
9913
        }
9914
        break;
9915
    default:
9916
        generate_exception(ctx, EXCP_RI);
9917
        break;
9918
    }
9919
}
9920

    
9921
static void gen_ldxs (DisasContext *ctx, int base, int index, int rd)
9922
{
9923
    TCGv t0 = tcg_temp_new();
9924
    TCGv t1 = tcg_temp_new();
9925

    
9926
    gen_load_gpr(t0, base);
9927

    
9928
    if (index != 0) {
9929
        gen_load_gpr(t1, index);
9930
        tcg_gen_shli_tl(t1, t1, 2);
9931
        gen_op_addr_add(ctx, t0, t1, t0);
9932
    }
9933

    
9934
    save_cpu_state(ctx, 0);
9935
    op_ld_lw(t1, t0, ctx);
9936
    gen_store_gpr(t1, rd);
9937

    
9938
    tcg_temp_free(t0);
9939
    tcg_temp_free(t1);
9940
}
9941

    
9942
static void gen_ldst_pair (DisasContext *ctx, uint32_t opc, int rd,
9943
                           int base, int16_t offset)
9944
{
9945
    const char *opn = "ldst_pair";
9946
    TCGv t0, t1;
9947

    
9948
    if (ctx->hflags & MIPS_HFLAG_BMASK || rd == 31 || rd == base) {
9949
        generate_exception(ctx, EXCP_RI);
9950
        return;
9951
    }
9952

    
9953
    t0 = tcg_temp_new();
9954
    t1 = tcg_temp_new();
9955

    
9956
    gen_base_offset_addr(ctx, t0, base, offset);
9957

    
9958
    switch (opc) {
9959
    case LWP:
9960
        save_cpu_state(ctx, 0);
9961
        op_ld_lw(t1, t0, ctx);
9962
        gen_store_gpr(t1, rd);
9963
        tcg_gen_movi_tl(t1, 4);
9964
        gen_op_addr_add(ctx, t0, t0, t1);
9965
        op_ld_lw(t1, t0, ctx);
9966
        gen_store_gpr(t1, rd+1);
9967
        opn = "lwp";
9968
        break;
9969
    case SWP:
9970
        save_cpu_state(ctx, 1);
9971
        gen_load_gpr(t1, rd);
9972
        op_st_sw(t1, t0, ctx);
9973
        tcg_gen_movi_tl(t1, 4);
9974
        gen_op_addr_add(ctx, t0, t0, t1);
9975
        gen_load_gpr(t1, rd+1);
9976
        op_st_sw(t1, t0, ctx);
9977
        opn = "swp";
9978
        break;
9979
#ifdef TARGET_MIPS64
9980
    case LDP:
9981
        save_cpu_state(ctx, 0);
9982
        op_ld_ld(t1, t0, ctx);
9983
        gen_store_gpr(t1, rd);
9984
        tcg_gen_movi_tl(t1, 8);
9985
        gen_op_addr_add(ctx, t0, t0, t1);
9986
        op_ld_ld(t1, t0, ctx);
9987
        gen_store_gpr(t1, rd+1);
9988
        opn = "ldp";
9989
        break;
9990
    case SDP:
9991
        save_cpu_state(ctx, 1);
9992
        gen_load_gpr(t1, rd);
9993
        op_st_sd(t1, t0, ctx);
9994
        tcg_gen_movi_tl(t1, 8);
9995
        gen_op_addr_add(ctx, t0, t0, t1);
9996
        gen_load_gpr(t1, rd+1);
9997
        op_st_sd(t1, t0, ctx);
9998
        opn = "sdp";
9999
        break;
10000
#endif
10001
    }
10002
    (void)opn; /* avoid a compiler warning */
10003
    MIPS_DEBUG("%s, %s, %d(%s)", opn, regnames[rd], offset, regnames[base]);
10004
    tcg_temp_free(t0);
10005
    tcg_temp_free(t1);
10006
}
10007

    
10008
static void gen_pool32axf (CPUState *env, DisasContext *ctx, int rt, int rs,
10009
                           int *is_branch)
10010
{
10011
    int extension = (ctx->opcode >> 6) & 0x3f;
10012
    int minor = (ctx->opcode >> 12) & 0xf;
10013
    uint32_t mips32_op;
10014

    
10015
    switch (extension) {
10016
    case TEQ:
10017
        mips32_op = OPC_TEQ;
10018
        goto do_trap;
10019
    case TGE:
10020
        mips32_op = OPC_TGE;
10021
        goto do_trap;
10022
    case TGEU:
10023
        mips32_op = OPC_TGEU;
10024
        goto do_trap;
10025
    case TLT:
10026
        mips32_op = OPC_TLT;
10027
        goto do_trap;
10028
    case TLTU:
10029
        mips32_op = OPC_TLTU;
10030
        goto do_trap;
10031
    case TNE:
10032
        mips32_op = OPC_TNE;
10033
    do_trap:
10034
        gen_trap(ctx, mips32_op, rs, rt, -1);
10035
        break;
10036
#ifndef CONFIG_USER_ONLY
10037
    case MFC0:
10038
    case MFC0 + 32:
10039
        if (rt == 0) {
10040
            /* Treat as NOP. */
10041
            break;
10042
        }
10043
        gen_mfc0(env, ctx, cpu_gpr[rt], rs, (ctx->opcode >> 11) & 0x7);
10044
        break;
10045
    case MTC0:
10046
    case MTC0 + 32:
10047
        {
10048
            TCGv t0 = tcg_temp_new();
10049

    
10050
            gen_load_gpr(t0, rt);
10051
            gen_mtc0(env, ctx, t0, rs, (ctx->opcode >> 11) & 0x7);
10052
            tcg_temp_free(t0);
10053
        }
10054
        break;
10055
#endif
10056
    case 0x2c:
10057
        switch (minor) {
10058
        case SEB:
10059
            gen_bshfl(ctx, OPC_SEB, rs, rt);
10060
            break;
10061
        case SEH:
10062
            gen_bshfl(ctx, OPC_SEH, rs, rt);
10063
            break;
10064
        case CLO:
10065
            mips32_op = OPC_CLO;
10066
            goto do_cl;
10067
        case CLZ:
10068
            mips32_op = OPC_CLZ;
10069
        do_cl:
10070
            check_insn(env, ctx, ISA_MIPS32);
10071
            gen_cl(ctx, mips32_op, rt, rs);
10072
            break;
10073
        case RDHWR:
10074
            gen_rdhwr(env, ctx, rt, rs);
10075
            break;
10076
        case WSBH:
10077
            gen_bshfl(ctx, OPC_WSBH, rs, rt);
10078
            break;
10079
        case MULT:
10080
            mips32_op = OPC_MULT;
10081
            goto do_muldiv;
10082
        case MULTU:
10083
            mips32_op = OPC_MULTU;
10084
            goto do_muldiv;
10085
        case DIV:
10086
            mips32_op = OPC_DIV;
10087
            goto do_muldiv;
10088
        case DIVU:
10089
            mips32_op = OPC_DIVU;
10090
            goto do_muldiv;
10091
        case MADD:
10092
            mips32_op = OPC_MADD;
10093
            goto do_muldiv;
10094
        case MADDU:
10095
            mips32_op = OPC_MADDU;
10096
            goto do_muldiv;
10097
        case MSUB:
10098
            mips32_op = OPC_MSUB;
10099
            goto do_muldiv;
10100
        case MSUBU:
10101
            mips32_op = OPC_MSUBU;
10102
        do_muldiv:
10103
            check_insn(env, ctx, ISA_MIPS32);
10104
            gen_muldiv(ctx, mips32_op, rs, rt);
10105
            break;
10106
        default:
10107
            goto pool32axf_invalid;
10108
        }
10109
        break;
10110
    case 0x34:
10111
        switch (minor) {
10112
        case MFC2:
10113
        case MTC2:
10114
        case MFHC2:
10115
        case MTHC2:
10116
        case CFC2:
10117
        case CTC2:
10118
            generate_exception_err(ctx, EXCP_CpU, 2);
10119
            break;
10120
        default:
10121
            goto pool32axf_invalid;
10122
        }
10123
        break;
10124
    case 0x3c:
10125
        switch (minor) {
10126
        case JALR:
10127
        case JALR_HB:
10128
            gen_compute_branch (ctx, OPC_JALR, 4, rs, rt, 0);
10129
            *is_branch = 1;
10130
            break;
10131
        case JALRS:
10132
        case JALRS_HB:
10133
            gen_compute_branch (ctx, OPC_JALRS, 4, rs, rt, 0);
10134
            *is_branch = 1;
10135
            break;
10136
        default:
10137
            goto pool32axf_invalid;
10138
        }
10139
        break;
10140
    case 0x05:
10141
        switch (minor) {
10142
        case RDPGPR:
10143
            check_insn(env, ctx, ISA_MIPS32R2);
10144
            gen_load_srsgpr(rt, rs);
10145
            break;
10146
        case WRPGPR:
10147
            check_insn(env, ctx, ISA_MIPS32R2);
10148
            gen_store_srsgpr(rt, rs);
10149
            break;
10150
        default:
10151
            goto pool32axf_invalid;
10152
        }
10153
        break;
10154
#ifndef CONFIG_USER_ONLY
10155
    case 0x0d:
10156
        switch (minor) {
10157
        case TLBP:
10158
            mips32_op = OPC_TLBP;
10159
            goto do_cp0;
10160
        case TLBR:
10161
            mips32_op = OPC_TLBR;
10162
            goto do_cp0;
10163
        case TLBWI:
10164
            mips32_op = OPC_TLBWI;
10165
            goto do_cp0;
10166
        case TLBWR:
10167
            mips32_op = OPC_TLBWR;
10168
            goto do_cp0;
10169
        case WAIT:
10170
            mips32_op = OPC_WAIT;
10171
            goto do_cp0;
10172
        case DERET:
10173
            mips32_op = OPC_DERET;
10174
            goto do_cp0;
10175
        case ERET:
10176
            mips32_op = OPC_ERET;
10177
        do_cp0:
10178
            gen_cp0(env, ctx, mips32_op, rt, rs);
10179
            break;
10180
        default:
10181
            goto pool32axf_invalid;
10182
        }
10183
        break;
10184
    case 0x1d:
10185
        switch (minor) {
10186
        case DI:
10187
            {
10188
                TCGv t0 = tcg_temp_new();
10189

    
10190
                save_cpu_state(ctx, 1);
10191
                gen_helper_di(t0);
10192
                gen_store_gpr(t0, rs);
10193
                /* Stop translation as we may have switched the execution mode */
10194
                ctx->bstate = BS_STOP;
10195
                tcg_temp_free(t0);
10196
            }
10197
            break;
10198
        case EI:
10199
            {
10200
                TCGv t0 = tcg_temp_new();
10201

    
10202
                save_cpu_state(ctx, 1);
10203
                gen_helper_ei(t0);
10204
                gen_store_gpr(t0, rs);
10205
                /* Stop translation as we may have switched the execution mode */
10206
                ctx->bstate = BS_STOP;
10207
                tcg_temp_free(t0);
10208
            }
10209
            break;
10210
        default:
10211
            goto pool32axf_invalid;
10212
        }
10213
        break;
10214
#endif
10215
    case 0x2d:
10216
        switch (minor) {
10217
        case SYNC:
10218
            /* NOP */
10219
            break;
10220
        case SYSCALL:
10221
            generate_exception(ctx, EXCP_SYSCALL);
10222
            ctx->bstate = BS_STOP;
10223
            break;
10224
        case SDBBP:
10225
            check_insn(env, ctx, ISA_MIPS32);
10226
            if (!(ctx->hflags & MIPS_HFLAG_DM)) {
10227
                generate_exception(ctx, EXCP_DBp);
10228
            } else {
10229
                generate_exception(ctx, EXCP_DBp);
10230
            }
10231
            break;
10232
        default:
10233
            goto pool32axf_invalid;
10234
        }
10235
        break;
10236
    case 0x35:
10237
        switch (minor) {
10238
        case MFHI32:
10239
            gen_HILO(ctx, OPC_MFHI, rs);
10240
            break;
10241
        case MFLO32:
10242
            gen_HILO(ctx, OPC_MFLO, rs);
10243
            break;
10244
        case MTHI32:
10245
            gen_HILO(ctx, OPC_MTHI, rs);
10246
            break;
10247
        case MTLO32:
10248
            gen_HILO(ctx, OPC_MTLO, rs);
10249
            break;
10250
        default:
10251
            goto pool32axf_invalid;
10252
        }
10253
        break;
10254
    default:
10255
    pool32axf_invalid:
10256
        MIPS_INVAL("pool32axf");
10257
        generate_exception(ctx, EXCP_RI);
10258
        break;
10259
    }
10260
}
10261

    
10262
/* Values for microMIPS fmt field.  Variable-width, depending on which
10263
   formats the instruction supports.  */
10264

    
10265
enum {
10266
    FMT_SD_S = 0,
10267
    FMT_SD_D = 1,
10268

    
10269
    FMT_SDPS_S = 0,
10270
    FMT_SDPS_D = 1,
10271
    FMT_SDPS_PS = 2,
10272

    
10273
    FMT_SWL_S = 0,
10274
    FMT_SWL_W = 1,
10275
    FMT_SWL_L = 2,
10276

    
10277
    FMT_DWL_D = 0,
10278
    FMT_DWL_W = 1,
10279
    FMT_DWL_L = 2
10280
};
10281

    
10282
static void gen_pool32fxf (CPUState *env, DisasContext *ctx, int rt, int rs)
10283
{
10284
    int extension = (ctx->opcode >> 6) & 0x3ff;
10285
    uint32_t mips32_op;
10286

    
10287
#define FLOAT_1BIT_FMT(opc, fmt) (fmt << 8) | opc
10288
#define FLOAT_2BIT_FMT(opc, fmt) (fmt << 7) | opc
10289
#define COND_FLOAT_MOV(opc, cond) (cond << 7) | opc
10290

    
10291
    switch (extension) {
10292
    case FLOAT_1BIT_FMT(CFC1, 0):
10293
        mips32_op = OPC_CFC1;
10294
        goto do_cp1;
10295
    case FLOAT_1BIT_FMT(CTC1, 0):
10296
        mips32_op = OPC_CTC1;
10297
        goto do_cp1;
10298
    case FLOAT_1BIT_FMT(MFC1, 0):
10299
        mips32_op = OPC_MFC1;
10300
        goto do_cp1;
10301
    case FLOAT_1BIT_FMT(MTC1, 0):
10302
        mips32_op = OPC_MTC1;
10303
        goto do_cp1;
10304
    case FLOAT_1BIT_FMT(MFHC1, 0):
10305
        mips32_op = OPC_MFHC1;
10306
        goto do_cp1;
10307
    case FLOAT_1BIT_FMT(MTHC1, 0):
10308
        mips32_op = OPC_MTHC1;
10309
    do_cp1:
10310
        gen_cp1(ctx, mips32_op, rt, rs);
10311
        break;
10312

    
10313
        /* Reciprocal square root */
10314
    case FLOAT_1BIT_FMT(RSQRT_FMT, FMT_SD_S):
10315
        mips32_op = OPC_RSQRT_S;
10316
        goto do_unaryfp;
10317
    case FLOAT_1BIT_FMT(RSQRT_FMT, FMT_SD_D):
10318
        mips32_op = OPC_RSQRT_D;
10319
        goto do_unaryfp;
10320

    
10321
        /* Square root */
10322
    case FLOAT_1BIT_FMT(SQRT_FMT, FMT_SD_S):
10323
        mips32_op = OPC_SQRT_S;
10324
        goto do_unaryfp;
10325
    case FLOAT_1BIT_FMT(SQRT_FMT, FMT_SD_D):
10326
        mips32_op = OPC_SQRT_D;
10327
        goto do_unaryfp;
10328

    
10329
        /* Reciprocal */
10330
    case FLOAT_1BIT_FMT(RECIP_FMT, FMT_SD_S):
10331
        mips32_op = OPC_RECIP_S;
10332
        goto do_unaryfp;
10333
    case FLOAT_1BIT_FMT(RECIP_FMT, FMT_SD_D):
10334
        mips32_op = OPC_RECIP_D;
10335
        goto do_unaryfp;
10336

    
10337
        /* Floor */
10338
    case FLOAT_1BIT_FMT(FLOOR_L, FMT_SD_S):
10339
        mips32_op = OPC_FLOOR_L_S;
10340
        goto do_unaryfp;
10341
    case FLOAT_1BIT_FMT(FLOOR_L, FMT_SD_D):
10342
        mips32_op = OPC_FLOOR_L_D;
10343
        goto do_unaryfp;
10344
    case FLOAT_1BIT_FMT(FLOOR_W, FMT_SD_S):
10345
        mips32_op = OPC_FLOOR_W_S;
10346
        goto do_unaryfp;
10347
    case FLOAT_1BIT_FMT(FLOOR_W, FMT_SD_D):
10348
        mips32_op = OPC_FLOOR_W_D;
10349
        goto do_unaryfp;
10350

    
10351
        /* Ceiling */
10352
    case FLOAT_1BIT_FMT(CEIL_L, FMT_SD_S):
10353
        mips32_op = OPC_CEIL_L_S;
10354
        goto do_unaryfp;
10355
    case FLOAT_1BIT_FMT(CEIL_L, FMT_SD_D):
10356
        mips32_op = OPC_CEIL_L_D;
10357
        goto do_unaryfp;
10358
    case FLOAT_1BIT_FMT(CEIL_W, FMT_SD_S):
10359
        mips32_op = OPC_CEIL_W_S;
10360
        goto do_unaryfp;
10361
    case FLOAT_1BIT_FMT(CEIL_W, FMT_SD_D):
10362
        mips32_op = OPC_CEIL_W_D;
10363
        goto do_unaryfp;
10364

    
10365
        /* Truncation */
10366
    case FLOAT_1BIT_FMT(TRUNC_L, FMT_SD_S):
10367
        mips32_op = OPC_TRUNC_L_S;
10368
        goto do_unaryfp;
10369
    case FLOAT_1BIT_FMT(TRUNC_L, FMT_SD_D):
10370
        mips32_op = OPC_TRUNC_L_D;
10371
        goto do_unaryfp;
10372
    case FLOAT_1BIT_FMT(TRUNC_W, FMT_SD_S):
10373
        mips32_op = OPC_TRUNC_W_S;
10374
        goto do_unaryfp;
10375
    case FLOAT_1BIT_FMT(TRUNC_W, FMT_SD_D):
10376
        mips32_op = OPC_TRUNC_W_D;
10377
        goto do_unaryfp;
10378

    
10379
        /* Round */
10380
    case FLOAT_1BIT_FMT(ROUND_L, FMT_SD_S):
10381
        mips32_op = OPC_ROUND_L_S;
10382
        goto do_unaryfp;
10383
    case FLOAT_1BIT_FMT(ROUND_L, FMT_SD_D):
10384
        mips32_op = OPC_ROUND_L_D;
10385
        goto do_unaryfp;
10386
    case FLOAT_1BIT_FMT(ROUND_W, FMT_SD_S):
10387
        mips32_op = OPC_ROUND_W_S;
10388
        goto do_unaryfp;
10389
    case FLOAT_1BIT_FMT(ROUND_W, FMT_SD_D):
10390
        mips32_op = OPC_ROUND_W_D;
10391
        goto do_unaryfp;
10392

    
10393
        /* Integer to floating-point conversion */
10394
    case FLOAT_1BIT_FMT(CVT_L, FMT_SD_S):
10395
        mips32_op = OPC_CVT_L_S;
10396
        goto do_unaryfp;
10397
    case FLOAT_1BIT_FMT(CVT_L, FMT_SD_D):
10398
        mips32_op = OPC_CVT_L_D;
10399
        goto do_unaryfp;
10400
    case FLOAT_1BIT_FMT(CVT_W, FMT_SD_S):
10401
        mips32_op = OPC_CVT_W_S;
10402
        goto do_unaryfp;
10403
    case FLOAT_1BIT_FMT(CVT_W, FMT_SD_D):
10404
        mips32_op = OPC_CVT_W_D;
10405
        goto do_unaryfp;
10406

    
10407
        /* Paired-foo conversions */
10408
    case FLOAT_1BIT_FMT(CVT_S_PL, 0):
10409
        mips32_op = OPC_CVT_S_PL;
10410
        goto do_unaryfp;
10411
    case FLOAT_1BIT_FMT(CVT_S_PU, 0):
10412
        mips32_op = OPC_CVT_S_PU;
10413
        goto do_unaryfp;
10414
    case FLOAT_1BIT_FMT(CVT_PW_PS, 0):
10415
        mips32_op = OPC_CVT_PW_PS;
10416
        goto do_unaryfp;
10417
    case FLOAT_1BIT_FMT(CVT_PS_PW, 0):
10418
        mips32_op = OPC_CVT_PS_PW;
10419
        goto do_unaryfp;
10420

    
10421
        /* Floating-point moves */
10422
    case FLOAT_2BIT_FMT(MOV_FMT, FMT_SDPS_S):
10423
        mips32_op = OPC_MOV_S;
10424
        goto do_unaryfp;
10425
    case FLOAT_2BIT_FMT(MOV_FMT, FMT_SDPS_D):
10426
        mips32_op = OPC_MOV_D;
10427
        goto do_unaryfp;
10428
    case FLOAT_2BIT_FMT(MOV_FMT, FMT_SDPS_PS):
10429
        mips32_op = OPC_MOV_PS;
10430
        goto do_unaryfp;
10431

    
10432
        /* Absolute value */
10433
    case FLOAT_2BIT_FMT(ABS_FMT, FMT_SDPS_S):
10434
        mips32_op = OPC_ABS_S;
10435
        goto do_unaryfp;
10436
    case FLOAT_2BIT_FMT(ABS_FMT, FMT_SDPS_D):
10437
        mips32_op = OPC_ABS_D;
10438
        goto do_unaryfp;
10439
    case FLOAT_2BIT_FMT(ABS_FMT, FMT_SDPS_PS):
10440
        mips32_op = OPC_ABS_PS;
10441
        goto do_unaryfp;
10442

    
10443
        /* Negation */
10444
    case FLOAT_2BIT_FMT(NEG_FMT, FMT_SDPS_S):
10445
        mips32_op = OPC_NEG_S;
10446
        goto do_unaryfp;
10447
    case FLOAT_2BIT_FMT(NEG_FMT, FMT_SDPS_D):
10448
        mips32_op = OPC_NEG_D;
10449
        goto do_unaryfp;
10450
    case FLOAT_2BIT_FMT(NEG_FMT, FMT_SDPS_PS):
10451
        mips32_op = OPC_NEG_PS;
10452
        goto do_unaryfp;
10453

    
10454
        /* Reciprocal square root step */
10455
    case FLOAT_2BIT_FMT(RSQRT1_FMT, FMT_SDPS_S):
10456
        mips32_op = OPC_RSQRT1_S;
10457
        goto do_unaryfp;
10458
    case FLOAT_2BIT_FMT(RSQRT1_FMT, FMT_SDPS_D):
10459
        mips32_op = OPC_RSQRT1_D;
10460
        goto do_unaryfp;
10461
    case FLOAT_2BIT_FMT(RSQRT1_FMT, FMT_SDPS_PS):
10462
        mips32_op = OPC_RSQRT1_PS;
10463
        goto do_unaryfp;
10464

    
10465
        /* Reciprocal step */
10466
    case FLOAT_2BIT_FMT(RECIP1_FMT, FMT_SDPS_S):
10467
        mips32_op = OPC_RECIP1_S;
10468
        goto do_unaryfp;
10469
    case FLOAT_2BIT_FMT(RECIP1_FMT, FMT_SDPS_D):
10470
        mips32_op = OPC_RECIP1_S;
10471
        goto do_unaryfp;
10472
    case FLOAT_2BIT_FMT(RECIP1_FMT, FMT_SDPS_PS):
10473
        mips32_op = OPC_RECIP1_PS;
10474
        goto do_unaryfp;
10475

    
10476
        /* Conversions from double */
10477
    case FLOAT_2BIT_FMT(CVT_D, FMT_SWL_S):
10478
        mips32_op = OPC_CVT_D_S;
10479
        goto do_unaryfp;
10480
    case FLOAT_2BIT_FMT(CVT_D, FMT_SWL_W):
10481
        mips32_op = OPC_CVT_D_W;
10482
        goto do_unaryfp;
10483
    case FLOAT_2BIT_FMT(CVT_D, FMT_SWL_L):
10484
        mips32_op = OPC_CVT_D_L;
10485
        goto do_unaryfp;
10486

    
10487
        /* Conversions from single */
10488
    case FLOAT_2BIT_FMT(CVT_S, FMT_DWL_D):
10489
        mips32_op = OPC_CVT_S_D;
10490
        goto do_unaryfp;
10491
    case FLOAT_2BIT_FMT(CVT_S, FMT_DWL_W):
10492
        mips32_op = OPC_CVT_S_W;
10493
        goto do_unaryfp;
10494
    case FLOAT_2BIT_FMT(CVT_S, FMT_DWL_L):
10495
        mips32_op = OPC_CVT_S_L;
10496
    do_unaryfp:
10497
        gen_farith(ctx, mips32_op, -1, rs, rt, 0);
10498
        break;
10499

    
10500
        /* Conditional moves on floating-point codes */
10501
    case COND_FLOAT_MOV(MOVT, 0):
10502
    case COND_FLOAT_MOV(MOVT, 1):
10503
    case COND_FLOAT_MOV(MOVT, 2):
10504
    case COND_FLOAT_MOV(MOVT, 3):
10505
    case COND_FLOAT_MOV(MOVT, 4):
10506
    case COND_FLOAT_MOV(MOVT, 5):
10507
    case COND_FLOAT_MOV(MOVT, 6):
10508
    case COND_FLOAT_MOV(MOVT, 7):
10509
        gen_movci(ctx, rt, rs, (ctx->opcode >> 13) & 0x7, 1);
10510
        break;
10511
    case COND_FLOAT_MOV(MOVF, 0):
10512
    case COND_FLOAT_MOV(MOVF, 1):
10513
    case COND_FLOAT_MOV(MOVF, 2):
10514
    case COND_FLOAT_MOV(MOVF, 3):
10515
    case COND_FLOAT_MOV(MOVF, 4):
10516
    case COND_FLOAT_MOV(MOVF, 5):
10517
    case COND_FLOAT_MOV(MOVF, 6):
10518
    case COND_FLOAT_MOV(MOVF, 7):
10519
        gen_movci(ctx, rt, rs, (ctx->opcode >> 13) & 0x7, 0);
10520
        break;
10521
    default:
10522
        MIPS_INVAL("pool32fxf");
10523
        generate_exception(ctx, EXCP_RI);
10524
        break;
10525
    }
10526
}
10527

    
10528
static void decode_micromips32_opc (CPUState *env, DisasContext *ctx,
10529
                                    uint16_t insn_hw1, int *is_branch)
10530
{
10531
    int32_t offset;
10532
    uint16_t insn;
10533
    int rt, rs, rd, rr;
10534
    int16_t imm;
10535
    uint32_t op, minor, mips32_op;
10536
    uint32_t cond, fmt, cc;
10537

    
10538
    insn = lduw_code(ctx->pc + 2);
10539
    ctx->opcode = (ctx->opcode << 16) | insn;
10540

    
10541
    rt = (ctx->opcode >> 21) & 0x1f;
10542
    rs = (ctx->opcode >> 16) & 0x1f;
10543
    rd = (ctx->opcode >> 11) & 0x1f;
10544
    rr = (ctx->opcode >> 6) & 0x1f;
10545
    imm = (int16_t) ctx->opcode;
10546

    
10547
    op = (ctx->opcode >> 26) & 0x3f;
10548
    switch (op) {
10549
    case POOL32A:
10550
        minor = ctx->opcode & 0x3f;
10551
        switch (minor) {
10552
        case 0x00:
10553
            minor = (ctx->opcode >> 6) & 0xf;
10554
            switch (minor) {
10555
            case SLL32:
10556
                mips32_op = OPC_SLL;
10557
                goto do_shifti;
10558
            case SRA:
10559
                mips32_op = OPC_SRA;
10560
                goto do_shifti;
10561
            case SRL32:
10562
                mips32_op = OPC_SRL;
10563
                goto do_shifti;
10564
            case ROTR:
10565
                mips32_op = OPC_ROTR;
10566
            do_shifti:
10567
                gen_shift_imm(env, ctx, mips32_op, rt, rs, rd);
10568
                break;
10569
            default:
10570
                goto pool32a_invalid;
10571
            }
10572
            break;
10573
        case 0x10:
10574
            minor = (ctx->opcode >> 6) & 0xf;
10575
            switch (minor) {
10576
                /* Arithmetic */
10577
            case ADD:
10578
                mips32_op = OPC_ADD;
10579
                goto do_arith;
10580
            case ADDU32:
10581
                mips32_op = OPC_ADDU;
10582
                goto do_arith;
10583
            case SUB:
10584
                mips32_op = OPC_SUB;
10585
                goto do_arith;
10586
            case SUBU32:
10587
                mips32_op = OPC_SUBU;
10588
                goto do_arith;
10589
            case MUL:
10590
                mips32_op = OPC_MUL;
10591
            do_arith:
10592
                gen_arith(env, ctx, mips32_op, rd, rs, rt);
10593
                break;
10594
                /* Shifts */
10595
            case SLLV:
10596
                mips32_op = OPC_SLLV;
10597
                goto do_shift;
10598
            case SRLV:
10599
                mips32_op = OPC_SRLV;
10600
                goto do_shift;
10601
            case SRAV:
10602
                mips32_op = OPC_SRAV;
10603
                goto do_shift;
10604
            case ROTRV:
10605
                mips32_op = OPC_ROTRV;
10606
            do_shift:
10607
                gen_shift(env, ctx, mips32_op, rd, rs, rt);
10608
                break;
10609
                /* Logical operations */
10610
            case AND:
10611
                mips32_op = OPC_AND;
10612
                goto do_logic;
10613
            case OR32:
10614
                mips32_op = OPC_OR;
10615
                goto do_logic;
10616
            case NOR:
10617
                mips32_op = OPC_NOR;
10618
                goto do_logic;
10619
            case XOR32:
10620
                mips32_op = OPC_XOR;
10621
            do_logic:
10622
                gen_logic(env, mips32_op, rd, rs, rt);
10623
                break;
10624
                /* Set less than */
10625
            case SLT:
10626
                mips32_op = OPC_SLT;
10627
                goto do_slt;
10628
            case SLTU:
10629
                mips32_op = OPC_SLTU;
10630
            do_slt:
10631
                gen_slt(env, mips32_op, rd, rs, rt);
10632
                break;
10633
            default:
10634
                goto pool32a_invalid;
10635
            }
10636
            break;
10637
        case 0x18:
10638
            minor = (ctx->opcode >> 6) & 0xf;
10639
            switch (minor) {
10640
                /* Conditional moves */
10641
            case MOVN:
10642
                mips32_op = OPC_MOVN;
10643
                goto do_cmov;
10644
            case MOVZ:
10645
                mips32_op = OPC_MOVZ;
10646
            do_cmov:
10647
                gen_cond_move(env, mips32_op, rd, rs, rt);
10648
                break;
10649
            case LWXS:
10650
                gen_ldxs(ctx, rs, rt, rd);
10651
                break;
10652
            default:
10653
                goto pool32a_invalid;
10654
            }
10655
            break;
10656
        case INS:
10657
            gen_bitops(ctx, OPC_INS, rt, rs, rr, rd);
10658
            return;
10659
        case EXT:
10660
            gen_bitops(ctx, OPC_EXT, rt, rs, rr, rd);
10661
            return;
10662
        case POOL32AXF:
10663
            gen_pool32axf(env, ctx, rt, rs, is_branch);
10664
            break;
10665
        case 0x07:
10666
            generate_exception(ctx, EXCP_BREAK);
10667
            break;
10668
        default:
10669
        pool32a_invalid:
10670
                MIPS_INVAL("pool32a");
10671
                generate_exception(ctx, EXCP_RI);
10672
                break;
10673
        }
10674
        break;
10675
    case POOL32B:
10676
        minor = (ctx->opcode >> 12) & 0xf;
10677
        switch (minor) {
10678
        case CACHE:
10679
            /* Treat as no-op. */
10680
            break;
10681
        case LWC2:
10682
        case SWC2:
10683
            /* COP2: Not implemented. */
10684
            generate_exception_err(ctx, EXCP_CpU, 2);
10685
            break;
10686
        case LWP:
10687
        case SWP:
10688
#ifdef TARGET_MIPS64
10689
        case LDP:
10690
        case SDP:
10691
#endif
10692
            gen_ldst_pair(ctx, minor, rt, rs, SIMM(ctx->opcode, 0, 12));
10693
            break;
10694
        case LWM32:
10695
        case SWM32:
10696
#ifdef TARGET_MIPS64
10697
        case LDM:
10698
        case SDM:
10699
#endif
10700
            gen_ldst_multiple(ctx, minor, rt, rs, SIMM(ctx->opcode, 0, 12));
10701
            break;
10702
        default:
10703
            MIPS_INVAL("pool32b");
10704
            generate_exception(ctx, EXCP_RI);
10705
            break;
10706
        }
10707
        break;
10708
    case POOL32F:
10709
        if (env->CP0_Config1 & (1 << CP0C1_FP)) {
10710
            minor = ctx->opcode & 0x3f;
10711
            check_cp1_enabled(ctx);
10712
            switch (minor) {
10713
            case ALNV_PS:
10714
                mips32_op = OPC_ALNV_PS;
10715
                goto do_madd;
10716
            case MADD_S:
10717
                mips32_op = OPC_MADD_S;
10718
                goto do_madd;
10719
            case MADD_D:
10720
                mips32_op = OPC_MADD_D;
10721
                goto do_madd;
10722
            case MADD_PS:
10723
                mips32_op = OPC_MADD_PS;
10724
                goto do_madd;
10725
            case MSUB_S:
10726
                mips32_op = OPC_MSUB_S;
10727
                goto do_madd;
10728
            case MSUB_D:
10729
                mips32_op = OPC_MSUB_D;
10730
                goto do_madd;
10731
            case MSUB_PS:
10732
                mips32_op = OPC_MSUB_PS;
10733
                goto do_madd;
10734
            case NMADD_S:
10735
                mips32_op = OPC_NMADD_S;
10736
                goto do_madd;
10737
            case NMADD_D:
10738
                mips32_op = OPC_NMADD_D;
10739
                goto do_madd;
10740
            case NMADD_PS:
10741
                mips32_op = OPC_NMADD_PS;
10742
                goto do_madd;
10743
            case NMSUB_S:
10744
                mips32_op = OPC_NMSUB_S;
10745
                goto do_madd;
10746
            case NMSUB_D:
10747
                mips32_op = OPC_NMSUB_D;
10748
                goto do_madd;
10749
            case NMSUB_PS:
10750
                mips32_op = OPC_NMSUB_PS;
10751
            do_madd:
10752
                gen_flt3_arith(ctx, mips32_op, rd, rr, rs, rt);
10753
                break;
10754
            case CABS_COND_FMT:
10755
                cond = (ctx->opcode >> 6) & 0xf;
10756
                cc = (ctx->opcode >> 13) & 0x7;
10757
                fmt = (ctx->opcode >> 10) & 0x3;
10758
                switch (fmt) {
10759
                case 0x0:
10760
                    gen_cmpabs_s(ctx, cond, rt, rs, cc);
10761
                    break;
10762
                case 0x1:
10763
                    gen_cmpabs_d(ctx, cond, rt, rs, cc);
10764
                    break;
10765
                case 0x2:
10766
                    gen_cmpabs_ps(ctx, cond, rt, rs, cc);
10767
                    break;
10768
                default:
10769
                    goto pool32f_invalid;
10770
                }
10771
                break;
10772
            case C_COND_FMT:
10773
                cond = (ctx->opcode >> 6) & 0xf;
10774
                cc = (ctx->opcode >> 13) & 0x7;
10775
                fmt = (ctx->opcode >> 10) & 0x3;
10776
                switch (fmt) {
10777
                case 0x0:
10778
                    gen_cmp_s(ctx, cond, rt, rs, cc);
10779
                    break;
10780
                case 0x1:
10781
                    gen_cmp_d(ctx, cond, rt, rs, cc);
10782
                    break;
10783
                case 0x2:
10784
                    gen_cmp_ps(ctx, cond, rt, rs, cc);
10785
                    break;
10786
                default:
10787
                    goto pool32f_invalid;
10788
                }
10789
                break;
10790
            case POOL32FXF:
10791
                gen_pool32fxf(env, ctx, rt, rs);
10792
                break;
10793
            case 0x00:
10794
                /* PLL foo */
10795
                switch ((ctx->opcode >> 6) & 0x7) {
10796
                case PLL_PS:
10797
                    mips32_op = OPC_PLL_PS;
10798
                    goto do_ps;
10799
                case PLU_PS:
10800
                    mips32_op = OPC_PLU_PS;
10801
                    goto do_ps;
10802
                case PUL_PS:
10803
                    mips32_op = OPC_PUL_PS;
10804
                    goto do_ps;
10805
                case PUU_PS:
10806
                    mips32_op = OPC_PUU_PS;
10807
                    goto do_ps;
10808
                case CVT_PS_S:
10809
                    mips32_op = OPC_CVT_PS_S;
10810
                do_ps:
10811
                    gen_farith(ctx, mips32_op, rt, rs, rd, 0);
10812
                    break;
10813
                default:
10814
                    goto pool32f_invalid;
10815
                }
10816
                break;
10817
            case 0x08:
10818
                /* [LS][WDU]XC1 */
10819
                switch ((ctx->opcode >> 6) & 0x7) {
10820
                case LWXC1:
10821
                    mips32_op = OPC_LWXC1;
10822
                    goto do_ldst_cp1;
10823
                case SWXC1:
10824
                    mips32_op = OPC_SWXC1;
10825
                    goto do_ldst_cp1;
10826
                case LDXC1:
10827
                    mips32_op = OPC_LDXC1;
10828
                    goto do_ldst_cp1;
10829
                case SDXC1:
10830
                    mips32_op = OPC_SDXC1;
10831
                    goto do_ldst_cp1;
10832
                case LUXC1:
10833
                    mips32_op = OPC_LUXC1;
10834
                    goto do_ldst_cp1;
10835
                case SUXC1:
10836
                    mips32_op = OPC_SUXC1;
10837
                do_ldst_cp1:
10838
                    gen_flt3_ldst(ctx, mips32_op, rd, rd, rt, rs);
10839
                    break;
10840
                default:
10841
                    goto pool32f_invalid;
10842
                }
10843
                break;
10844
            case 0x18:
10845
                /* 3D insns */
10846
                fmt = (ctx->opcode >> 9) & 0x3;
10847
                switch ((ctx->opcode >> 6) & 0x7) {
10848
                case RSQRT2_FMT:
10849
                    switch (fmt) {
10850
                    case FMT_SDPS_S:
10851
                        mips32_op = OPC_RSQRT2_S;
10852
                        goto do_3d;
10853
                    case FMT_SDPS_D:
10854
                        mips32_op = OPC_RSQRT2_D;
10855
                        goto do_3d;
10856
                    case FMT_SDPS_PS:
10857
                        mips32_op = OPC_RSQRT2_PS;
10858
                        goto do_3d;
10859
                    default:
10860
                        goto pool32f_invalid;
10861
                    }
10862
                    break;
10863
                case RECIP2_FMT:
10864
                    switch (fmt) {
10865
                    case FMT_SDPS_S:
10866
                        mips32_op = OPC_RECIP2_S;
10867
                        goto do_3d;
10868
                    case FMT_SDPS_D:
10869
                        mips32_op = OPC_RECIP2_D;
10870
                        goto do_3d;
10871
                    case FMT_SDPS_PS:
10872
                        mips32_op = OPC_RECIP2_PS;
10873
                        goto do_3d;
10874
                    default:
10875
                        goto pool32f_invalid;
10876
                    }
10877
                    break;
10878
                case ADDR_PS:
10879
                    mips32_op = OPC_ADDR_PS;
10880
                    goto do_3d;
10881
                case MULR_PS:
10882
                    mips32_op = OPC_MULR_PS;
10883
                do_3d:
10884
                    gen_farith(ctx, mips32_op, rt, rs, rd, 0);
10885
                    break;
10886
                default:
10887
                    goto pool32f_invalid;
10888
                }
10889
                break;
10890
            case 0x20:
10891
                /* MOV[FT].fmt and PREFX */
10892
                cc = (ctx->opcode >> 13) & 0x7;
10893
                fmt = (ctx->opcode >> 9) & 0x3;
10894
                switch ((ctx->opcode >> 6) & 0x7) {
10895
                case MOVF_FMT:
10896
                    switch (fmt) {
10897
                    case FMT_SDPS_S:
10898
                        gen_movcf_s(rs, rt, cc, 0);
10899
                        break;
10900
                    case FMT_SDPS_D:
10901
                        gen_movcf_d(ctx, rs, rt, cc, 0);
10902
                        break;
10903
                    case FMT_SDPS_PS:
10904
                        gen_movcf_ps(rs, rt, cc, 0);
10905
                        break;
10906
                    default:
10907
                        goto pool32f_invalid;
10908
                    }
10909
                    break;
10910
                case MOVT_FMT:
10911
                    switch (fmt) {
10912
                    case FMT_SDPS_S:
10913
                        gen_movcf_s(rs, rt, cc, 1);
10914
                        break;
10915
                    case FMT_SDPS_D:
10916
                        gen_movcf_d(ctx, rs, rt, cc, 1);
10917
                        break;
10918
                    case FMT_SDPS_PS:
10919
                        gen_movcf_ps(rs, rt, cc, 1);
10920
                        break;
10921
                    default:
10922
                        goto pool32f_invalid;
10923
                    }
10924
                    break;
10925
                case PREFX:
10926
                    break;
10927
                default:
10928
                    goto pool32f_invalid;
10929
                }
10930
                break;
10931
#define FINSN_3ARG_SDPS(prfx)                           \
10932
                switch ((ctx->opcode >> 8) & 0x3) {     \
10933
                case FMT_SDPS_S:                        \
10934
                    mips32_op = OPC_##prfx##_S;         \
10935
                    goto do_fpop;                       \
10936
                case FMT_SDPS_D:                        \
10937
                    mips32_op = OPC_##prfx##_D;         \
10938
                    goto do_fpop;                       \
10939
                case FMT_SDPS_PS:                       \
10940
                    mips32_op = OPC_##prfx##_PS;        \
10941
                    goto do_fpop;                       \
10942
                default:                                \
10943
                    goto pool32f_invalid;               \
10944
                }
10945
            case 0x30:
10946
                /* regular FP ops */
10947
                switch ((ctx->opcode >> 6) & 0x3) {
10948
                case ADD_FMT:
10949
                    FINSN_3ARG_SDPS(ADD);
10950
                    break;
10951
                case SUB_FMT:
10952
                    FINSN_3ARG_SDPS(SUB);
10953
                    break;
10954
                case MUL_FMT:
10955
                    FINSN_3ARG_SDPS(MUL);
10956
                    break;
10957
                case DIV_FMT:
10958
                    fmt = (ctx->opcode >> 8) & 0x3;
10959
                    if (fmt == 1) {
10960
                        mips32_op = OPC_DIV_D;
10961
                    } else if (fmt == 0) {
10962
                        mips32_op = OPC_DIV_S;
10963
                    } else {
10964
                        goto pool32f_invalid;
10965
                    }
10966
                    goto do_fpop;
10967
                default:
10968
                    goto pool32f_invalid;
10969
                }
10970
                break;
10971
            case 0x38:
10972
                /* cmovs */
10973
                switch ((ctx->opcode >> 6) & 0x3) {
10974
                case MOVN_FMT:
10975
                    FINSN_3ARG_SDPS(MOVN);
10976
                    break;
10977
                case MOVZ_FMT:
10978
                    FINSN_3ARG_SDPS(MOVZ);
10979
                    break;
10980
                default:
10981
                    goto pool32f_invalid;
10982
                }
10983
                break;
10984
            do_fpop:
10985
                gen_farith(ctx, mips32_op, rt, rs, rd, 0);
10986
                break;
10987
            default:
10988
            pool32f_invalid:
10989
                MIPS_INVAL("pool32f");
10990
                generate_exception(ctx, EXCP_RI);
10991
                break;
10992
            }
10993
        } else {
10994
            generate_exception_err(ctx, EXCP_CpU, 1);
10995
        }
10996
        break;
10997
    case POOL32I:
10998
        minor = (ctx->opcode >> 21) & 0x1f;
10999
        switch (minor) {
11000
        case BLTZ:
11001
            mips32_op = OPC_BLTZ;
11002
            goto do_branch;
11003
        case BLTZAL:
11004
            mips32_op = OPC_BLTZAL;
11005
            goto do_branch;
11006
        case BLTZALS:
11007
            mips32_op = OPC_BLTZALS;
11008
            goto do_branch;
11009
        case BGEZ:
11010
            mips32_op = OPC_BGEZ;
11011
            goto do_branch;
11012
        case BGEZAL:
11013
            mips32_op = OPC_BGEZAL;
11014
            goto do_branch;
11015
        case BGEZALS:
11016
            mips32_op = OPC_BGEZALS;
11017
            goto do_branch;
11018
        case BLEZ:
11019
            mips32_op = OPC_BLEZ;
11020
            goto do_branch;
11021
        case BGTZ:
11022
            mips32_op = OPC_BGTZ;
11023
        do_branch:
11024
            gen_compute_branch(ctx, mips32_op, 4, rs, -1, imm << 1);
11025
            *is_branch = 1;
11026
            break;
11027

    
11028
            /* Traps */
11029
        case TLTI:
11030
            mips32_op = OPC_TLTI;
11031
            goto do_trapi;
11032
        case TGEI:
11033
            mips32_op = OPC_TGEI;
11034
            goto do_trapi;
11035
        case TLTIU:
11036
            mips32_op = OPC_TLTIU;
11037
            goto do_trapi;
11038
        case TGEIU:
11039
            mips32_op = OPC_TGEIU;
11040
            goto do_trapi;
11041
        case TNEI:
11042
            mips32_op = OPC_TNEI;
11043
            goto do_trapi;
11044
        case TEQI:
11045
            mips32_op = OPC_TEQI;
11046
        do_trapi:
11047
            gen_trap(ctx, mips32_op, rs, -1, imm);
11048
            break;
11049

    
11050
        case BNEZC:
11051
        case BEQZC:
11052
            gen_compute_branch(ctx, minor == BNEZC ? OPC_BNE : OPC_BEQ,
11053
                               4, rs, 0, imm << 1);
11054
            /* Compact branches don't have a delay slot, so just let
11055
               the normal delay slot handling take us to the branch
11056
               target. */
11057
            break;
11058
        case LUI:
11059
            gen_logic_imm(env, OPC_LUI, rs, -1, imm);
11060
            break;
11061
        case SYNCI:
11062
            break;
11063
        case BC2F:
11064
        case BC2T:
11065
            /* COP2: Not implemented. */
11066
            generate_exception_err(ctx, EXCP_CpU, 2);
11067
            break;
11068
        case BC1F:
11069
            mips32_op = (ctx->opcode & (1 << 16)) ? OPC_BC1FANY2 : OPC_BC1F;
11070
            goto do_cp1branch;
11071
        case BC1T:
11072
            mips32_op = (ctx->opcode & (1 << 16)) ? OPC_BC1TANY2 : OPC_BC1T;
11073
            goto do_cp1branch;
11074
        case BC1ANY4F:
11075
            mips32_op = OPC_BC1FANY4;
11076
            goto do_cp1mips3d;
11077
        case BC1ANY4T:
11078
            mips32_op = OPC_BC1TANY4;
11079
        do_cp1mips3d:
11080
            check_cop1x(ctx);
11081
            check_insn(env, ctx, ASE_MIPS3D);
11082
            /* Fall through */
11083
        do_cp1branch:
11084
            gen_compute_branch1(env, ctx, mips32_op,
11085
                                (ctx->opcode >> 18) & 0x7, imm << 1);
11086
            *is_branch = 1;
11087
            break;
11088
        case BPOSGE64:
11089
        case BPOSGE32:
11090
            /* MIPS DSP: not implemented */
11091
            /* Fall through */
11092
        default:
11093
            MIPS_INVAL("pool32i");
11094
            generate_exception(ctx, EXCP_RI);
11095
            break;
11096
        }
11097
        break;
11098
    case POOL32C:
11099
        minor = (ctx->opcode >> 12) & 0xf;
11100
        switch (minor) {
11101
        case LWL:
11102
            mips32_op = OPC_LWL;
11103
            goto do_ld_lr;
11104
        case SWL:
11105
            mips32_op = OPC_SWL;
11106
            goto do_st_lr;
11107
        case LWR:
11108
            mips32_op = OPC_LWR;
11109
            goto do_ld_lr;
11110
        case SWR:
11111
            mips32_op = OPC_SWR;
11112
            goto do_st_lr;
11113
#if defined(TARGET_MIPS64)
11114
        case LDL:
11115
            mips32_op = OPC_LDL;
11116
            goto do_ld_lr;
11117
        case SDL:
11118
            mips32_op = OPC_SDL;
11119
            goto do_st_lr;
11120
        case LDR:
11121
            mips32_op = OPC_LDR;
11122
            goto do_ld_lr;
11123
        case SDR:
11124
            mips32_op = OPC_SDR;
11125
            goto do_st_lr;
11126
        case LWU:
11127
            mips32_op = OPC_LWU;
11128
            goto do_ld_lr;
11129
        case LLD:
11130
            mips32_op = OPC_LLD;
11131
            goto do_ld_lr;
11132
#endif
11133
        case LL:
11134
            mips32_op = OPC_LL;
11135
            goto do_ld_lr;
11136
        do_ld_lr:
11137
            gen_ld(env, ctx, mips32_op, rt, rs, SIMM(ctx->opcode, 0, 12));
11138
            break;
11139
        do_st_lr:
11140
            gen_st(ctx, mips32_op, rt, rs, SIMM(ctx->opcode, 0, 12));
11141
            break;
11142
        case SC:
11143
            gen_st_cond(ctx, OPC_SC, rt, rs, SIMM(ctx->opcode, 0, 12));
11144
            break;
11145
#if defined(TARGET_MIPS64)
11146
        case SCD:
11147
            gen_st_cond(ctx, OPC_SCD, rt, rs, SIMM(ctx->opcode, 0, 12));
11148
            break;
11149
#endif
11150
        case PREF:
11151
            /* Treat as no-op */
11152
            break;
11153
        default:
11154
            MIPS_INVAL("pool32c");
11155
            generate_exception(ctx, EXCP_RI);
11156
            break;
11157
        }
11158
        break;
11159
    case ADDI32:
11160
        mips32_op = OPC_ADDI;
11161
        goto do_addi;
11162
    case ADDIU32:
11163
        mips32_op = OPC_ADDIU;
11164
    do_addi:
11165
        gen_arith_imm(env, ctx, mips32_op, rt, rs, imm);
11166
        break;
11167

    
11168
        /* Logical operations */
11169
    case ORI32:
11170
        mips32_op = OPC_ORI;
11171
        goto do_logici;
11172
    case XORI32:
11173
        mips32_op = OPC_XORI;
11174
        goto do_logici;
11175
    case ANDI32:
11176
        mips32_op = OPC_ANDI;
11177
    do_logici:
11178
        gen_logic_imm(env, mips32_op, rt, rs, imm);
11179
        break;
11180

    
11181
        /* Set less than immediate */
11182
    case SLTI32:
11183
        mips32_op = OPC_SLTI;
11184
        goto do_slti;
11185
    case SLTIU32:
11186
        mips32_op = OPC_SLTIU;
11187
    do_slti:
11188
        gen_slt_imm(env, mips32_op, rt, rs, imm);
11189
        break;
11190
    case JALX32:
11191
        offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
11192
        gen_compute_branch(ctx, OPC_JALX, 4, rt, rs, offset);
11193
        *is_branch = 1;
11194
        break;
11195
    case JALS32:
11196
        offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 1;
11197
        gen_compute_branch(ctx, OPC_JALS, 4, rt, rs, offset);
11198
        *is_branch = 1;
11199
        break;
11200
    case BEQ32:
11201
        gen_compute_branch(ctx, OPC_BEQ, 4, rt, rs, imm << 1);
11202
        *is_branch = 1;
11203
        break;
11204
    case BNE32:
11205
        gen_compute_branch(ctx, OPC_BNE, 4, rt, rs, imm << 1);
11206
        *is_branch = 1;
11207
        break;
11208
    case J32:
11209
        gen_compute_branch(ctx, OPC_J, 4, rt, rs,
11210
                           (int32_t)(ctx->opcode & 0x3FFFFFF) << 1);
11211
        *is_branch = 1;
11212
        break;
11213
    case JAL32:
11214
        gen_compute_branch(ctx, OPC_JAL, 4, rt, rs,
11215
                           (int32_t)(ctx->opcode & 0x3FFFFFF) << 1);
11216
        *is_branch = 1;
11217
        break;
11218
        /* Floating point (COP1) */
11219
    case LWC132:
11220
        mips32_op = OPC_LWC1;
11221
        goto do_cop1;
11222
    case LDC132:
11223
        mips32_op = OPC_LDC1;
11224
        goto do_cop1;
11225
    case SWC132:
11226
        mips32_op = OPC_SWC1;
11227
        goto do_cop1;
11228
    case SDC132:
11229
        mips32_op = OPC_SDC1;
11230
    do_cop1:
11231
        gen_cop1_ldst(env, ctx, mips32_op, rt, rs, imm);
11232
        break;
11233
    case ADDIUPC:
11234
        {
11235
            int reg = mmreg(ZIMM(ctx->opcode, 23, 3));
11236
            int offset = SIMM(ctx->opcode, 0, 23) << 2;
11237

    
11238
            gen_addiupc(ctx, reg, offset, 0, 0);
11239
        }
11240
        break;
11241
        /* Loads and stores */
11242
    case LB32:
11243
        mips32_op = OPC_LB;
11244
        goto do_ld;
11245
    case LBU32:
11246
        mips32_op = OPC_LBU;
11247
        goto do_ld;
11248
    case LH32:
11249
        mips32_op = OPC_LH;
11250
        goto do_ld;
11251
    case LHU32:
11252
        mips32_op = OPC_LHU;
11253
        goto do_ld;
11254
    case LW32:
11255
        mips32_op = OPC_LW;
11256
        goto do_ld;
11257
#ifdef TARGET_MIPS64
11258
    case LD32:
11259
        mips32_op = OPC_LD;
11260
        goto do_ld;
11261
    case SD32:
11262
        mips32_op = OPC_SD;
11263
        goto do_st;
11264
#endif
11265
    case SB32:
11266
        mips32_op = OPC_SB;
11267
        goto do_st;
11268
    case SH32:
11269
        mips32_op = OPC_SH;
11270
        goto do_st;
11271
    case SW32:
11272
        mips32_op = OPC_SW;
11273
        goto do_st;
11274
    do_ld:
11275
        gen_ld(env, ctx, mips32_op, rt, rs, imm);
11276
        break;
11277
    do_st:
11278
        gen_st(ctx, mips32_op, rt, rs, imm);
11279
        break;
11280
    default:
11281
        generate_exception(ctx, EXCP_RI);
11282
        break;
11283
    }
11284
}
11285

    
11286
static int decode_micromips_opc (CPUState *env, DisasContext *ctx, int *is_branch)
11287
{
11288
    uint32_t op;
11289

    
11290
    /* make sure instructions are on a halfword boundary */
11291
    if (ctx->pc & 0x1) {
11292
        env->CP0_BadVAddr = ctx->pc;
11293
        generate_exception(ctx, EXCP_AdEL);
11294
        ctx->bstate = BS_STOP;
11295
        return 2;
11296
    }
11297

    
11298
    op = (ctx->opcode >> 10) & 0x3f;
11299
    /* Enforce properly-sized instructions in a delay slot */
11300
    if (ctx->hflags & MIPS_HFLAG_BMASK) {
11301
        int bits = ctx->hflags & MIPS_HFLAG_BMASK_EXT;
11302

    
11303
        switch (op) {
11304
        case POOL32A:
11305
        case POOL32B:
11306
        case POOL32I:
11307
        case POOL32C:
11308
        case ADDI32:
11309
        case ADDIU32:
11310
        case ORI32:
11311
        case XORI32:
11312
        case SLTI32:
11313
        case SLTIU32:
11314
        case ANDI32:
11315
        case JALX32:
11316
        case LBU32:
11317
        case LHU32:
11318
        case POOL32F:
11319
        case JALS32:
11320
        case BEQ32:
11321
        case BNE32:
11322
        case J32:
11323
        case JAL32:
11324
        case SB32:
11325
        case SH32:
11326
        case POOL32S:
11327
        case ADDIUPC:
11328
        case SWC132:
11329
        case SDC132:
11330
        case SD32:
11331
        case SW32:
11332
        case LB32:
11333
        case LH32:
11334
        case DADDIU32:
11335
        case POOL48A:           /* ??? */
11336
        case LWC132:
11337
        case LDC132:
11338
        case LD32:
11339
        case LW32:
11340
            if (bits & MIPS_HFLAG_BDS16) {
11341
                generate_exception(ctx, EXCP_RI);
11342
                /* Just stop translation; the user is confused.  */
11343
                ctx->bstate = BS_STOP;
11344
                return 2;
11345
            }
11346
            break;
11347
        case POOL16A:
11348
        case POOL16B:
11349
        case POOL16C:
11350
        case LWGP16:
11351
        case POOL16F:
11352
        case LBU16:
11353
        case LHU16:
11354
        case LWSP16:
11355
        case LW16:
11356
        case SB16:
11357
        case SH16:
11358
        case SWSP16:
11359
        case SW16:
11360
        case MOVE16:
11361
        case ANDI16:
11362
        case POOL16D:
11363
        case POOL16E:
11364
        case BEQZ16:
11365
        case BNEZ16:
11366
        case B16:
11367
        case LI16:
11368
            if (bits & MIPS_HFLAG_BDS32) {
11369
                generate_exception(ctx, EXCP_RI);
11370
                /* Just stop translation; the user is confused.  */
11371
                ctx->bstate = BS_STOP;
11372
                return 2;
11373
            }
11374
            break;
11375
        default:
11376
            break;
11377
        }
11378
    }
11379
    switch (op) {
11380
    case POOL16A:
11381
        {
11382
            int rd = mmreg(uMIPS_RD(ctx->opcode));
11383
            int rs1 = mmreg(uMIPS_RS1(ctx->opcode));
11384
            int rs2 = mmreg(uMIPS_RS2(ctx->opcode));
11385
            uint32_t opc = 0;
11386

    
11387
            switch (ctx->opcode & 0x1) {
11388
            case ADDU16:
11389
                opc = OPC_ADDU;
11390
                break;
11391
            case SUBU16:
11392
                opc = OPC_SUBU;
11393
                break;
11394
            }
11395

    
11396
            gen_arith(env, ctx, opc, rd, rs1, rs2);
11397
        }
11398
        break;
11399
    case POOL16B:
11400
        {
11401
            int rd = mmreg(uMIPS_RD(ctx->opcode));
11402
            int rs = mmreg(uMIPS_RS(ctx->opcode));
11403
            int amount = (ctx->opcode >> 1) & 0x7;
11404
            uint32_t opc = 0;
11405
            amount = amount == 0 ? 8 : amount;
11406

    
11407
            switch (ctx->opcode & 0x1) {
11408
            case SLL16:
11409
                opc = OPC_SLL;
11410
                break;
11411
            case SRL16:
11412
                opc = OPC_SRL;
11413
                break;
11414
            }
11415

    
11416
            gen_shift_imm(env, ctx, opc, rd, rs, amount);
11417
        }
11418
        break;
11419
    case POOL16C:
11420
        gen_pool16c_insn(env, ctx, is_branch);
11421
        break;
11422
    case LWGP16:
11423
        {
11424
            int rd = mmreg(uMIPS_RD(ctx->opcode));
11425
            int rb = 28;            /* GP */
11426
            int16_t offset = SIMM(ctx->opcode, 0, 7) << 2;
11427

    
11428
            gen_ld(env, ctx, OPC_LW, rd, rb, offset);
11429
        }
11430
        break;
11431
    case POOL16F:
11432
        if (ctx->opcode & 1) {
11433
            generate_exception(ctx, EXCP_RI);
11434
        } else {
11435
            /* MOVEP */
11436
            int enc_dest = uMIPS_RD(ctx->opcode);
11437
            int enc_rt = uMIPS_RS2(ctx->opcode);
11438
            int enc_rs = uMIPS_RS1(ctx->opcode);
11439
            int rd, rs, re, rt;
11440
            static const int rd_enc[] = { 5, 5, 6, 4, 4, 4, 4, 4 };
11441
            static const int re_enc[] = { 6, 7, 7, 21, 22, 5, 6, 7 };
11442
            static const int rs_rt_enc[] = { 0, 17, 2, 3, 16, 18, 19, 20 };
11443

    
11444
            rd = rd_enc[enc_dest];
11445
            re = re_enc[enc_dest];
11446
            rs = rs_rt_enc[enc_rs];
11447
            rt = rs_rt_enc[enc_rt];
11448

    
11449
            gen_arith_imm(env, ctx, OPC_ADDIU, rd, rs, 0);
11450
            gen_arith_imm(env, ctx, OPC_ADDIU, re, rt, 0);
11451
        }
11452
        break;
11453
    case LBU16:
11454
        {
11455
            int rd = mmreg(uMIPS_RD(ctx->opcode));
11456
            int rb = mmreg(uMIPS_RS(ctx->opcode));
11457
            int16_t offset = ZIMM(ctx->opcode, 0, 4);
11458
            offset = (offset == 0xf ? -1 : offset);
11459

    
11460
            gen_ld(env, ctx, OPC_LBU, rd, rb, offset);
11461
        }
11462
        break;
11463
    case LHU16:
11464
        {
11465
            int rd = mmreg(uMIPS_RD(ctx->opcode));
11466
            int rb = mmreg(uMIPS_RS(ctx->opcode));
11467
            int16_t offset = ZIMM(ctx->opcode, 0, 4) << 1;
11468

    
11469
            gen_ld(env, ctx, OPC_LHU, rd, rb, offset);
11470
        }
11471
        break;
11472
    case LWSP16:
11473
        {
11474
            int rd = (ctx->opcode >> 5) & 0x1f;
11475
            int rb = 29;            /* SP */
11476
            int16_t offset = ZIMM(ctx->opcode, 0, 5) << 2;
11477

    
11478
            gen_ld(env, ctx, OPC_LW, rd, rb, offset);
11479
        }
11480
        break;
11481
    case LW16:
11482
        {
11483
            int rd = mmreg(uMIPS_RD(ctx->opcode));
11484
            int rb = mmreg(uMIPS_RS(ctx->opcode));
11485
            int16_t offset = ZIMM(ctx->opcode, 0, 4) << 2;
11486

    
11487
            gen_ld(env, ctx, OPC_LW, rd, rb, offset);
11488
        }
11489
        break;
11490
    case SB16:
11491
        {
11492
            int rd = mmreg2(uMIPS_RD(ctx->opcode));
11493
            int rb = mmreg(uMIPS_RS(ctx->opcode));
11494
            int16_t offset = ZIMM(ctx->opcode, 0, 4);
11495

    
11496
            gen_st(ctx, OPC_SB, rd, rb, offset);
11497
        }
11498
        break;
11499
    case SH16:
11500
        {
11501
            int rd = mmreg2(uMIPS_RD(ctx->opcode));
11502
            int rb = mmreg(uMIPS_RS(ctx->opcode));
11503
            int16_t offset = ZIMM(ctx->opcode, 0, 4) << 1;
11504

    
11505
            gen_st(ctx, OPC_SH, rd, rb, offset);
11506
        }
11507
        break;
11508
    case SWSP16:
11509
        {
11510
            int rd = (ctx->opcode >> 5) & 0x1f;
11511
            int rb = 29;            /* SP */
11512
            int16_t offset = ZIMM(ctx->opcode, 0, 5) << 2;
11513

    
11514
            gen_st(ctx, OPC_SW, rd, rb, offset);
11515
        }
11516
        break;
11517
    case SW16:
11518
        {
11519
            int rd = mmreg2(uMIPS_RD(ctx->opcode));
11520
            int rb = mmreg(uMIPS_RS(ctx->opcode));
11521
            int16_t offset = ZIMM(ctx->opcode, 0, 4) << 2;
11522

    
11523
            gen_st(ctx, OPC_SW, rd, rb, offset);
11524
        }
11525
        break;
11526
    case MOVE16:
11527
        {
11528
            int rd = uMIPS_RD5(ctx->opcode);
11529
            int rs = uMIPS_RS5(ctx->opcode);
11530

    
11531
            gen_arith_imm(env, ctx, OPC_ADDIU, rd, rs, 0);
11532
        }
11533
        break;
11534
    case ANDI16:
11535
        gen_andi16(env, ctx);
11536
        break;
11537
    case POOL16D:
11538
        switch (ctx->opcode & 0x1) {
11539
        case ADDIUS5:
11540
            gen_addius5(env, ctx);
11541
            break;
11542
        case ADDIUSP:
11543
            gen_addiusp(env, ctx);
11544
            break;
11545
        }
11546
        break;
11547
    case POOL16E:
11548
        switch (ctx->opcode & 0x1) {
11549
        case ADDIUR2:
11550
            gen_addiur2(env, ctx);
11551
            break;
11552
        case ADDIUR1SP:
11553
            gen_addiur1sp(env, ctx);
11554
            break;
11555
        }
11556
        break;
11557
    case B16:
11558
        gen_compute_branch(ctx, OPC_BEQ, 2, 0, 0,
11559
                           SIMM(ctx->opcode, 0, 10) << 1);
11560
        *is_branch = 1;
11561
        break;
11562
    case BNEZ16:
11563
    case BEQZ16:
11564
        gen_compute_branch(ctx, op == BNEZ16 ? OPC_BNE : OPC_BEQ, 2,
11565
                           mmreg(uMIPS_RD(ctx->opcode)),
11566
                           0, SIMM(ctx->opcode, 0, 7) << 1);
11567
        *is_branch = 1;
11568
        break;
11569
    case LI16:
11570
        {
11571
            int reg = mmreg(uMIPS_RD(ctx->opcode));
11572
            int imm = ZIMM(ctx->opcode, 0, 7);
11573

    
11574
            imm = (imm == 0x7f ? -1 : imm);
11575
            tcg_gen_movi_tl(cpu_gpr[reg], imm);
11576
        }
11577
        break;
11578
    case RES_20:
11579
    case RES_28:
11580
    case RES_29:
11581
    case RES_30:
11582
    case RES_31:
11583
    case RES_38:
11584
    case RES_39:
11585
        generate_exception(ctx, EXCP_RI);
11586
        break;
11587
    default:
11588
        decode_micromips32_opc (env, ctx, op, is_branch);
11589
        return 4;
11590
    }
11591

    
11592
    return 2;
11593
}
11594

    
11595
/* SmartMIPS extension to MIPS32 */
11596

    
11597
#if defined(TARGET_MIPS64)
11598

    
11599
/* MDMX extension to MIPS64 */
11600

    
11601
#endif
11602

    
11603
static void decode_opc (CPUState *env, DisasContext *ctx, int *is_branch)
11604
{
11605
    int32_t offset;
11606
    int rs, rt, rd, sa;
11607
    uint32_t op, op1, op2;
11608
    int16_t imm;
11609

    
11610
    /* make sure instructions are on a word boundary */
11611
    if (ctx->pc & 0x3) {
11612
        env->CP0_BadVAddr = ctx->pc;
11613
        generate_exception(ctx, EXCP_AdEL);
11614
        return;
11615
    }
11616

    
11617
    /* Handle blikely not taken case */
11618
    if ((ctx->hflags & MIPS_HFLAG_BMASK_BASE) == MIPS_HFLAG_BL) {
11619
        int l1 = gen_new_label();
11620

    
11621
        MIPS_DEBUG("blikely condition (" TARGET_FMT_lx ")", ctx->pc + 4);
11622
        tcg_gen_brcondi_tl(TCG_COND_NE, bcond, 0, l1);
11623
        tcg_gen_movi_i32(hflags, ctx->hflags & ~MIPS_HFLAG_BMASK);
11624
        gen_goto_tb(ctx, 1, ctx->pc + 4);
11625
        gen_set_label(l1);
11626
    }
11627

    
11628
    if (unlikely(qemu_loglevel_mask(CPU_LOG_TB_OP)))
11629
        tcg_gen_debug_insn_start(ctx->pc);
11630

    
11631
    op = MASK_OP_MAJOR(ctx->opcode);
11632
    rs = (ctx->opcode >> 21) & 0x1f;
11633
    rt = (ctx->opcode >> 16) & 0x1f;
11634
    rd = (ctx->opcode >> 11) & 0x1f;
11635
    sa = (ctx->opcode >> 6) & 0x1f;
11636
    imm = (int16_t)ctx->opcode;
11637
    switch (op) {
11638
    case OPC_SPECIAL:
11639
        op1 = MASK_SPECIAL(ctx->opcode);
11640
        switch (op1) {
11641
        case OPC_SLL:          /* Shift with immediate */
11642
        case OPC_SRA:
11643
            gen_shift_imm(env, ctx, op1, rd, rt, sa);
11644
            break;
11645
        case OPC_SRL:
11646
            switch ((ctx->opcode >> 21) & 0x1f) {
11647
            case 1:
11648
                /* rotr is decoded as srl on non-R2 CPUs */
11649
                if (env->insn_flags & ISA_MIPS32R2) {
11650
                    op1 = OPC_ROTR;
11651
                }
11652
                /* Fallthrough */
11653
            case 0:
11654
                gen_shift_imm(env, ctx, op1, rd, rt, sa);
11655
                break;
11656
            default:
11657
                generate_exception(ctx, EXCP_RI);
11658
                break;
11659
            }
11660
            break;
11661
        case OPC_MOVN:         /* Conditional move */
11662
        case OPC_MOVZ:
11663
            check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32 |
11664
                                 INSN_LOONGSON2E | INSN_LOONGSON2F);
11665
            gen_cond_move(env, op1, rd, rs, rt);
11666
            break;
11667
        case OPC_ADD ... OPC_SUBU:
11668
            gen_arith(env, ctx, op1, rd, rs, rt);
11669
            break;
11670
        case OPC_SLLV:         /* Shifts */
11671
        case OPC_SRAV:
11672
            gen_shift(env, ctx, op1, rd, rs, rt);
11673
            break;
11674
        case OPC_SRLV:
11675
            switch ((ctx->opcode >> 6) & 0x1f) {
11676
            case 1:
11677
                /* rotrv is decoded as srlv on non-R2 CPUs */
11678
                if (env->insn_flags & ISA_MIPS32R2) {
11679
                    op1 = OPC_ROTRV;
11680
                }
11681
                /* Fallthrough */
11682
            case 0:
11683
                gen_shift(env, ctx, op1, rd, rs, rt);
11684
                break;
11685
            default:
11686
                generate_exception(ctx, EXCP_RI);
11687
                break;
11688
            }
11689
            break;
11690
        case OPC_SLT:          /* Set on less than */
11691
        case OPC_SLTU:
11692
            gen_slt(env, op1, rd, rs, rt);
11693
            break;
11694
        case OPC_AND:          /* Logic*/
11695
        case OPC_OR:
11696
        case OPC_NOR:
11697
        case OPC_XOR:
11698
            gen_logic(env, op1, rd, rs, rt);
11699
            break;
11700
        case OPC_MULT ... OPC_DIVU:
11701
            if (sa) {
11702
                check_insn(env, ctx, INSN_VR54XX);
11703
                op1 = MASK_MUL_VR54XX(ctx->opcode);
11704
                gen_mul_vr54xx(ctx, op1, rd, rs, rt);
11705
            } else
11706
                gen_muldiv(ctx, op1, rs, rt);
11707
            break;
11708
        case OPC_JR ... OPC_JALR:
11709
            gen_compute_branch(ctx, op1, 4, rs, rd, sa);
11710
            *is_branch = 1;
11711
            break;
11712
        case OPC_TGE ... OPC_TEQ: /* Traps */
11713
        case OPC_TNE:
11714
            gen_trap(ctx, op1, rs, rt, -1);
11715
            break;
11716
        case OPC_MFHI:          /* Move from HI/LO */
11717
        case OPC_MFLO:
11718
            gen_HILO(ctx, op1, rd);
11719
            break;
11720
        case OPC_MTHI:
11721
        case OPC_MTLO:          /* Move to HI/LO */
11722
            gen_HILO(ctx, op1, rs);
11723
            break;
11724
        case OPC_PMON:          /* Pmon entry point, also R4010 selsl */
11725
#ifdef MIPS_STRICT_STANDARD
11726
            MIPS_INVAL("PMON / selsl");
11727
            generate_exception(ctx, EXCP_RI);
11728
#else
11729
            gen_helper_0i(pmon, sa);
11730
#endif
11731
            break;
11732
        case OPC_SYSCALL:
11733
            generate_exception(ctx, EXCP_SYSCALL);
11734
            ctx->bstate = BS_STOP;
11735
            break;
11736
        case OPC_BREAK:
11737
            generate_exception(ctx, EXCP_BREAK);
11738
            break;
11739
        case OPC_SPIM:
11740
#ifdef MIPS_STRICT_STANDARD
11741
            MIPS_INVAL("SPIM");
11742
            generate_exception(ctx, EXCP_RI);
11743
#else
11744
           /* Implemented as RI exception for now. */
11745
            MIPS_INVAL("spim (unofficial)");
11746
            generate_exception(ctx, EXCP_RI);
11747
#endif
11748
            break;
11749
        case OPC_SYNC:
11750
            /* Treat as NOP. */
11751
            break;
11752

    
11753
        case OPC_MOVCI:
11754
            check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
11755
            if (env->CP0_Config1 & (1 << CP0C1_FP)) {
11756
                check_cp1_enabled(ctx);
11757
                gen_movci(ctx, rd, rs, (ctx->opcode >> 18) & 0x7,
11758
                          (ctx->opcode >> 16) & 1);
11759
            } else {
11760
                generate_exception_err(ctx, EXCP_CpU, 1);
11761
            }
11762
            break;
11763

    
11764
#if defined(TARGET_MIPS64)
11765
       /* MIPS64 specific opcodes */
11766
        case OPC_DSLL:
11767
        case OPC_DSRA:
11768
        case OPC_DSLL32:
11769
        case OPC_DSRA32:
11770
            check_insn(env, ctx, ISA_MIPS3);
11771
            check_mips_64(ctx);
11772
            gen_shift_imm(env, ctx, op1, rd, rt, sa);
11773
            break;
11774
        case OPC_DSRL:
11775
            switch ((ctx->opcode >> 21) & 0x1f) {
11776
            case 1:
11777
                /* drotr is decoded as dsrl on non-R2 CPUs */
11778
                if (env->insn_flags & ISA_MIPS32R2) {
11779
                    op1 = OPC_DROTR;
11780
                }
11781
                /* Fallthrough */
11782
            case 0:
11783
                check_insn(env, ctx, ISA_MIPS3);
11784
                check_mips_64(ctx);
11785
                gen_shift_imm(env, ctx, op1, rd, rt, sa);
11786
                break;
11787
            default:
11788
                generate_exception(ctx, EXCP_RI);
11789
                break;
11790
            }
11791
            break;
11792
        case OPC_DSRL32:
11793
            switch ((ctx->opcode >> 21) & 0x1f) {
11794
            case 1:
11795
                /* drotr32 is decoded as dsrl32 on non-R2 CPUs */
11796
                if (env->insn_flags & ISA_MIPS32R2) {
11797
                    op1 = OPC_DROTR32;
11798
                }
11799
                /* Fallthrough */
11800
            case 0:
11801
                check_insn(env, ctx, ISA_MIPS3);
11802
                check_mips_64(ctx);
11803
                gen_shift_imm(env, ctx, op1, rd, rt, sa);
11804
                break;
11805
            default:
11806
                generate_exception(ctx, EXCP_RI);
11807
                break;
11808
            }
11809
            break;
11810
        case OPC_DADD ... OPC_DSUBU:
11811
            check_insn(env, ctx, ISA_MIPS3);
11812
            check_mips_64(ctx);
11813
            gen_arith(env, ctx, op1, rd, rs, rt);
11814
            break;
11815
        case OPC_DSLLV:
11816
        case OPC_DSRAV:
11817
            check_insn(env, ctx, ISA_MIPS3);
11818
            check_mips_64(ctx);
11819
            gen_shift(env, ctx, op1, rd, rs, rt);
11820
            break;
11821
        case OPC_DSRLV:
11822
            switch ((ctx->opcode >> 6) & 0x1f) {
11823
            case 1:
11824
                /* drotrv is decoded as dsrlv on non-R2 CPUs */
11825
                if (env->insn_flags & ISA_MIPS32R2) {
11826
                    op1 = OPC_DROTRV;
11827
                }
11828
                /* Fallthrough */
11829
            case 0:
11830
                check_insn(env, ctx, ISA_MIPS3);
11831
                check_mips_64(ctx);
11832
                gen_shift(env, ctx, op1, rd, rs, rt);
11833
                break;
11834
            default:
11835
                generate_exception(ctx, EXCP_RI);
11836
                break;
11837
            }
11838
            break;
11839
        case OPC_DMULT ... OPC_DDIVU:
11840
            check_insn(env, ctx, ISA_MIPS3);
11841
            check_mips_64(ctx);
11842
            gen_muldiv(ctx, op1, rs, rt);
11843
            break;
11844
#endif
11845
        default:            /* Invalid */
11846
            MIPS_INVAL("special");
11847
            generate_exception(ctx, EXCP_RI);
11848
            break;
11849
        }
11850
        break;
11851
    case OPC_SPECIAL2:
11852
        op1 = MASK_SPECIAL2(ctx->opcode);
11853
        switch (op1) {
11854
        case OPC_MADD ... OPC_MADDU: /* Multiply and add/sub */
11855
        case OPC_MSUB ... OPC_MSUBU:
11856
            check_insn(env, ctx, ISA_MIPS32);
11857
            gen_muldiv(ctx, op1, rs, rt);
11858
            break;
11859
        case OPC_MUL:
11860
            gen_arith(env, ctx, op1, rd, rs, rt);
11861
            break;
11862
        case OPC_CLO:
11863
        case OPC_CLZ:
11864
            check_insn(env, ctx, ISA_MIPS32);
11865
            gen_cl(ctx, op1, rd, rs);
11866
            break;
11867
        case OPC_SDBBP:
11868
            /* XXX: not clear which exception should be raised
11869
             *      when in debug mode...
11870
             */
11871
            check_insn(env, ctx, ISA_MIPS32);
11872
            if (!(ctx->hflags & MIPS_HFLAG_DM)) {
11873
                generate_exception(ctx, EXCP_DBp);
11874
            } else {
11875
                generate_exception(ctx, EXCP_DBp);
11876
            }
11877
            /* Treat as NOP. */
11878
            break;
11879
        case OPC_DIV_G_2F:
11880
        case OPC_DIVU_G_2F:
11881
        case OPC_MULT_G_2F:
11882
        case OPC_MULTU_G_2F:
11883
        case OPC_MOD_G_2F:
11884
        case OPC_MODU_G_2F:
11885
            check_insn(env, ctx, INSN_LOONGSON2F);
11886
            gen_loongson_integer(ctx, op1, rd, rs, rt);
11887
            break;
11888
#if defined(TARGET_MIPS64)
11889
        case OPC_DCLO:
11890
        case OPC_DCLZ:
11891
            check_insn(env, ctx, ISA_MIPS64);
11892
            check_mips_64(ctx);
11893
            gen_cl(ctx, op1, rd, rs);
11894
            break;
11895
        case OPC_DMULT_G_2F:
11896
        case OPC_DMULTU_G_2F:
11897
        case OPC_DDIV_G_2F:
11898
        case OPC_DDIVU_G_2F:
11899
        case OPC_DMOD_G_2F:
11900
        case OPC_DMODU_G_2F:
11901
            check_insn(env, ctx, INSN_LOONGSON2F);
11902
            gen_loongson_integer(ctx, op1, rd, rs, rt);
11903
            break;
11904
#endif
11905
        default:            /* Invalid */
11906
            MIPS_INVAL("special2");
11907
            generate_exception(ctx, EXCP_RI);
11908
            break;
11909
        }
11910
        break;
11911
    case OPC_SPECIAL3:
11912
        op1 = MASK_SPECIAL3(ctx->opcode);
11913
        switch (op1) {
11914
        case OPC_EXT:
11915
        case OPC_INS:
11916
            check_insn(env, ctx, ISA_MIPS32R2);
11917
            gen_bitops(ctx, op1, rt, rs, sa, rd);
11918
            break;
11919
        case OPC_BSHFL:
11920
            check_insn(env, ctx, ISA_MIPS32R2);
11921
            op2 = MASK_BSHFL(ctx->opcode);
11922
            gen_bshfl(ctx, op2, rt, rd);
11923
            break;
11924
        case OPC_RDHWR:
11925
            gen_rdhwr(env, ctx, rt, rd);
11926
            break;
11927
        case OPC_FORK:
11928
            check_insn(env, ctx, ASE_MT);
11929
            {
11930
                TCGv t0 = tcg_temp_new();
11931
                TCGv t1 = tcg_temp_new();
11932

    
11933
                gen_load_gpr(t0, rt);
11934
                gen_load_gpr(t1, rs);
11935
                gen_helper_fork(t0, t1);
11936
                tcg_temp_free(t0);
11937
                tcg_temp_free(t1);
11938
            }
11939
            break;
11940
        case OPC_YIELD:
11941
            check_insn(env, ctx, ASE_MT);
11942
            {
11943
                TCGv t0 = tcg_temp_new();
11944

    
11945
                save_cpu_state(ctx, 1);
11946
                gen_load_gpr(t0, rs);
11947
                gen_helper_yield(t0, t0);
11948
                gen_store_gpr(t0, rd);
11949
                tcg_temp_free(t0);
11950
            }
11951
            break;
11952
        case OPC_DIV_G_2E ... OPC_DIVU_G_2E:
11953
        case OPC_MULT_G_2E ... OPC_MULTU_G_2E:
11954
        case OPC_MOD_G_2E ... OPC_MODU_G_2E:
11955
            check_insn(env, ctx, INSN_LOONGSON2E);
11956
            gen_loongson_integer(ctx, op1, rd, rs, rt);
11957
            break;
11958
#if defined(TARGET_MIPS64)
11959
        case OPC_DEXTM ... OPC_DEXT:
11960
        case OPC_DINSM ... OPC_DINS:
11961
            check_insn(env, ctx, ISA_MIPS64R2);
11962
            check_mips_64(ctx);
11963
            gen_bitops(ctx, op1, rt, rs, sa, rd);
11964
            break;
11965
        case OPC_DBSHFL:
11966
            check_insn(env, ctx, ISA_MIPS64R2);
11967
            check_mips_64(ctx);
11968
            op2 = MASK_DBSHFL(ctx->opcode);
11969
            gen_bshfl(ctx, op2, rt, rd);
11970
            break;
11971
        case OPC_DDIV_G_2E ... OPC_DDIVU_G_2E:
11972
        case OPC_DMULT_G_2E ... OPC_DMULTU_G_2E:
11973
        case OPC_DMOD_G_2E ... OPC_DMODU_G_2E:
11974
            check_insn(env, ctx, INSN_LOONGSON2E);
11975
            gen_loongson_integer(ctx, op1, rd, rs, rt);
11976
            break;
11977
#endif
11978
        default:            /* Invalid */
11979
            MIPS_INVAL("special3");
11980
            generate_exception(ctx, EXCP_RI);
11981
            break;
11982
        }
11983
        break;
11984
    case OPC_REGIMM:
11985
        op1 = MASK_REGIMM(ctx->opcode);
11986
        switch (op1) {
11987
        case OPC_BLTZ ... OPC_BGEZL: /* REGIMM branches */
11988
        case OPC_BLTZAL ... OPC_BGEZALL:
11989
            gen_compute_branch(ctx, op1, 4, rs, -1, imm << 2);
11990
            *is_branch = 1;
11991
            break;
11992
        case OPC_TGEI ... OPC_TEQI: /* REGIMM traps */
11993
        case OPC_TNEI:
11994
            gen_trap(ctx, op1, rs, -1, imm);
11995
            break;
11996
        case OPC_SYNCI:
11997
            check_insn(env, ctx, ISA_MIPS32R2);
11998
            /* Treat as NOP. */
11999
            break;
12000
        default:            /* Invalid */
12001
            MIPS_INVAL("regimm");
12002
            generate_exception(ctx, EXCP_RI);
12003
            break;
12004
        }
12005
        break;
12006
    case OPC_CP0:
12007
        check_cp0_enabled(ctx);
12008
        op1 = MASK_CP0(ctx->opcode);
12009
        switch (op1) {
12010
        case OPC_MFC0:
12011
        case OPC_MTC0:
12012
        case OPC_MFTR:
12013
        case OPC_MTTR:
12014
#if defined(TARGET_MIPS64)
12015
        case OPC_DMFC0:
12016
        case OPC_DMTC0:
12017
#endif
12018
#ifndef CONFIG_USER_ONLY
12019
            gen_cp0(env, ctx, op1, rt, rd);
12020
#endif /* !CONFIG_USER_ONLY */
12021
            break;
12022
        case OPC_C0_FIRST ... OPC_C0_LAST:
12023
#ifndef CONFIG_USER_ONLY
12024
            gen_cp0(env, ctx, MASK_C0(ctx->opcode), rt, rd);
12025
#endif /* !CONFIG_USER_ONLY */
12026
            break;
12027
        case OPC_MFMC0:
12028
#ifndef CONFIG_USER_ONLY
12029
            {
12030
                TCGv t0 = tcg_temp_new();
12031

    
12032
                op2 = MASK_MFMC0(ctx->opcode);
12033
                switch (op2) {
12034
                case OPC_DMT:
12035
                    check_insn(env, ctx, ASE_MT);
12036
                    gen_helper_dmt(t0, t0);
12037
                    gen_store_gpr(t0, rt);
12038
                    break;
12039
                case OPC_EMT:
12040
                    check_insn(env, ctx, ASE_MT);
12041
                    gen_helper_emt(t0, t0);
12042
                    gen_store_gpr(t0, rt);
12043
                    break;
12044
                case OPC_DVPE:
12045
                    check_insn(env, ctx, ASE_MT);
12046
                    gen_helper_dvpe(t0, t0);
12047
                    gen_store_gpr(t0, rt);
12048
                    break;
12049
                case OPC_EVPE:
12050
                    check_insn(env, ctx, ASE_MT);
12051
                    gen_helper_evpe(t0, t0);
12052
                    gen_store_gpr(t0, rt);
12053
                    break;
12054
                case OPC_DI:
12055
                    check_insn(env, ctx, ISA_MIPS32R2);
12056
                    save_cpu_state(ctx, 1);
12057
                    gen_helper_di(t0);
12058
                    gen_store_gpr(t0, rt);
12059
                    /* Stop translation as we may have switched the execution mode */
12060
                    ctx->bstate = BS_STOP;
12061
                    break;
12062
                case OPC_EI:
12063
                    check_insn(env, ctx, ISA_MIPS32R2);
12064
                    save_cpu_state(ctx, 1);
12065
                    gen_helper_ei(t0);
12066
                    gen_store_gpr(t0, rt);
12067
                    /* Stop translation as we may have switched the execution mode */
12068
                    ctx->bstate = BS_STOP;
12069
                    break;
12070
                default:            /* Invalid */
12071
                    MIPS_INVAL("mfmc0");
12072
                    generate_exception(ctx, EXCP_RI);
12073
                    break;
12074
                }
12075
                tcg_temp_free(t0);
12076
            }
12077
#endif /* !CONFIG_USER_ONLY */
12078
            break;
12079
        case OPC_RDPGPR:
12080
            check_insn(env, ctx, ISA_MIPS32R2);
12081
            gen_load_srsgpr(rt, rd);
12082
            break;
12083
        case OPC_WRPGPR:
12084
            check_insn(env, ctx, ISA_MIPS32R2);
12085
            gen_store_srsgpr(rt, rd);
12086
            break;
12087
        default:
12088
            MIPS_INVAL("cp0");
12089
            generate_exception(ctx, EXCP_RI);
12090
            break;
12091
        }
12092
        break;
12093
    case OPC_ADDI: /* Arithmetic with immediate opcode */
12094
    case OPC_ADDIU:
12095
         gen_arith_imm(env, ctx, op, rt, rs, imm);
12096
         break;
12097
    case OPC_SLTI: /* Set on less than with immediate opcode */
12098
    case OPC_SLTIU:
12099
         gen_slt_imm(env, op, rt, rs, imm);
12100
         break;
12101
    case OPC_ANDI: /* Arithmetic with immediate opcode */
12102
    case OPC_LUI:
12103
    case OPC_ORI:
12104
    case OPC_XORI:
12105
         gen_logic_imm(env, op, rt, rs, imm);
12106
         break;
12107
    case OPC_J ... OPC_JAL: /* Jump */
12108
         offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
12109
         gen_compute_branch(ctx, op, 4, rs, rt, offset);
12110
         *is_branch = 1;
12111
         break;
12112
    case OPC_BEQ ... OPC_BGTZ: /* Branch */
12113
    case OPC_BEQL ... OPC_BGTZL:
12114
         gen_compute_branch(ctx, op, 4, rs, rt, imm << 2);
12115
         *is_branch = 1;
12116
         break;
12117
    case OPC_LB ... OPC_LWR: /* Load and stores */
12118
    case OPC_LL:
12119
         gen_ld(env, ctx, op, rt, rs, imm);
12120
         break;
12121
    case OPC_SB ... OPC_SW:
12122
    case OPC_SWR:
12123
         gen_st(ctx, op, rt, rs, imm);
12124
         break;
12125
    case OPC_SC:
12126
         gen_st_cond(ctx, op, rt, rs, imm);
12127
         break;
12128
    case OPC_CACHE:
12129
        check_insn(env, ctx, ISA_MIPS3 | ISA_MIPS32);
12130
        /* Treat as NOP. */
12131
        break;
12132
    case OPC_PREF:
12133
        check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
12134
        /* Treat as NOP. */
12135
        break;
12136

    
12137
    /* Floating point (COP1). */
12138
    case OPC_LWC1:
12139
    case OPC_LDC1:
12140
    case OPC_SWC1:
12141
    case OPC_SDC1:
12142
        gen_cop1_ldst(env, ctx, op, rt, rs, imm);
12143
        break;
12144

    
12145
    case OPC_CP1:
12146
        if (env->CP0_Config1 & (1 << CP0C1_FP)) {
12147
            check_cp1_enabled(ctx);
12148
            op1 = MASK_CP1(ctx->opcode);
12149
            switch (op1) {
12150
            case OPC_MFHC1:
12151
            case OPC_MTHC1:
12152
                check_insn(env, ctx, ISA_MIPS32R2);
12153
            case OPC_MFC1:
12154
            case OPC_CFC1:
12155
            case OPC_MTC1:
12156
            case OPC_CTC1:
12157
                gen_cp1(ctx, op1, rt, rd);
12158
                break;
12159
#if defined(TARGET_MIPS64)
12160
            case OPC_DMFC1:
12161
            case OPC_DMTC1:
12162
                check_insn(env, ctx, ISA_MIPS3);
12163
                gen_cp1(ctx, op1, rt, rd);
12164
                break;
12165
#endif
12166
            case OPC_BC1ANY2:
12167
            case OPC_BC1ANY4:
12168
                check_cop1x(ctx);
12169
                check_insn(env, ctx, ASE_MIPS3D);
12170
                /* fall through */
12171
            case OPC_BC1:
12172
                gen_compute_branch1(env, ctx, MASK_BC1(ctx->opcode),
12173
                                    (rt >> 2) & 0x7, imm << 2);
12174
                *is_branch = 1;
12175
                break;
12176
            case OPC_S_FMT:
12177
            case OPC_D_FMT:
12178
            case OPC_W_FMT:
12179
            case OPC_L_FMT:
12180
            case OPC_PS_FMT:
12181
                gen_farith(ctx, ctx->opcode & FOP(0x3f, 0x1f), rt, rd, sa,
12182
                           (imm >> 8) & 0x7);
12183
                break;
12184
            default:
12185
                MIPS_INVAL("cp1");
12186
                generate_exception (ctx, EXCP_RI);
12187
                break;
12188
            }
12189
        } else {
12190
            generate_exception_err(ctx, EXCP_CpU, 1);
12191
        }
12192
        break;
12193

    
12194
    /* COP2.  */
12195
    case OPC_LWC2:
12196
    case OPC_LDC2:
12197
    case OPC_SWC2:
12198
    case OPC_SDC2:
12199
    case OPC_CP2:
12200
        /* COP2: Not implemented. */
12201
        generate_exception_err(ctx, EXCP_CpU, 2);
12202
        break;
12203

    
12204
    case OPC_CP3:
12205
        if (env->CP0_Config1 & (1 << CP0C1_FP)) {
12206
            check_cp1_enabled(ctx);
12207
            op1 = MASK_CP3(ctx->opcode);
12208
            switch (op1) {
12209
            case OPC_LWXC1:
12210
            case OPC_LDXC1:
12211
            case OPC_LUXC1:
12212
            case OPC_SWXC1:
12213
            case OPC_SDXC1:
12214
            case OPC_SUXC1:
12215
                gen_flt3_ldst(ctx, op1, sa, rd, rs, rt);
12216
                break;
12217
            case OPC_PREFX:
12218
                /* Treat as NOP. */
12219
                break;
12220
            case OPC_ALNV_PS:
12221
            case OPC_MADD_S:
12222
            case OPC_MADD_D:
12223
            case OPC_MADD_PS:
12224
            case OPC_MSUB_S:
12225
            case OPC_MSUB_D:
12226
            case OPC_MSUB_PS:
12227
            case OPC_NMADD_S:
12228
            case OPC_NMADD_D:
12229
            case OPC_NMADD_PS:
12230
            case OPC_NMSUB_S:
12231
            case OPC_NMSUB_D:
12232
            case OPC_NMSUB_PS:
12233
                gen_flt3_arith(ctx, op1, sa, rs, rd, rt);
12234
                break;
12235
            default:
12236
                MIPS_INVAL("cp3");
12237
                generate_exception (ctx, EXCP_RI);
12238
                break;
12239
            }
12240
        } else {
12241
            generate_exception_err(ctx, EXCP_CpU, 1);
12242
        }
12243
        break;
12244

    
12245
#if defined(TARGET_MIPS64)
12246
    /* MIPS64 opcodes */
12247
    case OPC_LWU:
12248
    case OPC_LDL ... OPC_LDR:
12249
    case OPC_LLD:
12250
    case OPC_LD:
12251
        check_insn(env, ctx, ISA_MIPS3);
12252
        check_mips_64(ctx);
12253
        gen_ld(env, ctx, op, rt, rs, imm);
12254
        break;
12255
    case OPC_SDL ... OPC_SDR:
12256
    case OPC_SD:
12257
        check_insn(env, ctx, ISA_MIPS3);
12258
        check_mips_64(ctx);
12259
        gen_st(ctx, op, rt, rs, imm);
12260
        break;
12261
    case OPC_SCD:
12262
        check_insn(env, ctx, ISA_MIPS3);
12263
        check_mips_64(ctx);
12264
        gen_st_cond(ctx, op, rt, rs, imm);
12265
        break;
12266
    case OPC_DADDI:
12267
    case OPC_DADDIU:
12268
        check_insn(env, ctx, ISA_MIPS3);
12269
        check_mips_64(ctx);
12270
        gen_arith_imm(env, ctx, op, rt, rs, imm);
12271
        break;
12272
#endif
12273
    case OPC_JALX:
12274
        check_insn(env, ctx, ASE_MIPS16 | ASE_MICROMIPS);
12275
        offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
12276
        gen_compute_branch(ctx, op, 4, rs, rt, offset);
12277
        *is_branch = 1;
12278
        break;
12279
    case OPC_MDMX:
12280
        check_insn(env, ctx, ASE_MDMX);
12281
        /* MDMX: Not implemented. */
12282
    default:            /* Invalid */
12283
        MIPS_INVAL("major opcode");
12284
        generate_exception(ctx, EXCP_RI);
12285
        break;
12286
    }
12287
}
12288

    
12289
static inline void
12290
gen_intermediate_code_internal (CPUState *env, TranslationBlock *tb,
12291
                                int search_pc)
12292
{
12293
    DisasContext ctx;
12294
    target_ulong pc_start;
12295
    uint16_t *gen_opc_end;
12296
    CPUBreakpoint *bp;
12297
    int j, lj = -1;
12298
    int num_insns;
12299
    int max_insns;
12300
    int insn_bytes;
12301
    int is_branch;
12302

    
12303
    if (search_pc)
12304
        qemu_log("search pc %d\n", search_pc);
12305

    
12306
    pc_start = tb->pc;
12307
    gen_opc_end = gen_opc_buf + OPC_MAX_SIZE;
12308
    ctx.pc = pc_start;
12309
    ctx.saved_pc = -1;
12310
    ctx.singlestep_enabled = env->singlestep_enabled;
12311
    ctx.tb = tb;
12312
    ctx.bstate = BS_NONE;
12313
    /* Restore delay slot state from the tb context.  */
12314
    ctx.hflags = (uint32_t)tb->flags; /* FIXME: maybe use 64 bits here? */
12315
    restore_cpu_state(env, &ctx);
12316
#ifdef CONFIG_USER_ONLY
12317
        ctx.mem_idx = MIPS_HFLAG_UM;
12318
#else
12319
        ctx.mem_idx = ctx.hflags & MIPS_HFLAG_KSU;
12320
#endif
12321
    num_insns = 0;
12322
    max_insns = tb->cflags & CF_COUNT_MASK;
12323
    if (max_insns == 0)
12324
        max_insns = CF_COUNT_MASK;
12325
    LOG_DISAS("\ntb %p idx %d hflags %04x\n", tb, ctx.mem_idx, ctx.hflags);
12326
    gen_icount_start();
12327
    while (ctx.bstate == BS_NONE) {
12328
        if (unlikely(!QTAILQ_EMPTY(&env->breakpoints))) {
12329
            QTAILQ_FOREACH(bp, &env->breakpoints, entry) {
12330
                if (bp->pc == ctx.pc) {
12331
                    save_cpu_state(&ctx, 1);
12332
                    ctx.bstate = BS_BRANCH;
12333
                    gen_helper_0i(raise_exception, EXCP_DEBUG);
12334
                    /* Include the breakpoint location or the tb won't
12335
                     * be flushed when it must be.  */
12336
                    ctx.pc += 4;
12337
                    goto done_generating;
12338
                }
12339
            }
12340
        }
12341

    
12342
        if (search_pc) {
12343
            j = gen_opc_ptr - gen_opc_buf;
12344
            if (lj < j) {
12345
                lj++;
12346
                while (lj < j)
12347
                    gen_opc_instr_start[lj++] = 0;
12348
            }
12349
            gen_opc_pc[lj] = ctx.pc;
12350
            gen_opc_hflags[lj] = ctx.hflags & MIPS_HFLAG_BMASK;
12351
            gen_opc_instr_start[lj] = 1;
12352
            gen_opc_icount[lj] = num_insns;
12353
        }
12354
        if (num_insns + 1 == max_insns && (tb->cflags & CF_LAST_IO))
12355
            gen_io_start();
12356

    
12357
        is_branch = 0;
12358
        if (!(ctx.hflags & MIPS_HFLAG_M16)) {
12359
            ctx.opcode = ldl_code(ctx.pc);
12360
            insn_bytes = 4;
12361
            decode_opc(env, &ctx, &is_branch);
12362
        } else if (env->insn_flags & ASE_MICROMIPS) {
12363
            ctx.opcode = lduw_code(ctx.pc);
12364
            insn_bytes = decode_micromips_opc(env, &ctx, &is_branch);
12365
        } else if (env->insn_flags & ASE_MIPS16) {
12366
            ctx.opcode = lduw_code(ctx.pc);
12367
            insn_bytes = decode_mips16_opc(env, &ctx, &is_branch);
12368
        } else {
12369
            generate_exception(&ctx, EXCP_RI);
12370
            ctx.bstate = BS_STOP;
12371
            break;
12372
        }
12373
        if (!is_branch) {
12374
            handle_delay_slot(env, &ctx, insn_bytes);
12375
        }
12376
        ctx.pc += insn_bytes;
12377

    
12378
        num_insns++;
12379

    
12380
        /* Execute a branch and its delay slot as a single instruction.
12381
           This is what GDB expects and is consistent with what the
12382
           hardware does (e.g. if a delay slot instruction faults, the
12383
           reported PC is the PC of the branch).  */
12384
        if (env->singlestep_enabled && (ctx.hflags & MIPS_HFLAG_BMASK) == 0)
12385
            break;
12386

    
12387
        if ((ctx.pc & (TARGET_PAGE_SIZE - 1)) == 0)
12388
            break;
12389

    
12390
        if (gen_opc_ptr >= gen_opc_end)
12391
            break;
12392

    
12393
        if (num_insns >= max_insns)
12394
            break;
12395

    
12396
        if (singlestep)
12397
            break;
12398
    }
12399
    if (tb->cflags & CF_LAST_IO)
12400
        gen_io_end();
12401
    if (env->singlestep_enabled && ctx.bstate != BS_BRANCH) {
12402
        save_cpu_state(&ctx, ctx.bstate == BS_NONE);
12403
        gen_helper_0i(raise_exception, EXCP_DEBUG);
12404
    } else {
12405
        switch (ctx.bstate) {
12406
        case BS_STOP:
12407
            gen_goto_tb(&ctx, 0, ctx.pc);
12408
            break;
12409
        case BS_NONE:
12410
            save_cpu_state(&ctx, 0);
12411
            gen_goto_tb(&ctx, 0, ctx.pc);
12412
            break;
12413
        case BS_EXCP:
12414
            tcg_gen_exit_tb(0);
12415
            break;
12416
        case BS_BRANCH:
12417
        default:
12418
            break;
12419
        }
12420
    }
12421
done_generating:
12422
    gen_icount_end(tb, num_insns);
12423
    *gen_opc_ptr = INDEX_op_end;
12424
    if (search_pc) {
12425
        j = gen_opc_ptr - gen_opc_buf;
12426
        lj++;
12427
        while (lj <= j)
12428
            gen_opc_instr_start[lj++] = 0;
12429
    } else {
12430
        tb->size = ctx.pc - pc_start;
12431
        tb->icount = num_insns;
12432
    }
12433
#ifdef DEBUG_DISAS
12434
    LOG_DISAS("\n");
12435
    if (qemu_loglevel_mask(CPU_LOG_TB_IN_ASM)) {
12436
        qemu_log("IN: %s\n", lookup_symbol(pc_start));
12437
        log_target_disas(pc_start, ctx.pc - pc_start, 0);
12438
        qemu_log("\n");
12439
    }
12440
#endif
12441
}
12442

    
12443
void gen_intermediate_code (CPUState *env, struct TranslationBlock *tb)
12444
{
12445
    gen_intermediate_code_internal(env, tb, 0);
12446
}
12447

    
12448
void gen_intermediate_code_pc (CPUState *env, struct TranslationBlock *tb)
12449
{
12450
    gen_intermediate_code_internal(env, tb, 1);
12451
}
12452

    
12453
static void fpu_dump_state(CPUState *env, FILE *f, fprintf_function fpu_fprintf,
12454
                           int flags)
12455
{
12456
    int i;
12457
    int is_fpu64 = !!(env->hflags & MIPS_HFLAG_F64);
12458

    
12459
#define printfpr(fp)                                                    \
12460
    do {                                                                \
12461
        if (is_fpu64)                                                   \
12462
            fpu_fprintf(f, "w:%08x d:%016" PRIx64                       \
12463
                        " fd:%13g fs:%13g psu: %13g\n",                 \
12464
                        (fp)->w[FP_ENDIAN_IDX], (fp)->d,                \
12465
                        (double)(fp)->fd,                               \
12466
                        (double)(fp)->fs[FP_ENDIAN_IDX],                \
12467
                        (double)(fp)->fs[!FP_ENDIAN_IDX]);              \
12468
        else {                                                          \
12469
            fpr_t tmp;                                                  \
12470
            tmp.w[FP_ENDIAN_IDX] = (fp)->w[FP_ENDIAN_IDX];              \
12471
            tmp.w[!FP_ENDIAN_IDX] = ((fp) + 1)->w[FP_ENDIAN_IDX];       \
12472
            fpu_fprintf(f, "w:%08x d:%016" PRIx64                       \
12473
                        " fd:%13g fs:%13g psu:%13g\n",                  \
12474
                        tmp.w[FP_ENDIAN_IDX], tmp.d,                    \
12475
                        (double)tmp.fd,                                 \
12476
                        (double)tmp.fs[FP_ENDIAN_IDX],                  \
12477
                        (double)tmp.fs[!FP_ENDIAN_IDX]);                \
12478
        }                                                               \
12479
    } while(0)
12480

    
12481

    
12482
    fpu_fprintf(f, "CP1 FCR0 0x%08x  FCR31 0x%08x  SR.FR %d  fp_status 0x%02x\n",
12483
                env->active_fpu.fcr0, env->active_fpu.fcr31, is_fpu64,
12484
                get_float_exception_flags(&env->active_fpu.fp_status));
12485
    for (i = 0; i < 32; (is_fpu64) ? i++ : (i += 2)) {
12486
        fpu_fprintf(f, "%3s: ", fregnames[i]);
12487
        printfpr(&env->active_fpu.fpr[i]);
12488
    }
12489

    
12490
#undef printfpr
12491
}
12492

    
12493
#if defined(TARGET_MIPS64) && defined(MIPS_DEBUG_SIGN_EXTENSIONS)
12494
/* Debug help: The architecture requires 32bit code to maintain proper
12495
   sign-extended values on 64bit machines.  */
12496

    
12497
#define SIGN_EXT_P(val) ((((val) & ~0x7fffffff) == 0) || (((val) & ~0x7fffffff) == ~0x7fffffff))
12498

    
12499
static void
12500
cpu_mips_check_sign_extensions (CPUState *env, FILE *f,
12501
                                fprintf_function cpu_fprintf,
12502
                                int flags)
12503
{
12504
    int i;
12505

    
12506
    if (!SIGN_EXT_P(env->active_tc.PC))
12507
        cpu_fprintf(f, "BROKEN: pc=0x" TARGET_FMT_lx "\n", env->active_tc.PC);
12508
    if (!SIGN_EXT_P(env->active_tc.HI[0]))
12509
        cpu_fprintf(f, "BROKEN: HI=0x" TARGET_FMT_lx "\n", env->active_tc.HI[0]);
12510
    if (!SIGN_EXT_P(env->active_tc.LO[0]))
12511
        cpu_fprintf(f, "BROKEN: LO=0x" TARGET_FMT_lx "\n", env->active_tc.LO[0]);
12512
    if (!SIGN_EXT_P(env->btarget))
12513
        cpu_fprintf(f, "BROKEN: btarget=0x" TARGET_FMT_lx "\n", env->btarget);
12514

    
12515
    for (i = 0; i < 32; i++) {
12516
        if (!SIGN_EXT_P(env->active_tc.gpr[i]))
12517
            cpu_fprintf(f, "BROKEN: %s=0x" TARGET_FMT_lx "\n", regnames[i], env->active_tc.gpr[i]);
12518
    }
12519

    
12520
    if (!SIGN_EXT_P(env->CP0_EPC))
12521
        cpu_fprintf(f, "BROKEN: EPC=0x" TARGET_FMT_lx "\n", env->CP0_EPC);
12522
    if (!SIGN_EXT_P(env->lladdr))
12523
        cpu_fprintf(f, "BROKEN: LLAddr=0x" TARGET_FMT_lx "\n", env->lladdr);
12524
}
12525
#endif
12526

    
12527
void cpu_dump_state (CPUState *env, FILE *f, fprintf_function cpu_fprintf,
12528
                     int flags)
12529
{
12530
    int i;
12531

    
12532
    cpu_fprintf(f, "pc=0x" TARGET_FMT_lx " HI=0x" TARGET_FMT_lx
12533
                " LO=0x" TARGET_FMT_lx " ds %04x "
12534
                TARGET_FMT_lx " " TARGET_FMT_ld "\n",
12535
                env->active_tc.PC, env->active_tc.HI[0], env->active_tc.LO[0],
12536
                env->hflags, env->btarget, env->bcond);
12537
    for (i = 0; i < 32; i++) {
12538
        if ((i & 3) == 0)
12539
            cpu_fprintf(f, "GPR%02d:", i);
12540
        cpu_fprintf(f, " %s " TARGET_FMT_lx, regnames[i], env->active_tc.gpr[i]);
12541
        if ((i & 3) == 3)
12542
            cpu_fprintf(f, "\n");
12543
    }
12544

    
12545
    cpu_fprintf(f, "CP0 Status  0x%08x Cause   0x%08x EPC    0x" TARGET_FMT_lx "\n",
12546
                env->CP0_Status, env->CP0_Cause, env->CP0_EPC);
12547
    cpu_fprintf(f, "    Config0 0x%08x Config1 0x%08x LLAddr 0x" TARGET_FMT_lx "\n",
12548
                env->CP0_Config0, env->CP0_Config1, env->lladdr);
12549
    if (env->hflags & MIPS_HFLAG_FPU)
12550
        fpu_dump_state(env, f, cpu_fprintf, flags);
12551
#if defined(TARGET_MIPS64) && defined(MIPS_DEBUG_SIGN_EXTENSIONS)
12552
    cpu_mips_check_sign_extensions(env, f, cpu_fprintf, flags);
12553
#endif
12554
}
12555

    
12556
static void mips_tcg_init(void)
12557
{
12558
    int i;
12559
    static int inited;
12560

    
12561
    /* Initialize various static tables. */
12562
    if (inited)
12563
        return;
12564

    
12565
    cpu_env = tcg_global_reg_new_ptr(TCG_AREG0, "env");
12566
    TCGV_UNUSED(cpu_gpr[0]);
12567
    for (i = 1; i < 32; i++)
12568
        cpu_gpr[i] = tcg_global_mem_new(TCG_AREG0,
12569
                                        offsetof(CPUState, active_tc.gpr[i]),
12570
                                        regnames[i]);
12571
    cpu_PC = tcg_global_mem_new(TCG_AREG0,
12572
                                offsetof(CPUState, active_tc.PC), "PC");
12573
    for (i = 0; i < MIPS_DSP_ACC; i++) {
12574
        cpu_HI[i] = tcg_global_mem_new(TCG_AREG0,
12575
                                       offsetof(CPUState, active_tc.HI[i]),
12576
                                       regnames_HI[i]);
12577
        cpu_LO[i] = tcg_global_mem_new(TCG_AREG0,
12578
                                       offsetof(CPUState, active_tc.LO[i]),
12579
                                       regnames_LO[i]);
12580
        cpu_ACX[i] = tcg_global_mem_new(TCG_AREG0,
12581
                                        offsetof(CPUState, active_tc.ACX[i]),
12582
                                        regnames_ACX[i]);
12583
    }
12584
    cpu_dspctrl = tcg_global_mem_new(TCG_AREG0,
12585
                                     offsetof(CPUState, active_tc.DSPControl),
12586
                                     "DSPControl");
12587
    bcond = tcg_global_mem_new(TCG_AREG0,
12588
                               offsetof(CPUState, bcond), "bcond");
12589
    btarget = tcg_global_mem_new(TCG_AREG0,
12590
                                 offsetof(CPUState, btarget), "btarget");
12591
    hflags = tcg_global_mem_new_i32(TCG_AREG0,
12592
                                    offsetof(CPUState, hflags), "hflags");
12593

    
12594
    fpu_fcr0 = tcg_global_mem_new_i32(TCG_AREG0,
12595
                                      offsetof(CPUState, active_fpu.fcr0),
12596
                                      "fcr0");
12597
    fpu_fcr31 = tcg_global_mem_new_i32(TCG_AREG0,
12598
                                       offsetof(CPUState, active_fpu.fcr31),
12599
                                       "fcr31");
12600

    
12601
    /* register helpers */
12602
#define GEN_HELPER 2
12603
#include "helper.h"
12604

    
12605
    inited = 1;
12606
}
12607

    
12608
#include "translate_init.c"
12609

    
12610
CPUMIPSState *cpu_mips_init (const char *cpu_model)
12611
{
12612
    CPUMIPSState *env;
12613
    const mips_def_t *def;
12614

    
12615
    def = cpu_mips_find_by_name(cpu_model);
12616
    if (!def)
12617
        return NULL;
12618
    env = qemu_mallocz(sizeof(CPUMIPSState));
12619
    env->cpu_model = def;
12620
    env->cpu_model_str = cpu_model;
12621

    
12622
    cpu_exec_init(env);
12623
#ifndef CONFIG_USER_ONLY
12624
    mmu_init(env, def);
12625
#endif
12626
    fpu_init(env, def);
12627
    mvp_init(env, def);
12628
    mips_tcg_init();
12629
    cpu_reset(env);
12630
    qemu_init_vcpu(env);
12631
    return env;
12632
}
12633

    
12634
void cpu_reset (CPUMIPSState *env)
12635
{
12636
    if (qemu_loglevel_mask(CPU_LOG_RESET)) {
12637
        qemu_log("CPU Reset (CPU %d)\n", env->cpu_index);
12638
        log_cpu_state(env, 0);
12639
    }
12640

    
12641
    memset(env, 0, offsetof(CPUMIPSState, breakpoints));
12642
    tlb_flush(env, 1);
12643

    
12644
    /* Reset registers to their default values */
12645
    env->CP0_PRid = env->cpu_model->CP0_PRid;
12646
    env->CP0_Config0 = env->cpu_model->CP0_Config0;
12647
#ifdef TARGET_WORDS_BIGENDIAN
12648
    env->CP0_Config0 |= (1 << CP0C0_BE);
12649
#endif
12650
    env->CP0_Config1 = env->cpu_model->CP0_Config1;
12651
    env->CP0_Config2 = env->cpu_model->CP0_Config2;
12652
    env->CP0_Config3 = env->cpu_model->CP0_Config3;
12653
    env->CP0_Config6 = env->cpu_model->CP0_Config6;
12654
    env->CP0_Config7 = env->cpu_model->CP0_Config7;
12655
    env->CP0_LLAddr_rw_bitmask = env->cpu_model->CP0_LLAddr_rw_bitmask
12656
                                 << env->cpu_model->CP0_LLAddr_shift;
12657
    env->CP0_LLAddr_shift = env->cpu_model->CP0_LLAddr_shift;
12658
    env->SYNCI_Step = env->cpu_model->SYNCI_Step;
12659
    env->CCRes = env->cpu_model->CCRes;
12660
    env->CP0_Status_rw_bitmask = env->cpu_model->CP0_Status_rw_bitmask;
12661
    env->CP0_TCStatus_rw_bitmask = env->cpu_model->CP0_TCStatus_rw_bitmask;
12662
    env->CP0_SRSCtl = env->cpu_model->CP0_SRSCtl;
12663
    env->current_tc = 0;
12664
    env->SEGBITS = env->cpu_model->SEGBITS;
12665
    env->SEGMask = (target_ulong)((1ULL << env->cpu_model->SEGBITS) - 1);
12666
#if defined(TARGET_MIPS64)
12667
    if (env->cpu_model->insn_flags & ISA_MIPS3) {
12668
        env->SEGMask |= 3ULL << 62;
12669
    }
12670
#endif
12671
    env->PABITS = env->cpu_model->PABITS;
12672
    env->PAMask = (target_ulong)((1ULL << env->cpu_model->PABITS) - 1);
12673
    env->CP0_SRSConf0_rw_bitmask = env->cpu_model->CP0_SRSConf0_rw_bitmask;
12674
    env->CP0_SRSConf0 = env->cpu_model->CP0_SRSConf0;
12675
    env->CP0_SRSConf1_rw_bitmask = env->cpu_model->CP0_SRSConf1_rw_bitmask;
12676
    env->CP0_SRSConf1 = env->cpu_model->CP0_SRSConf1;
12677
    env->CP0_SRSConf2_rw_bitmask = env->cpu_model->CP0_SRSConf2_rw_bitmask;
12678
    env->CP0_SRSConf2 = env->cpu_model->CP0_SRSConf2;
12679
    env->CP0_SRSConf3_rw_bitmask = env->cpu_model->CP0_SRSConf3_rw_bitmask;
12680
    env->CP0_SRSConf3 = env->cpu_model->CP0_SRSConf3;
12681
    env->CP0_SRSConf4_rw_bitmask = env->cpu_model->CP0_SRSConf4_rw_bitmask;
12682
    env->CP0_SRSConf4 = env->cpu_model->CP0_SRSConf4;
12683
    env->insn_flags = env->cpu_model->insn_flags;
12684

    
12685
#if defined(CONFIG_USER_ONLY)
12686
    env->hflags = MIPS_HFLAG_UM;
12687
    /* Enable access to the SYNCI_Step register.  */
12688
    env->CP0_HWREna |= (1 << 1);
12689
    if (env->CP0_Config1 & (1 << CP0C1_FP)) {
12690
        env->hflags |= MIPS_HFLAG_FPU;
12691
    }
12692
#ifdef TARGET_MIPS64
12693
    if (env->active_fpu.fcr0 & (1 << FCR0_F64)) {
12694
        env->hflags |= MIPS_HFLAG_F64;
12695
    }
12696
#endif
12697
#else
12698
    if (env->hflags & MIPS_HFLAG_BMASK) {
12699
        /* If the exception was raised from a delay slot,
12700
           come back to the jump.  */
12701
        env->CP0_ErrorEPC = env->active_tc.PC - 4;
12702
    } else {
12703
        env->CP0_ErrorEPC = env->active_tc.PC;
12704
    }
12705
    env->active_tc.PC = (int32_t)0xBFC00000;
12706
    env->CP0_Random = env->tlb->nb_tlb - 1;
12707
    env->tlb->tlb_in_use = env->tlb->nb_tlb;
12708
    env->CP0_Wired = 0;
12709
    env->CP0_EBase = 0x80000000 | (env->cpu_index & 0x3FF);
12710
    env->CP0_Status = (1 << CP0St_BEV) | (1 << CP0St_ERL);
12711
    /* vectored interrupts not implemented, timer on int 7,
12712
       no performance counters. */
12713
    env->CP0_IntCtl = 0xe0000000;
12714
    {
12715
        int i;
12716

    
12717
        for (i = 0; i < 7; i++) {
12718
            env->CP0_WatchLo[i] = 0;
12719
            env->CP0_WatchHi[i] = 0x80000000;
12720
        }
12721
        env->CP0_WatchLo[7] = 0;
12722
        env->CP0_WatchHi[7] = 0;
12723
    }
12724
    /* Count register increments in debug mode, EJTAG version 1 */
12725
    env->CP0_Debug = (1 << CP0DB_CNT) | (0x1 << CP0DB_VER);
12726
    env->hflags = MIPS_HFLAG_CP0;
12727
#endif
12728
#if defined(TARGET_MIPS64)
12729
    if (env->cpu_model->insn_flags & ISA_MIPS3) {
12730
        env->hflags |= MIPS_HFLAG_64;
12731
    }
12732
#endif
12733
    env->exception_index = EXCP_NONE;
12734
}
12735

    
12736
void gen_pc_load(CPUState *env, TranslationBlock *tb,
12737
                unsigned long searched_pc, int pc_pos, void *puc)
12738
{
12739
    env->active_tc.PC = gen_opc_pc[pc_pos];
12740
    env->hflags &= ~MIPS_HFLAG_BMASK;
12741
    env->hflags |= gen_opc_hflags[pc_pos];
12742
}