target-mips: fix commits 7040 and 7042
[qemu] / target-mips / translate.c
1 /*
2  *  MIPS32 emulation for qemu: main translation routines.
3  *
4  *  Copyright (c) 2004-2005 Jocelyn Mayer
5  *  Copyright (c) 2006 Marius Groeger (FPU operations)
6  *  Copyright (c) 2006 Thiemo Seufer (MIPS32R2 support)
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public
10  * License as published by the Free Software Foundation; either
11  * version 2 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with this library; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA  02110-1301 USA
21  */
22
23 #include <stdarg.h>
24 #include <stdlib.h>
25 #include <stdio.h>
26 #include <string.h>
27 #include <inttypes.h>
28
29 #include "cpu.h"
30 #include "exec-all.h"
31 #include "disas.h"
32 #include "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_BEQ      = (0x04 << 26),  /* Unconditional if rs = rt = 0 (B) */
72     OPC_BEQL     = (0x14 << 26),
73     OPC_BNE      = (0x05 << 26),
74     OPC_BNEL     = (0x15 << 26),
75     OPC_BLEZ     = (0x06 << 26),
76     OPC_BLEZL    = (0x16 << 26),
77     OPC_BGTZ     = (0x07 << 26),
78     OPC_BGTZL    = (0x17 << 26),
79     OPC_JALX     = (0x1D << 26),  /* MIPS 16 only */
80     /* Load and stores */
81     OPC_LDL      = (0x1A << 26),
82     OPC_LDR      = (0x1B << 26),
83     OPC_LB       = (0x20 << 26),
84     OPC_LH       = (0x21 << 26),
85     OPC_LWL      = (0x22 << 26),
86     OPC_LW       = (0x23 << 26),
87     OPC_LBU      = (0x24 << 26),
88     OPC_LHU      = (0x25 << 26),
89     OPC_LWR      = (0x26 << 26),
90     OPC_LWU      = (0x27 << 26),
91     OPC_SB       = (0x28 << 26),
92     OPC_SH       = (0x29 << 26),
93     OPC_SWL      = (0x2A << 26),
94     OPC_SW       = (0x2B << 26),
95     OPC_SDL      = (0x2C << 26),
96     OPC_SDR      = (0x2D << 26),
97     OPC_SWR      = (0x2E << 26),
98     OPC_LL       = (0x30 << 26),
99     OPC_LLD      = (0x34 << 26),
100     OPC_LD       = (0x37 << 26),
101     OPC_SC       = (0x38 << 26),
102     OPC_SCD      = (0x3C << 26),
103     OPC_SD       = (0x3F << 26),
104     /* Floating point load/store */
105     OPC_LWC1     = (0x31 << 26),
106     OPC_LWC2     = (0x32 << 26),
107     OPC_LDC1     = (0x35 << 26),
108     OPC_LDC2     = (0x36 << 26),
109     OPC_SWC1     = (0x39 << 26),
110     OPC_SWC2     = (0x3A << 26),
111     OPC_SDC1     = (0x3D << 26),
112     OPC_SDC2     = (0x3E << 26),
113     /* MDMX ASE specific */
114     OPC_MDMX     = (0x1E << 26),
115     /* Cache and prefetch */
116     OPC_CACHE    = (0x2F << 26),
117     OPC_PREF     = (0x33 << 26),
118     /* Reserved major opcode */
119     OPC_MAJOR3B_RESERVED = (0x3B << 26),
120 };
121
122 /* MIPS special opcodes */
123 #define MASK_SPECIAL(op)   MASK_OP_MAJOR(op) | (op & 0x3F)
124
125 enum {
126     /* Shifts */
127     OPC_SLL      = 0x00 | OPC_SPECIAL,
128     /* NOP is SLL r0, r0, 0   */
129     /* SSNOP is SLL r0, r0, 1 */
130     /* EHB is SLL r0, r0, 3 */
131     OPC_SRL      = 0x02 | OPC_SPECIAL, /* also ROTR */
132     OPC_SRA      = 0x03 | OPC_SPECIAL,
133     OPC_SLLV     = 0x04 | OPC_SPECIAL,
134     OPC_SRLV     = 0x06 | OPC_SPECIAL, /* also ROTRV */
135     OPC_SRAV     = 0x07 | OPC_SPECIAL,
136     OPC_DSLLV    = 0x14 | OPC_SPECIAL,
137     OPC_DSRLV    = 0x16 | OPC_SPECIAL, /* also DROTRV */
138     OPC_DSRAV    = 0x17 | OPC_SPECIAL,
139     OPC_DSLL     = 0x38 | OPC_SPECIAL,
140     OPC_DSRL     = 0x3A | OPC_SPECIAL, /* also DROTR */
141     OPC_DSRA     = 0x3B | OPC_SPECIAL,
142     OPC_DSLL32   = 0x3C | OPC_SPECIAL,
143     OPC_DSRL32   = 0x3E | OPC_SPECIAL, /* also DROTR32 */
144     OPC_DSRA32   = 0x3F | OPC_SPECIAL,
145     /* Multiplication / division */
146     OPC_MULT     = 0x18 | OPC_SPECIAL,
147     OPC_MULTU    = 0x19 | OPC_SPECIAL,
148     OPC_DIV      = 0x1A | OPC_SPECIAL,
149     OPC_DIVU     = 0x1B | OPC_SPECIAL,
150     OPC_DMULT    = 0x1C | OPC_SPECIAL,
151     OPC_DMULTU   = 0x1D | OPC_SPECIAL,
152     OPC_DDIV     = 0x1E | OPC_SPECIAL,
153     OPC_DDIVU    = 0x1F | OPC_SPECIAL,
154     /* 2 registers arithmetic / logic */
155     OPC_ADD      = 0x20 | OPC_SPECIAL,
156     OPC_ADDU     = 0x21 | OPC_SPECIAL,
157     OPC_SUB      = 0x22 | OPC_SPECIAL,
158     OPC_SUBU     = 0x23 | OPC_SPECIAL,
159     OPC_AND      = 0x24 | OPC_SPECIAL,
160     OPC_OR       = 0x25 | OPC_SPECIAL,
161     OPC_XOR      = 0x26 | OPC_SPECIAL,
162     OPC_NOR      = 0x27 | OPC_SPECIAL,
163     OPC_SLT      = 0x2A | OPC_SPECIAL,
164     OPC_SLTU     = 0x2B | OPC_SPECIAL,
165     OPC_DADD     = 0x2C | OPC_SPECIAL,
166     OPC_DADDU    = 0x2D | OPC_SPECIAL,
167     OPC_DSUB     = 0x2E | OPC_SPECIAL,
168     OPC_DSUBU    = 0x2F | OPC_SPECIAL,
169     /* Jumps */
170     OPC_JR       = 0x08 | OPC_SPECIAL, /* Also JR.HB */
171     OPC_JALR     = 0x09 | OPC_SPECIAL, /* Also JALR.HB */
172     /* Traps */
173     OPC_TGE      = 0x30 | OPC_SPECIAL,
174     OPC_TGEU     = 0x31 | OPC_SPECIAL,
175     OPC_TLT      = 0x32 | OPC_SPECIAL,
176     OPC_TLTU     = 0x33 | OPC_SPECIAL,
177     OPC_TEQ      = 0x34 | OPC_SPECIAL,
178     OPC_TNE      = 0x36 | OPC_SPECIAL,
179     /* HI / LO registers load & stores */
180     OPC_MFHI     = 0x10 | OPC_SPECIAL,
181     OPC_MTHI     = 0x11 | OPC_SPECIAL,
182     OPC_MFLO     = 0x12 | OPC_SPECIAL,
183     OPC_MTLO     = 0x13 | OPC_SPECIAL,
184     /* Conditional moves */
185     OPC_MOVZ     = 0x0A | OPC_SPECIAL,
186     OPC_MOVN     = 0x0B | OPC_SPECIAL,
187
188     OPC_MOVCI    = 0x01 | OPC_SPECIAL,
189
190     /* Special */
191     OPC_PMON     = 0x05 | OPC_SPECIAL, /* inofficial */
192     OPC_SYSCALL  = 0x0C | OPC_SPECIAL,
193     OPC_BREAK    = 0x0D | OPC_SPECIAL,
194     OPC_SPIM     = 0x0E | OPC_SPECIAL, /* inofficial */
195     OPC_SYNC     = 0x0F | OPC_SPECIAL,
196
197     OPC_SPECIAL15_RESERVED = 0x15 | OPC_SPECIAL,
198     OPC_SPECIAL28_RESERVED = 0x28 | OPC_SPECIAL,
199     OPC_SPECIAL29_RESERVED = 0x29 | OPC_SPECIAL,
200     OPC_SPECIAL35_RESERVED = 0x35 | OPC_SPECIAL,
201     OPC_SPECIAL37_RESERVED = 0x37 | OPC_SPECIAL,
202     OPC_SPECIAL39_RESERVED = 0x39 | OPC_SPECIAL,
203     OPC_SPECIAL3D_RESERVED = 0x3D | OPC_SPECIAL,
204 };
205
206 /* Multiplication variants of the vr54xx. */
207 #define MASK_MUL_VR54XX(op)   MASK_SPECIAL(op) | (op & (0x1F << 6))
208
209 enum {
210     OPC_VR54XX_MULS    = (0x03 << 6) | OPC_MULT,
211     OPC_VR54XX_MULSU   = (0x03 << 6) | OPC_MULTU,
212     OPC_VR54XX_MACC    = (0x05 << 6) | OPC_MULT,
213     OPC_VR54XX_MACCU   = (0x05 << 6) | OPC_MULTU,
214     OPC_VR54XX_MSAC    = (0x07 << 6) | OPC_MULT,
215     OPC_VR54XX_MSACU   = (0x07 << 6) | OPC_MULTU,
216     OPC_VR54XX_MULHI   = (0x09 << 6) | OPC_MULT,
217     OPC_VR54XX_MULHIU  = (0x09 << 6) | OPC_MULTU,
218     OPC_VR54XX_MULSHI  = (0x0B << 6) | OPC_MULT,
219     OPC_VR54XX_MULSHIU = (0x0B << 6) | OPC_MULTU,
220     OPC_VR54XX_MACCHI  = (0x0D << 6) | OPC_MULT,
221     OPC_VR54XX_MACCHIU = (0x0D << 6) | OPC_MULTU,
222     OPC_VR54XX_MSACHI  = (0x0F << 6) | OPC_MULT,
223     OPC_VR54XX_MSACHIU = (0x0F << 6) | OPC_MULTU,
224 };
225
226 /* REGIMM (rt field) opcodes */
227 #define MASK_REGIMM(op)    MASK_OP_MAJOR(op) | (op & (0x1F << 16))
228
229 enum {
230     OPC_BLTZ     = (0x00 << 16) | OPC_REGIMM,
231     OPC_BLTZL    = (0x02 << 16) | OPC_REGIMM,
232     OPC_BGEZ     = (0x01 << 16) | OPC_REGIMM,
233     OPC_BGEZL    = (0x03 << 16) | OPC_REGIMM,
234     OPC_BLTZAL   = (0x10 << 16) | OPC_REGIMM,
235     OPC_BLTZALL  = (0x12 << 16) | OPC_REGIMM,
236     OPC_BGEZAL   = (0x11 << 16) | OPC_REGIMM,
237     OPC_BGEZALL  = (0x13 << 16) | OPC_REGIMM,
238     OPC_TGEI     = (0x08 << 16) | OPC_REGIMM,
239     OPC_TGEIU    = (0x09 << 16) | OPC_REGIMM,
240     OPC_TLTI     = (0x0A << 16) | OPC_REGIMM,
241     OPC_TLTIU    = (0x0B << 16) | OPC_REGIMM,
242     OPC_TEQI     = (0x0C << 16) | OPC_REGIMM,
243     OPC_TNEI     = (0x0E << 16) | OPC_REGIMM,
244     OPC_SYNCI    = (0x1F << 16) | OPC_REGIMM,
245 };
246
247 /* Special2 opcodes */
248 #define MASK_SPECIAL2(op)  MASK_OP_MAJOR(op) | (op & 0x3F)
249
250 enum {
251     /* Multiply & xxx operations */
252     OPC_MADD     = 0x00 | OPC_SPECIAL2,
253     OPC_MADDU    = 0x01 | OPC_SPECIAL2,
254     OPC_MUL      = 0x02 | OPC_SPECIAL2,
255     OPC_MSUB     = 0x04 | OPC_SPECIAL2,
256     OPC_MSUBU    = 0x05 | OPC_SPECIAL2,
257     /* Misc */
258     OPC_CLZ      = 0x20 | OPC_SPECIAL2,
259     OPC_CLO      = 0x21 | OPC_SPECIAL2,
260     OPC_DCLZ     = 0x24 | OPC_SPECIAL2,
261     OPC_DCLO     = 0x25 | OPC_SPECIAL2,
262     /* Special */
263     OPC_SDBBP    = 0x3F | OPC_SPECIAL2,
264 };
265
266 /* Special3 opcodes */
267 #define MASK_SPECIAL3(op)  MASK_OP_MAJOR(op) | (op & 0x3F)
268
269 enum {
270     OPC_EXT      = 0x00 | OPC_SPECIAL3,
271     OPC_DEXTM    = 0x01 | OPC_SPECIAL3,
272     OPC_DEXTU    = 0x02 | OPC_SPECIAL3,
273     OPC_DEXT     = 0x03 | OPC_SPECIAL3,
274     OPC_INS      = 0x04 | OPC_SPECIAL3,
275     OPC_DINSM    = 0x05 | OPC_SPECIAL3,
276     OPC_DINSU    = 0x06 | OPC_SPECIAL3,
277     OPC_DINS     = 0x07 | OPC_SPECIAL3,
278     OPC_FORK     = 0x08 | OPC_SPECIAL3,
279     OPC_YIELD    = 0x09 | OPC_SPECIAL3,
280     OPC_BSHFL    = 0x20 | OPC_SPECIAL3,
281     OPC_DBSHFL   = 0x24 | OPC_SPECIAL3,
282     OPC_RDHWR    = 0x3B | OPC_SPECIAL3,
283 };
284
285 /* BSHFL opcodes */
286 #define MASK_BSHFL(op)     MASK_SPECIAL3(op) | (op & (0x1F << 6))
287
288 enum {
289     OPC_WSBH     = (0x02 << 6) | OPC_BSHFL,
290     OPC_SEB      = (0x10 << 6) | OPC_BSHFL,
291     OPC_SEH      = (0x18 << 6) | OPC_BSHFL,
292 };
293
294 /* DBSHFL opcodes */
295 #define MASK_DBSHFL(op)    MASK_SPECIAL3(op) | (op & (0x1F << 6))
296
297 enum {
298     OPC_DSBH     = (0x02 << 6) | OPC_DBSHFL,
299     OPC_DSHD     = (0x05 << 6) | OPC_DBSHFL,
300 };
301
302 /* Coprocessor 0 (rs field) */
303 #define MASK_CP0(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
304
305 enum {
306     OPC_MFC0     = (0x00 << 21) | OPC_CP0,
307     OPC_DMFC0    = (0x01 << 21) | OPC_CP0,
308     OPC_MTC0     = (0x04 << 21) | OPC_CP0,
309     OPC_DMTC0    = (0x05 << 21) | OPC_CP0,
310     OPC_MFTR     = (0x08 << 21) | OPC_CP0,
311     OPC_RDPGPR   = (0x0A << 21) | OPC_CP0,
312     OPC_MFMC0    = (0x0B << 21) | OPC_CP0,
313     OPC_MTTR     = (0x0C << 21) | OPC_CP0,
314     OPC_WRPGPR   = (0x0E << 21) | OPC_CP0,
315     OPC_C0       = (0x10 << 21) | OPC_CP0,
316     OPC_C0_FIRST = (0x10 << 21) | OPC_CP0,
317     OPC_C0_LAST  = (0x1F << 21) | OPC_CP0,
318 };
319
320 /* MFMC0 opcodes */
321 #define MASK_MFMC0(op)     MASK_CP0(op) | (op & 0xFFFF)
322
323 enum {
324     OPC_DMT      = 0x01 | (0 << 5) | (0x0F << 6) | (0x01 << 11) | OPC_MFMC0,
325     OPC_EMT      = 0x01 | (1 << 5) | (0x0F << 6) | (0x01 << 11) | OPC_MFMC0,
326     OPC_DVPE     = 0x01 | (0 << 5) | OPC_MFMC0,
327     OPC_EVPE     = 0x01 | (1 << 5) | OPC_MFMC0,
328     OPC_DI       = (0 << 5) | (0x0C << 11) | OPC_MFMC0,
329     OPC_EI       = (1 << 5) | (0x0C << 11) | OPC_MFMC0,
330 };
331
332 /* Coprocessor 0 (with rs == C0) */
333 #define MASK_C0(op)        MASK_CP0(op) | (op & 0x3F)
334
335 enum {
336     OPC_TLBR     = 0x01 | OPC_C0,
337     OPC_TLBWI    = 0x02 | OPC_C0,
338     OPC_TLBWR    = 0x06 | OPC_C0,
339     OPC_TLBP     = 0x08 | OPC_C0,
340     OPC_RFE      = 0x10 | OPC_C0,
341     OPC_ERET     = 0x18 | OPC_C0,
342     OPC_DERET    = 0x1F | OPC_C0,
343     OPC_WAIT     = 0x20 | OPC_C0,
344 };
345
346 /* Coprocessor 1 (rs field) */
347 #define MASK_CP1(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
348
349 enum {
350     OPC_MFC1     = (0x00 << 21) | OPC_CP1,
351     OPC_DMFC1    = (0x01 << 21) | OPC_CP1,
352     OPC_CFC1     = (0x02 << 21) | OPC_CP1,
353     OPC_MFHC1    = (0x03 << 21) | OPC_CP1,
354     OPC_MTC1     = (0x04 << 21) | OPC_CP1,
355     OPC_DMTC1    = (0x05 << 21) | OPC_CP1,
356     OPC_CTC1     = (0x06 << 21) | OPC_CP1,
357     OPC_MTHC1    = (0x07 << 21) | OPC_CP1,
358     OPC_BC1      = (0x08 << 21) | OPC_CP1, /* bc */
359     OPC_BC1ANY2  = (0x09 << 21) | OPC_CP1,
360     OPC_BC1ANY4  = (0x0A << 21) | OPC_CP1,
361     OPC_S_FMT    = (0x10 << 21) | OPC_CP1, /* 16: fmt=single fp */
362     OPC_D_FMT    = (0x11 << 21) | OPC_CP1, /* 17: fmt=double fp */
363     OPC_E_FMT    = (0x12 << 21) | OPC_CP1, /* 18: fmt=extended fp */
364     OPC_Q_FMT    = (0x13 << 21) | OPC_CP1, /* 19: fmt=quad fp */
365     OPC_W_FMT    = (0x14 << 21) | OPC_CP1, /* 20: fmt=32bit fixed */
366     OPC_L_FMT    = (0x15 << 21) | OPC_CP1, /* 21: fmt=64bit fixed */
367     OPC_PS_FMT   = (0x16 << 21) | OPC_CP1, /* 22: fmt=paired single fp */
368 };
369
370 #define MASK_CP1_FUNC(op)       MASK_CP1(op) | (op & 0x3F)
371 #define MASK_BC1(op)            MASK_CP1(op) | (op & (0x3 << 16))
372
373 enum {
374     OPC_BC1F     = (0x00 << 16) | OPC_BC1,
375     OPC_BC1T     = (0x01 << 16) | OPC_BC1,
376     OPC_BC1FL    = (0x02 << 16) | OPC_BC1,
377     OPC_BC1TL    = (0x03 << 16) | OPC_BC1,
378 };
379
380 enum {
381     OPC_BC1FANY2     = (0x00 << 16) | OPC_BC1ANY2,
382     OPC_BC1TANY2     = (0x01 << 16) | OPC_BC1ANY2,
383 };
384
385 enum {
386     OPC_BC1FANY4     = (0x00 << 16) | OPC_BC1ANY4,
387     OPC_BC1TANY4     = (0x01 << 16) | OPC_BC1ANY4,
388 };
389
390 #define MASK_CP2(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
391
392 enum {
393     OPC_MFC2    = (0x00 << 21) | OPC_CP2,
394     OPC_DMFC2   = (0x01 << 21) | OPC_CP2,
395     OPC_CFC2    = (0x02 << 21) | OPC_CP2,
396     OPC_MFHC2   = (0x03 << 21) | OPC_CP2,
397     OPC_MTC2    = (0x04 << 21) | OPC_CP2,
398     OPC_DMTC2   = (0x05 << 21) | OPC_CP2,
399     OPC_CTC2    = (0x06 << 21) | OPC_CP2,
400     OPC_MTHC2   = (0x07 << 21) | OPC_CP2,
401     OPC_BC2     = (0x08 << 21) | OPC_CP2,
402 };
403
404 #define MASK_CP3(op)       MASK_OP_MAJOR(op) | (op & 0x3F)
405
406 enum {
407     OPC_LWXC1   = 0x00 | OPC_CP3,
408     OPC_LDXC1   = 0x01 | OPC_CP3,
409     OPC_LUXC1   = 0x05 | OPC_CP3,
410     OPC_SWXC1   = 0x08 | OPC_CP3,
411     OPC_SDXC1   = 0x09 | OPC_CP3,
412     OPC_SUXC1   = 0x0D | OPC_CP3,
413     OPC_PREFX   = 0x0F | OPC_CP3,
414     OPC_ALNV_PS = 0x1E | OPC_CP3,
415     OPC_MADD_S  = 0x20 | OPC_CP3,
416     OPC_MADD_D  = 0x21 | OPC_CP3,
417     OPC_MADD_PS = 0x26 | OPC_CP3,
418     OPC_MSUB_S  = 0x28 | OPC_CP3,
419     OPC_MSUB_D  = 0x29 | OPC_CP3,
420     OPC_MSUB_PS = 0x2E | OPC_CP3,
421     OPC_NMADD_S = 0x30 | OPC_CP3,
422     OPC_NMADD_D = 0x31 | OPC_CP3,
423     OPC_NMADD_PS= 0x36 | OPC_CP3,
424     OPC_NMSUB_S = 0x38 | OPC_CP3,
425     OPC_NMSUB_D = 0x39 | OPC_CP3,
426     OPC_NMSUB_PS= 0x3E | OPC_CP3,
427 };
428
429 /* global register indices */
430 static TCGv_ptr cpu_env;
431 static TCGv cpu_gpr[32], cpu_PC;
432 static TCGv cpu_HI[MIPS_DSP_ACC], cpu_LO[MIPS_DSP_ACC], cpu_ACX[MIPS_DSP_ACC];
433 static TCGv cpu_dspctrl, btarget, bcond;
434 static TCGv_i32 hflags;
435 static TCGv_i32 fpu_fcr0, fpu_fcr31;
436
437 #include "gen-icount.h"
438
439 #define gen_helper_0i(name, arg) do {                             \
440     TCGv_i32 helper_tmp = tcg_const_i32(arg);                     \
441     gen_helper_##name(helper_tmp);                                \
442     tcg_temp_free_i32(helper_tmp);                                \
443     } while(0)
444
445 #define gen_helper_1i(name, arg1, arg2) do {                      \
446     TCGv_i32 helper_tmp = tcg_const_i32(arg2);                    \
447     gen_helper_##name(arg1, helper_tmp);                          \
448     tcg_temp_free_i32(helper_tmp);                                \
449     } while(0)
450
451 #define gen_helper_2i(name, arg1, arg2, arg3) do {                \
452     TCGv_i32 helper_tmp = tcg_const_i32(arg3);                    \
453     gen_helper_##name(arg1, arg2, helper_tmp);                    \
454     tcg_temp_free_i32(helper_tmp);                                \
455     } while(0)
456
457 #define gen_helper_3i(name, arg1, arg2, arg3, arg4) do {          \
458     TCGv_i32 helper_tmp = tcg_const_i32(arg4);                    \
459     gen_helper_##name(arg1, arg2, arg3, helper_tmp);              \
460     tcg_temp_free_i32(helper_tmp);                                \
461     } while(0)
462
463 typedef struct DisasContext {
464     struct TranslationBlock *tb;
465     target_ulong pc, saved_pc;
466     uint32_t opcode;
467     /* Routine used to access memory */
468     int mem_idx;
469     uint32_t hflags, saved_hflags;
470     int bstate;
471     target_ulong btarget;
472 } DisasContext;
473
474 enum {
475     BS_NONE     = 0, /* We go out of the TB without reaching a branch or an
476                       * exception condition */
477     BS_STOP     = 1, /* We want to stop translation for any reason */
478     BS_BRANCH   = 2, /* We reached a branch condition     */
479     BS_EXCP     = 3, /* We reached an exception condition */
480 };
481
482 static const char *regnames[] =
483     { "r0", "at", "v0", "v1", "a0", "a1", "a2", "a3",
484       "t0", "t1", "t2", "t3", "t4", "t5", "t6", "t7",
485       "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7",
486       "t8", "t9", "k0", "k1", "gp", "sp", "s8", "ra", };
487
488 static const char *regnames_HI[] =
489     { "HI0", "HI1", "HI2", "HI3", };
490
491 static const char *regnames_LO[] =
492     { "LO0", "LO1", "LO2", "LO3", };
493
494 static const char *regnames_ACX[] =
495     { "ACX0", "ACX1", "ACX2", "ACX3", };
496
497 static const char *fregnames[] =
498     { "f0",  "f1",  "f2",  "f3",  "f4",  "f5",  "f6",  "f7",
499       "f8",  "f9",  "f10", "f11", "f12", "f13", "f14", "f15",
500       "f16", "f17", "f18", "f19", "f20", "f21", "f22", "f23",
501       "f24", "f25", "f26", "f27", "f28", "f29", "f30", "f31", };
502
503 #ifdef MIPS_DEBUG_DISAS
504 #define MIPS_DEBUG(fmt, args...)                         \
505         qemu_log_mask(CPU_LOG_TB_IN_ASM,                \
506                        TARGET_FMT_lx ": %08x " fmt "\n", \
507                        ctx->pc, ctx->opcode , ##args)
508 #define LOG_DISAS(...) qemu_log_mask(CPU_LOG_TB_IN_ASM, ## __VA_ARGS__)
509 #else
510 #define MIPS_DEBUG(fmt, args...) do { } while(0)
511 #define LOG_DISAS(...) do { } while (0)
512 #endif
513
514 #define MIPS_INVAL(op)                                                        \
515 do {                                                                          \
516     MIPS_DEBUG("Invalid %s %03x %03x %03x", op, ctx->opcode >> 26,            \
517                ctx->opcode & 0x3F, ((ctx->opcode >> 16) & 0x1F));             \
518 } while (0)
519
520 /* General purpose registers moves. */
521 static inline void gen_load_gpr (TCGv t, int reg)
522 {
523     if (reg == 0)
524         tcg_gen_movi_tl(t, 0);
525     else
526         tcg_gen_mov_tl(t, cpu_gpr[reg]);
527 }
528
529 static inline void gen_store_gpr (TCGv t, int reg)
530 {
531     if (reg != 0)
532         tcg_gen_mov_tl(cpu_gpr[reg], t);
533 }
534
535 /* Moves to/from ACX register.  */
536 static inline void gen_load_ACX (TCGv t, int reg)
537 {
538     tcg_gen_mov_tl(t, cpu_ACX[reg]);
539 }
540
541 static inline void gen_store_ACX (TCGv t, int reg)
542 {
543     tcg_gen_mov_tl(cpu_ACX[reg], t);
544 }
545
546 /* Moves to/from shadow registers. */
547 static inline void gen_load_srsgpr (int from, int to)
548 {
549     TCGv r_tmp1 = tcg_temp_new();
550
551     if (from == 0)
552         tcg_gen_movi_tl(r_tmp1, 0);
553     else {
554         TCGv_i32 r_tmp2 = tcg_temp_new_i32();
555         TCGv_ptr addr = tcg_temp_new_ptr();
556
557         tcg_gen_ld_i32(r_tmp2, cpu_env, offsetof(CPUState, CP0_SRSCtl));
558         tcg_gen_shri_i32(r_tmp2, r_tmp2, CP0SRSCtl_PSS);
559         tcg_gen_andi_i32(r_tmp2, r_tmp2, 0xf);
560         tcg_gen_muli_i32(r_tmp2, r_tmp2, sizeof(target_ulong) * 32);
561         tcg_gen_ext_i32_ptr(addr, r_tmp2);
562         tcg_gen_add_ptr(addr, cpu_env, addr);
563
564         tcg_gen_ld_tl(r_tmp1, addr, sizeof(target_ulong) * from);
565         tcg_temp_free_ptr(addr);
566         tcg_temp_free_i32(r_tmp2);
567     }
568     gen_store_gpr(r_tmp1, to);
569     tcg_temp_free(r_tmp1);
570 }
571
572 static inline void gen_store_srsgpr (int from, int to)
573 {
574     if (to != 0) {
575         TCGv r_tmp1 = tcg_temp_new();
576         TCGv_i32 r_tmp2 = tcg_temp_new_i32();
577         TCGv_ptr addr = tcg_temp_new_ptr();
578
579         gen_load_gpr(r_tmp1, from);
580         tcg_gen_ld_i32(r_tmp2, cpu_env, offsetof(CPUState, CP0_SRSCtl));
581         tcg_gen_shri_i32(r_tmp2, r_tmp2, CP0SRSCtl_PSS);
582         tcg_gen_andi_i32(r_tmp2, r_tmp2, 0xf);
583         tcg_gen_muli_i32(r_tmp2, r_tmp2, sizeof(target_ulong) * 32);
584         tcg_gen_ext_i32_ptr(addr, r_tmp2);
585         tcg_gen_add_ptr(addr, cpu_env, addr);
586
587         tcg_gen_st_tl(r_tmp1, addr, sizeof(target_ulong) * to);
588         tcg_temp_free_ptr(addr);
589         tcg_temp_free_i32(r_tmp2);
590         tcg_temp_free(r_tmp1);
591     }
592 }
593
594 /* Floating point register moves. */
595 static inline void gen_load_fpr32 (TCGv_i32 t, int reg)
596 {
597     tcg_gen_ld_i32(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].w[FP_ENDIAN_IDX]));
598 }
599
600 static inline void gen_store_fpr32 (TCGv_i32 t, int reg)
601 {
602     tcg_gen_st_i32(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].w[FP_ENDIAN_IDX]));
603 }
604
605 static inline void gen_load_fpr32h (TCGv_i32 t, int reg)
606 {
607     tcg_gen_ld_i32(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].w[!FP_ENDIAN_IDX]));
608 }
609
610 static inline void gen_store_fpr32h (TCGv_i32 t, int reg)
611 {
612     tcg_gen_st_i32(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].w[!FP_ENDIAN_IDX]));
613 }
614
615 static inline void gen_load_fpr64 (DisasContext *ctx, TCGv_i64 t, int reg)
616 {
617     if (ctx->hflags & MIPS_HFLAG_F64) {
618         tcg_gen_ld_i64(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].d));
619     } else {
620         TCGv_i32 t0 = tcg_temp_new_i32();
621         TCGv_i32 t1 = tcg_temp_new_i32();
622         gen_load_fpr32(t0, reg & ~1);
623         gen_load_fpr32(t1, reg | 1);
624         tcg_gen_concat_i32_i64(t, t0, t1);
625         tcg_temp_free_i32(t0);
626         tcg_temp_free_i32(t1);
627     }
628 }
629
630 static inline void gen_store_fpr64 (DisasContext *ctx, TCGv_i64 t, int reg)
631 {
632     if (ctx->hflags & MIPS_HFLAG_F64) {
633         tcg_gen_st_i64(t, cpu_env, offsetof(CPUState, active_fpu.fpr[reg].d));
634     } else {
635         TCGv_i64 t0 = tcg_temp_new_i64();
636         TCGv_i32 t1 = tcg_temp_new_i32();
637         tcg_gen_trunc_i64_i32(t1, t);
638         gen_store_fpr32(t1, reg & ~1);
639         tcg_gen_shri_i64(t0, t, 32);
640         tcg_gen_trunc_i64_i32(t1, t0);
641         gen_store_fpr32(t1, reg | 1);
642         tcg_temp_free_i32(t1);
643         tcg_temp_free_i64(t0);
644     }
645 }
646
647 static inline int get_fp_bit (int cc)
648 {
649     if (cc)
650         return 24 + cc;
651     else
652         return 23;
653 }
654
655 #define FOP_CONDS(type, fmt, bits)                                            \
656 static inline void gen_cmp ## type ## _ ## fmt(int n, TCGv_i##bits a,         \
657                                                TCGv_i##bits b, int cc)        \
658 {                                                                             \
659     switch (n) {                                                              \
660     case  0: gen_helper_2i(cmp ## type ## _ ## fmt ## _f, a, b, cc);    break;\
661     case  1: gen_helper_2i(cmp ## type ## _ ## fmt ## _un, a, b, cc);   break;\
662     case  2: gen_helper_2i(cmp ## type ## _ ## fmt ## _eq, a, b, cc);   break;\
663     case  3: gen_helper_2i(cmp ## type ## _ ## fmt ## _ueq, a, b, cc);  break;\
664     case  4: gen_helper_2i(cmp ## type ## _ ## fmt ## _olt, a, b, cc);  break;\
665     case  5: gen_helper_2i(cmp ## type ## _ ## fmt ## _ult, a, b, cc);  break;\
666     case  6: gen_helper_2i(cmp ## type ## _ ## fmt ## _ole, a, b, cc);  break;\
667     case  7: gen_helper_2i(cmp ## type ## _ ## fmt ## _ule, a, b, cc);  break;\
668     case  8: gen_helper_2i(cmp ## type ## _ ## fmt ## _sf, a, b, cc);   break;\
669     case  9: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngle, a, b, cc); break;\
670     case 10: gen_helper_2i(cmp ## type ## _ ## fmt ## _seq, a, b, cc);  break;\
671     case 11: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngl, a, b, cc);  break;\
672     case 12: gen_helper_2i(cmp ## type ## _ ## fmt ## _lt, a, b, cc);   break;\
673     case 13: gen_helper_2i(cmp ## type ## _ ## fmt ## _nge, a, b, cc);  break;\
674     case 14: gen_helper_2i(cmp ## type ## _ ## fmt ## _le, a, b, cc);   break;\
675     case 15: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngt, a, b, cc);  break;\
676     default: abort();                                                         \
677     }                                                                         \
678 }
679
680 FOP_CONDS(, d, 64)
681 FOP_CONDS(abs, d, 64)
682 FOP_CONDS(, s, 32)
683 FOP_CONDS(abs, s, 32)
684 FOP_CONDS(, ps, 64)
685 FOP_CONDS(abs, ps, 64)
686 #undef FOP_CONDS
687
688 /* Tests */
689 #define OP_COND(name, cond)                                         \
690 static inline void glue(gen_op_, name) (TCGv ret, TCGv t0, TCGv t1) \
691 {                                                                   \
692     int l1 = gen_new_label();                                       \
693     int l2 = gen_new_label();                                       \
694                                                                     \
695     tcg_gen_brcond_tl(cond, t0, t1, l1);                            \
696     tcg_gen_movi_tl(ret, 0);                                        \
697     tcg_gen_br(l2);                                                 \
698     gen_set_label(l1);                                              \
699     tcg_gen_movi_tl(ret, 1);                                        \
700     gen_set_label(l2);                                              \
701 }
702 OP_COND(eq, TCG_COND_EQ);
703 OP_COND(ne, TCG_COND_NE);
704 OP_COND(ge, TCG_COND_GE);
705 OP_COND(geu, TCG_COND_GEU);
706 OP_COND(lt, TCG_COND_LT);
707 OP_COND(ltu, TCG_COND_LTU);
708 #undef OP_COND
709
710 #define OP_CONDI(name, cond)                                                 \
711 static inline void glue(gen_op_, name) (TCGv ret, TCGv t0, target_ulong val) \
712 {                                                                            \
713     int l1 = gen_new_label();                                                \
714     int l2 = gen_new_label();                                                \
715                                                                              \
716     tcg_gen_brcondi_tl(cond, t0, val, l1);                                   \
717     tcg_gen_movi_tl(ret, 0);                                                 \
718     tcg_gen_br(l2);                                                          \
719     gen_set_label(l1);                                                       \
720     tcg_gen_movi_tl(ret, 1);                                                 \
721     gen_set_label(l2);                                                       \
722 }
723 OP_CONDI(lti, TCG_COND_LT);
724 OP_CONDI(ltiu, TCG_COND_LTU);
725 #undef OP_CONDI
726
727 #define OP_CONDZ(name, cond)                                  \
728 static inline void glue(gen_op_, name) (TCGv ret, TCGv t0)    \
729 {                                                             \
730     int l1 = gen_new_label();                                 \
731     int l2 = gen_new_label();                                 \
732                                                               \
733     tcg_gen_brcondi_tl(cond, t0, 0, l1);                      \
734     tcg_gen_movi_tl(ret, 0);                                  \
735     tcg_gen_br(l2);                                           \
736     gen_set_label(l1);                                        \
737     tcg_gen_movi_tl(ret, 1);                                  \
738     gen_set_label(l2);                                        \
739 }
740 OP_CONDZ(gez, TCG_COND_GE);
741 OP_CONDZ(gtz, TCG_COND_GT);
742 OP_CONDZ(lez, TCG_COND_LE);
743 OP_CONDZ(ltz, TCG_COND_LT);
744 #undef OP_CONDZ
745
746 static inline void gen_save_pc(target_ulong pc)
747 {
748     tcg_gen_movi_tl(cpu_PC, pc);
749 }
750
751 static inline void save_cpu_state (DisasContext *ctx, int do_save_pc)
752 {
753     LOG_DISAS("hflags %08x saved %08x\n", ctx->hflags, ctx->saved_hflags);
754     if (do_save_pc && ctx->pc != ctx->saved_pc) {
755         gen_save_pc(ctx->pc);
756         ctx->saved_pc = ctx->pc;
757     }
758     if (ctx->hflags != ctx->saved_hflags) {
759         tcg_gen_movi_i32(hflags, ctx->hflags);
760         ctx->saved_hflags = ctx->hflags;
761         switch (ctx->hflags & MIPS_HFLAG_BMASK) {
762         case MIPS_HFLAG_BR:
763             break;
764         case MIPS_HFLAG_BC:
765         case MIPS_HFLAG_BL:
766         case MIPS_HFLAG_B:
767             tcg_gen_movi_tl(btarget, ctx->btarget);
768             break;
769         }
770     }
771 }
772
773 static inline void restore_cpu_state (CPUState *env, DisasContext *ctx)
774 {
775     ctx->saved_hflags = ctx->hflags;
776     switch (ctx->hflags & MIPS_HFLAG_BMASK) {
777     case MIPS_HFLAG_BR:
778         break;
779     case MIPS_HFLAG_BC:
780     case MIPS_HFLAG_BL:
781     case MIPS_HFLAG_B:
782         ctx->btarget = env->btarget;
783         break;
784     }
785 }
786
787 static inline void
788 generate_exception_err (DisasContext *ctx, int excp, int err)
789 {
790     TCGv_i32 texcp = tcg_const_i32(excp);
791     TCGv_i32 terr = tcg_const_i32(err);
792     save_cpu_state(ctx, 1);
793     gen_helper_raise_exception_err(texcp, terr);
794     tcg_temp_free_i32(terr);
795     tcg_temp_free_i32(texcp);
796     gen_helper_interrupt_restart();
797     tcg_gen_exit_tb(0);
798 }
799
800 static inline void
801 generate_exception (DisasContext *ctx, int excp)
802 {
803     save_cpu_state(ctx, 1);
804     gen_helper_0i(raise_exception, excp);
805     gen_helper_interrupt_restart();
806     tcg_gen_exit_tb(0);
807 }
808
809 /* Addresses computation */
810 static inline void gen_op_addr_add (DisasContext *ctx, TCGv t0, TCGv t1)
811 {
812     tcg_gen_add_tl(t0, t0, t1);
813
814 #if defined(TARGET_MIPS64)
815     /* For compatibility with 32-bit code, data reference in user mode
816        with Status_UX = 0 should be casted to 32-bit and sign extended.
817        See the MIPS64 PRA manual, section 4.10. */
818     if (((ctx->hflags & MIPS_HFLAG_KSU) == MIPS_HFLAG_UM) &&
819         !(ctx->hflags & MIPS_HFLAG_UX)) {
820         tcg_gen_ext32s_i64(t0, t0);
821     }
822 #endif
823 }
824
825 static inline void check_cp0_enabled(DisasContext *ctx)
826 {
827     if (unlikely(!(ctx->hflags & MIPS_HFLAG_CP0)))
828         generate_exception_err(ctx, EXCP_CpU, 1);
829 }
830
831 static inline void check_cp1_enabled(DisasContext *ctx)
832 {
833     if (unlikely(!(ctx->hflags & MIPS_HFLAG_FPU)))
834         generate_exception_err(ctx, EXCP_CpU, 1);
835 }
836
837 /* Verify that the processor is running with COP1X instructions enabled.
838    This is associated with the nabla symbol in the MIPS32 and MIPS64
839    opcode tables.  */
840
841 static inline void check_cop1x(DisasContext *ctx)
842 {
843     if (unlikely(!(ctx->hflags & MIPS_HFLAG_COP1X)))
844         generate_exception(ctx, EXCP_RI);
845 }
846
847 /* Verify that the processor is running with 64-bit floating-point
848    operations enabled.  */
849
850 static inline void check_cp1_64bitmode(DisasContext *ctx)
851 {
852     if (unlikely(~ctx->hflags & (MIPS_HFLAG_F64 | MIPS_HFLAG_COP1X)))
853         generate_exception(ctx, EXCP_RI);
854 }
855
856 /*
857  * Verify if floating point register is valid; an operation is not defined
858  * if bit 0 of any register specification is set and the FR bit in the
859  * Status register equals zero, since the register numbers specify an
860  * even-odd pair of adjacent coprocessor general registers. When the FR bit
861  * in the Status register equals one, both even and odd register numbers
862  * are valid. This limitation exists only for 64 bit wide (d,l,ps) registers.
863  *
864  * Multiple 64 bit wide registers can be checked by calling
865  * gen_op_cp1_registers(freg1 | freg2 | ... | fregN);
866  */
867 static inline void check_cp1_registers(DisasContext *ctx, int regs)
868 {
869     if (unlikely(!(ctx->hflags & MIPS_HFLAG_F64) && (regs & 1)))
870         generate_exception(ctx, EXCP_RI);
871 }
872
873 /* This code generates a "reserved instruction" exception if the
874    CPU does not support the instruction set corresponding to flags. */
875 static inline void check_insn(CPUState *env, DisasContext *ctx, int flags)
876 {
877     if (unlikely(!(env->insn_flags & flags)))
878         generate_exception(ctx, EXCP_RI);
879 }
880
881 /* This code generates a "reserved instruction" exception if 64-bit
882    instructions are not enabled. */
883 static inline void check_mips_64(DisasContext *ctx)
884 {
885     if (unlikely(!(ctx->hflags & MIPS_HFLAG_64)))
886         generate_exception(ctx, EXCP_RI);
887 }
888
889 /* load/store instructions. */
890 #define OP_LD(insn,fname)                                        \
891 static inline void op_ldst_##insn(TCGv t0, DisasContext *ctx)    \
892 {                                                                \
893     tcg_gen_qemu_##fname(t0, t0, ctx->mem_idx);                  \
894 }
895 OP_LD(lb,ld8s);
896 OP_LD(lbu,ld8u);
897 OP_LD(lh,ld16s);
898 OP_LD(lhu,ld16u);
899 OP_LD(lw,ld32s);
900 #if defined(TARGET_MIPS64)
901 OP_LD(lwu,ld32u);
902 OP_LD(ld,ld64);
903 #endif
904 #undef OP_LD
905
906 #define OP_ST(insn,fname)                                        \
907 static inline void op_ldst_##insn(TCGv t0, TCGv t1, DisasContext *ctx) \
908 {                                                                \
909     tcg_gen_qemu_##fname(t1, t0, ctx->mem_idx);                  \
910 }
911 OP_ST(sb,st8);
912 OP_ST(sh,st16);
913 OP_ST(sw,st32);
914 #if defined(TARGET_MIPS64)
915 OP_ST(sd,st64);
916 #endif
917 #undef OP_ST
918
919 #define OP_LD_ATOMIC(insn,fname)                                        \
920 static inline void op_ldst_##insn(TCGv t0, TCGv t1, DisasContext *ctx)  \
921 {                                                                       \
922     tcg_gen_mov_tl(t1, t0);                                             \
923     tcg_gen_qemu_##fname(t0, t0, ctx->mem_idx);                         \
924     tcg_gen_st_tl(t1, cpu_env, offsetof(CPUState, CP0_LLAddr));         \
925 }
926 OP_LD_ATOMIC(ll,ld32s);
927 #if defined(TARGET_MIPS64)
928 OP_LD_ATOMIC(lld,ld64);
929 #endif
930 #undef OP_LD_ATOMIC
931
932 #define OP_ST_ATOMIC(insn,fname,almask)                                 \
933 static inline void op_ldst_##insn(TCGv t0, TCGv t1, DisasContext *ctx)  \
934 {                                                                       \
935     TCGv r_tmp = tcg_temp_new();                                        \
936     int l1 = gen_new_label();                                           \
937     int l2 = gen_new_label();                                           \
938     int l3 = gen_new_label();                                           \
939                                                                         \
940     tcg_gen_andi_tl(r_tmp, t0, almask);                                 \
941     tcg_gen_brcondi_tl(TCG_COND_EQ, r_tmp, 0, l1);                      \
942     tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_BadVAddr));       \
943     generate_exception(ctx, EXCP_AdES);                                 \
944     gen_set_label(l1);                                                  \
945     tcg_gen_ld_tl(r_tmp, cpu_env, offsetof(CPUState, CP0_LLAddr));      \
946     tcg_gen_brcond_tl(TCG_COND_NE, t0, r_tmp, l2);                      \
947     tcg_temp_free(r_tmp);                                               \
948     tcg_gen_qemu_##fname(t1, t0, ctx->mem_idx);                         \
949     tcg_gen_movi_tl(t0, 1);                                             \
950     tcg_gen_br(l3);                                                     \
951     gen_set_label(l2);                                                  \
952     tcg_gen_movi_tl(t0, 0);                                             \
953     gen_set_label(l3);                                                  \
954 }
955 OP_ST_ATOMIC(sc,st32,0x3);
956 #if defined(TARGET_MIPS64)
957 OP_ST_ATOMIC(scd,st64,0x7);
958 #endif
959 #undef OP_ST_ATOMIC
960
961 /* Load and store */
962 static void gen_ldst (DisasContext *ctx, uint32_t opc, int rt,
963                       int base, int16_t offset)
964 {
965     const char *opn = "ldst";
966     TCGv t0 = tcg_temp_new();
967     TCGv t1 = tcg_temp_new();
968
969     if (base == 0) {
970         tcg_gen_movi_tl(t0, offset);
971     } else if (offset == 0) {
972         gen_load_gpr(t0, base);
973     } else {
974         tcg_gen_movi_tl(t0, offset);
975         gen_op_addr_add(ctx, t0, cpu_gpr[base]);
976     }
977     /* Don't do NOP if destination is zero: we must perform the actual
978        memory access. */
979     switch (opc) {
980 #if defined(TARGET_MIPS64)
981     case OPC_LWU:
982         save_cpu_state(ctx, 0);
983         op_ldst_lwu(t0, ctx);
984         gen_store_gpr(t0, rt);
985         opn = "lwu";
986         break;
987     case OPC_LD:
988         save_cpu_state(ctx, 0);
989         op_ldst_ld(t0, ctx);
990         gen_store_gpr(t0, rt);
991         opn = "ld";
992         break;
993     case OPC_LLD:
994         save_cpu_state(ctx, 0);
995         op_ldst_lld(t0, t1, ctx);
996         gen_store_gpr(t0, rt);
997         opn = "lld";
998         break;
999     case OPC_SD:
1000         save_cpu_state(ctx, 0);
1001         gen_load_gpr(t1, rt);
1002         op_ldst_sd(t0, t1, ctx);
1003         opn = "sd";
1004         break;
1005     case OPC_LDL:
1006         save_cpu_state(ctx, 1);
1007         gen_load_gpr(t1, rt);
1008         gen_helper_3i(ldl, t1, t0, t1, ctx->mem_idx);
1009         gen_store_gpr(t1, rt);
1010         opn = "ldl";
1011         break;
1012     case OPC_SDL:
1013         save_cpu_state(ctx, 1);
1014         gen_load_gpr(t1, rt);
1015         gen_helper_2i(sdl, t0, t1, ctx->mem_idx);
1016         opn = "sdl";
1017         break;
1018     case OPC_LDR:
1019         save_cpu_state(ctx, 1);
1020         gen_load_gpr(t1, rt);
1021         gen_helper_3i(ldr, t1, t0, t1, ctx->mem_idx);
1022         gen_store_gpr(t1, rt);
1023         opn = "ldr";
1024         break;
1025     case OPC_SDR:
1026         save_cpu_state(ctx, 1);
1027         gen_load_gpr(t1, rt);
1028         gen_helper_2i(sdr, t0, t1, ctx->mem_idx);
1029         opn = "sdr";
1030         break;
1031 #endif
1032     case OPC_LW:
1033         save_cpu_state(ctx, 0);
1034         op_ldst_lw(t0, ctx);
1035         gen_store_gpr(t0, rt);
1036         opn = "lw";
1037         break;
1038     case OPC_SW:
1039         save_cpu_state(ctx, 0);
1040         gen_load_gpr(t1, rt);
1041         op_ldst_sw(t0, t1, ctx);
1042         opn = "sw";
1043         break;
1044     case OPC_LH:
1045         save_cpu_state(ctx, 0);
1046         op_ldst_lh(t0, ctx);
1047         gen_store_gpr(t0, rt);
1048         opn = "lh";
1049         break;
1050     case OPC_SH:
1051         save_cpu_state(ctx, 0);
1052         gen_load_gpr(t1, rt);
1053         op_ldst_sh(t0, t1, ctx);
1054         opn = "sh";
1055         break;
1056     case OPC_LHU:
1057         save_cpu_state(ctx, 0);
1058         op_ldst_lhu(t0, ctx);
1059         gen_store_gpr(t0, rt);
1060         opn = "lhu";
1061         break;
1062     case OPC_LB:
1063         save_cpu_state(ctx, 0);
1064         op_ldst_lb(t0, ctx);
1065         gen_store_gpr(t0, rt);
1066         opn = "lb";
1067         break;
1068     case OPC_SB:
1069         save_cpu_state(ctx, 0);
1070         gen_load_gpr(t1, rt);
1071         op_ldst_sb(t0, t1, ctx);
1072         opn = "sb";
1073         break;
1074     case OPC_LBU:
1075         save_cpu_state(ctx, 0);
1076         op_ldst_lbu(t0, ctx);
1077         gen_store_gpr(t0, rt);
1078         opn = "lbu";
1079         break;
1080     case OPC_LWL:
1081         save_cpu_state(ctx, 1);
1082         gen_load_gpr(t1, rt);
1083         gen_helper_3i(lwl, t1, t0, t1, ctx->mem_idx);
1084         gen_store_gpr(t1, rt);
1085         opn = "lwl";
1086         break;
1087     case OPC_SWL:
1088         save_cpu_state(ctx, 1);
1089         gen_load_gpr(t1, rt);
1090         gen_helper_2i(swl, t0, t1, ctx->mem_idx);
1091         opn = "swr";
1092         break;
1093     case OPC_LWR:
1094         save_cpu_state(ctx, 1);
1095         gen_load_gpr(t1, rt);
1096         gen_helper_3i(lwr, t1, t0, t1, ctx->mem_idx);
1097         gen_store_gpr(t1, rt);
1098         opn = "lwr";
1099         break;
1100     case OPC_SWR:
1101         save_cpu_state(ctx, 1);
1102         gen_load_gpr(t1, rt);
1103         gen_helper_2i(swr, t0, t1, ctx->mem_idx);
1104         opn = "swr";
1105         break;
1106     case OPC_LL:
1107         save_cpu_state(ctx, 0);
1108         op_ldst_ll(t0, t1, ctx);
1109         gen_store_gpr(t0, rt);
1110         opn = "ll";
1111         break;
1112     }
1113     MIPS_DEBUG("%s %s, %d(%s)", opn, regnames[rt], offset, regnames[base]);
1114     tcg_temp_free(t0);
1115     tcg_temp_free(t1);
1116 }
1117
1118 /* Store conditional */
1119 static void gen_st_cond (DisasContext *ctx, uint32_t opc, int rt,
1120                          int base, int16_t offset)
1121 {
1122     const char *opn = "st_cond";
1123     TCGv t0, t1;
1124
1125     t0 = tcg_temp_local_new();
1126
1127     if (base == 0) {
1128         tcg_gen_movi_tl(t0, offset);
1129     } else if (offset == 0) {
1130         gen_load_gpr(t0, base);
1131     } else {
1132         tcg_gen_movi_tl(t0, offset);
1133         gen_op_addr_add(ctx, t0, cpu_gpr[base]);
1134     }
1135     /* Don't do NOP if destination is zero: we must perform the actual
1136        memory access. */
1137
1138     t1 = tcg_temp_local_new();
1139     gen_load_gpr(t1, rt);
1140     switch (opc) {
1141 #if defined(TARGET_MIPS64)
1142     case OPC_SCD:
1143         save_cpu_state(ctx, 0);
1144         op_ldst_scd(t0, t1, ctx);
1145         opn = "scd";
1146         break;
1147 #endif
1148     case OPC_SC:
1149         save_cpu_state(ctx, 0);
1150         op_ldst_sc(t0, t1, ctx);
1151         opn = "sc";
1152         break;
1153     }
1154     MIPS_DEBUG("%s %s, %d(%s)", opn, regnames[rt], offset, regnames[base]);
1155     tcg_temp_free(t1);
1156     gen_store_gpr(t0, rt);
1157     tcg_temp_free(t0);
1158 }
1159
1160 /* Load and store */
1161 static void gen_flt_ldst (DisasContext *ctx, uint32_t opc, int ft,
1162                           int base, int16_t offset)
1163 {
1164     const char *opn = "flt_ldst";
1165     TCGv t0 = tcg_temp_new();
1166
1167     if (base == 0) {
1168         tcg_gen_movi_tl(t0, offset);
1169     } else if (offset == 0) {
1170         gen_load_gpr(t0, base);
1171     } else {
1172         tcg_gen_movi_tl(t0, offset);
1173         gen_op_addr_add(ctx, t0, cpu_gpr[base]);
1174     }
1175     /* Don't do NOP if destination is zero: we must perform the actual
1176        memory access. */
1177     switch (opc) {
1178     case OPC_LWC1:
1179         {
1180             TCGv_i32 fp0 = tcg_temp_new_i32();
1181             TCGv t1 = tcg_temp_new();
1182
1183             tcg_gen_qemu_ld32s(t1, t0, ctx->mem_idx);
1184             tcg_gen_trunc_tl_i32(fp0, t1);
1185             gen_store_fpr32(fp0, ft);
1186             tcg_temp_free(t1);
1187             tcg_temp_free_i32(fp0);
1188         }
1189         opn = "lwc1";
1190         break;
1191     case OPC_SWC1:
1192         {
1193             TCGv_i32 fp0 = tcg_temp_new_i32();
1194             TCGv t1 = tcg_temp_new();
1195
1196             gen_load_fpr32(fp0, ft);
1197             tcg_gen_extu_i32_tl(t1, fp0);
1198             tcg_gen_qemu_st32(t1, t0, ctx->mem_idx);
1199             tcg_temp_free(t1);
1200             tcg_temp_free_i32(fp0);
1201         }
1202         opn = "swc1";
1203         break;
1204     case OPC_LDC1:
1205         {
1206             TCGv_i64 fp0 = tcg_temp_new_i64();
1207
1208             tcg_gen_qemu_ld64(fp0, t0, ctx->mem_idx);
1209             gen_store_fpr64(ctx, fp0, ft);
1210             tcg_temp_free_i64(fp0);
1211         }
1212         opn = "ldc1";
1213         break;
1214     case OPC_SDC1:
1215         {
1216             TCGv_i64 fp0 = tcg_temp_new_i64();
1217
1218             gen_load_fpr64(ctx, fp0, ft);
1219             tcg_gen_qemu_st64(fp0, t0, ctx->mem_idx);
1220             tcg_temp_free_i64(fp0);
1221         }
1222         opn = "sdc1";
1223         break;
1224     default:
1225         MIPS_INVAL(opn);
1226         generate_exception(ctx, EXCP_RI);
1227         goto out;
1228     }
1229     MIPS_DEBUG("%s %s, %d(%s)", opn, fregnames[ft], offset, regnames[base]);
1230  out:
1231     tcg_temp_free(t0);
1232 }
1233
1234 /* Arithmetic with immediate operand */
1235 static void gen_arith_imm (CPUState *env, DisasContext *ctx, uint32_t opc,
1236                            int rt, int rs, int16_t imm)
1237 {
1238     target_ulong uimm = (target_long)imm; /* Sign extend to 32/64 bits */
1239     const char *opn = "imm arith";
1240
1241     if (rt == 0 && opc != OPC_ADDI && opc != OPC_DADDI) {
1242         /* If no destination, treat it as a NOP.
1243            For addi, we must generate the overflow exception when needed. */
1244         MIPS_DEBUG("NOP");
1245         return;
1246     }
1247     switch (opc) {
1248     case OPC_ADDI:
1249         {
1250             TCGv t0 = tcg_temp_local_new();
1251             TCGv t1 = tcg_temp_new();
1252             TCGv t2 = tcg_temp_new();
1253             int l1 = gen_new_label();
1254
1255             gen_load_gpr(t1, rs);
1256             tcg_gen_addi_tl(t0, t1, uimm);
1257             tcg_gen_ext32s_tl(t0, t0);
1258
1259             tcg_gen_xori_tl(t1, t1, ~uimm);
1260             tcg_gen_xori_tl(t2, t0, uimm);
1261             tcg_gen_and_tl(t1, t1, t2);
1262             tcg_temp_free(t2);
1263             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1264             tcg_temp_free(t1);
1265             /* operands of same sign, result different sign */
1266             generate_exception(ctx, EXCP_OVERFLOW);
1267             gen_set_label(l1);
1268             tcg_gen_ext32s_tl(t0, t0);
1269             gen_store_gpr(t0, rt);
1270             tcg_temp_free(t0);
1271         }
1272         opn = "addi";
1273         break;
1274     case OPC_ADDIU:
1275         if (rs != 0) {
1276             tcg_gen_addi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1277             tcg_gen_ext32s_tl(cpu_gpr[rt], cpu_gpr[rt]);
1278         } else {
1279             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1280         }
1281         opn = "addiu";
1282         break;
1283 #if defined(TARGET_MIPS64)
1284     case OPC_DADDI:
1285         {
1286             TCGv t0 = tcg_temp_local_new();
1287             TCGv t1 = tcg_temp_new();
1288             TCGv t2 = tcg_temp_new();
1289             int l1 = gen_new_label();
1290
1291             gen_load_gpr(t1, rs);
1292             tcg_gen_addi_tl(t0, t1, uimm);
1293
1294             tcg_gen_xori_tl(t1, t1, ~uimm);
1295             tcg_gen_xori_tl(t2, t0, uimm);
1296             tcg_gen_and_tl(t1, t1, t2);
1297             tcg_temp_free(t2);
1298             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1299             tcg_temp_free(t1);
1300             /* operands of same sign, result different sign */
1301             generate_exception(ctx, EXCP_OVERFLOW);
1302             gen_set_label(l1);
1303             gen_store_gpr(t0, rt);
1304             tcg_temp_free(t0);
1305         }
1306         opn = "daddi";
1307         break;
1308     case OPC_DADDIU:
1309         if (rs != 0) {
1310             tcg_gen_addi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1311         } else {
1312             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1313         }
1314         opn = "daddiu";
1315         break;
1316 #endif
1317     }
1318     MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1319 }
1320
1321 /* Logic with immediate operand */
1322 static void gen_logic_imm (CPUState *env, uint32_t opc, int rt, int rs, int16_t imm)
1323 {
1324     target_ulong uimm;
1325     const char *opn = "imm logic";
1326
1327     if (rt == 0) {
1328         /* If no destination, treat it as a NOP. */
1329         MIPS_DEBUG("NOP");
1330         return;
1331     }
1332     uimm = (uint16_t)imm;
1333     switch (opc) {
1334     case OPC_ANDI:
1335         if (likely(rs != 0))
1336             tcg_gen_andi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1337         else
1338             tcg_gen_movi_tl(cpu_gpr[rt], 0);
1339         opn = "andi";
1340         break;
1341     case OPC_ORI:
1342         if (rs != 0)
1343             tcg_gen_ori_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1344         else
1345             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1346         opn = "ori";
1347         break;
1348     case OPC_XORI:
1349         if (likely(rs != 0))
1350             tcg_gen_xori_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1351         else
1352             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1353         opn = "xori";
1354         break;
1355     case OPC_LUI:
1356         tcg_gen_movi_tl(cpu_gpr[rt], imm << 16);
1357         opn = "lui";
1358         break;
1359     }
1360     MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1361 }
1362
1363 /* Set on less than with immediate operand */
1364 static void gen_slt_imm (CPUState *env, uint32_t opc, int rt, int rs, int16_t imm)
1365 {
1366     target_ulong uimm = (target_long)imm; /* Sign extend to 32/64 bits */
1367     const char *opn = "imm arith";
1368     TCGv t0;
1369
1370     if (rt == 0) {
1371         /* If no destination, treat it as a NOP. */
1372         MIPS_DEBUG("NOP");
1373         return;
1374     }
1375     t0 = tcg_temp_new();
1376     gen_load_gpr(t0, rs);
1377     switch (opc) {
1378     case OPC_SLTI:
1379         gen_op_lti(cpu_gpr[rt], t0, uimm);
1380         opn = "slti";
1381         break;
1382     case OPC_SLTIU:
1383         gen_op_ltiu(cpu_gpr[rt], t0, uimm);
1384         opn = "sltiu";
1385         break;
1386     }
1387     MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1388     tcg_temp_free(t0);
1389 }
1390
1391 /* Shifts with immediate operand */
1392 static void gen_shift_imm(CPUState *env, DisasContext *ctx, uint32_t opc,
1393                           int rt, int rs, int16_t imm)
1394 {
1395     target_ulong uimm = ((uint16_t)imm) & 0x1f;
1396     const char *opn = "imm shift";
1397     TCGv t0;
1398
1399     if (rt == 0) {
1400         /* If no destination, treat it as a NOP. */
1401         MIPS_DEBUG("NOP");
1402         return;
1403     }
1404
1405     t0 = tcg_temp_new();
1406     gen_load_gpr(t0, rs);
1407     switch (opc) {
1408     case OPC_SLL:
1409         tcg_gen_shli_tl(t0, t0, uimm);
1410         tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
1411         opn = "sll";
1412         break;
1413     case OPC_SRA:
1414         tcg_gen_ext32s_tl(t0, t0);
1415         tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm);
1416         opn = "sra";
1417         break;
1418     case OPC_SRL:
1419         switch ((ctx->opcode >> 21) & 0x1f) {
1420         case 0:
1421             if (uimm != 0) {
1422                 tcg_gen_ext32u_tl(t0, t0);
1423                 tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm);
1424             } else {
1425                 tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
1426             }
1427             opn = "srl";
1428             break;
1429         case 1:
1430             /* rotr is decoded as srl on non-R2 CPUs */
1431             if (env->insn_flags & ISA_MIPS32R2) {
1432                 if (uimm != 0) {
1433                     TCGv_i32 r_tmp1 = tcg_temp_new_i32();
1434
1435                     tcg_gen_trunc_tl_i32(r_tmp1, t0);
1436                     tcg_gen_rotri_i32(r_tmp1, r_tmp1, uimm);
1437                     tcg_gen_ext_i32_tl(cpu_gpr[rt], r_tmp1);
1438                     tcg_temp_free_i32(r_tmp1);
1439                 }
1440                 opn = "rotr";
1441             } else {
1442                 if (uimm != 0) {
1443                     tcg_gen_ext32u_tl(t0, t0);
1444                     tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm);
1445                 } else {
1446                     tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
1447                 }
1448                 opn = "srl";
1449             }
1450             break;
1451         default:
1452             MIPS_INVAL("invalid srl flag");
1453             generate_exception(ctx, EXCP_RI);
1454             break;
1455         }
1456         break;
1457 #if defined(TARGET_MIPS64)
1458     case OPC_DSLL:
1459         tcg_gen_shli_tl(cpu_gpr[rt], t0, uimm);
1460         opn = "dsll";
1461         break;
1462     case OPC_DSRA:
1463         tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm);
1464         opn = "dsra";
1465         break;
1466     case OPC_DSRL:
1467         switch ((ctx->opcode >> 21) & 0x1f) {
1468         case 0:
1469             tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm);
1470             opn = "dsrl";
1471             break;
1472         case 1:
1473             /* drotr is decoded as dsrl on non-R2 CPUs */
1474             if (env->insn_flags & ISA_MIPS32R2) {
1475                 if (uimm != 0) {
1476                     tcg_gen_rotri_tl(cpu_gpr[rt], t0, uimm);
1477                 }
1478                 opn = "drotr";
1479             } else {
1480                 tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm);
1481                 opn = "dsrl";
1482             }
1483             break;
1484         default:
1485             MIPS_INVAL("invalid dsrl flag");
1486             generate_exception(ctx, EXCP_RI);
1487             break;
1488         }
1489         break;
1490     case OPC_DSLL32:
1491         tcg_gen_shli_tl(cpu_gpr[rt], t0, uimm + 32);
1492         opn = "dsll32";
1493         break;
1494     case OPC_DSRA32:
1495         tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm + 32);
1496         opn = "dsra32";
1497         break;
1498     case OPC_DSRL32:
1499         switch ((ctx->opcode >> 21) & 0x1f) {
1500         case 0:
1501             tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm + 32);
1502             opn = "dsrl32";
1503             break;
1504         case 1:
1505             /* drotr32 is decoded as dsrl32 on non-R2 CPUs */
1506             if (env->insn_flags & ISA_MIPS32R2) {
1507                 tcg_gen_rotri_tl(cpu_gpr[rt], t0, uimm + 32);
1508                 opn = "drotr32";
1509             } else {
1510                 tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm + 32);
1511                 opn = "dsrl32";
1512             }
1513             break;
1514         default:
1515             MIPS_INVAL("invalid dsrl32 flag");
1516             generate_exception(ctx, EXCP_RI);
1517             break;
1518         }
1519         break;
1520 #endif
1521     }
1522     MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1523     tcg_temp_free(t0);
1524 }
1525
1526 /* Arithmetic */
1527 static void gen_arith (CPUState *env, DisasContext *ctx, uint32_t opc,
1528                        int rd, int rs, int rt)
1529 {
1530     const char *opn = "arith";
1531
1532     if (rd == 0 && opc != OPC_ADD && opc != OPC_SUB
1533        && opc != OPC_DADD && opc != OPC_DSUB) {
1534         /* If no destination, treat it as a NOP.
1535            For add & sub, we must generate the overflow exception when needed. */
1536         MIPS_DEBUG("NOP");
1537         return;
1538     }
1539
1540     switch (opc) {
1541     case OPC_ADD:
1542         {
1543             TCGv t0 = tcg_temp_local_new();
1544             TCGv t1 = tcg_temp_new();
1545             TCGv t2 = tcg_temp_new();
1546             int l1 = gen_new_label();
1547
1548             gen_load_gpr(t1, rs);
1549             gen_load_gpr(t2, rt);
1550             tcg_gen_add_tl(t0, t1, t2);
1551             tcg_gen_ext32s_tl(t0, t0);
1552             tcg_gen_xor_tl(t1, t1, t2);
1553             tcg_gen_not_tl(t1, t1);
1554             tcg_gen_xor_tl(t2, t0, t2);
1555             tcg_gen_and_tl(t1, t1, t2);
1556             tcg_temp_free(t2);
1557             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1558             tcg_temp_free(t1);
1559             /* operands of same sign, result different sign */
1560             generate_exception(ctx, EXCP_OVERFLOW);
1561             gen_set_label(l1);
1562             gen_store_gpr(t0, rd);
1563             tcg_temp_free(t0);
1564         }
1565         opn = "add";
1566         break;
1567     case OPC_ADDU:
1568         if (rs != 0 && rt != 0) {
1569             tcg_gen_add_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1570             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1571         } else if (rs == 0 && rt != 0) {
1572             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1573         } else if (rs != 0 && rt == 0) {
1574             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1575         } else {
1576             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1577         }
1578         opn = "addu";
1579         break;
1580     case OPC_SUB:
1581         {
1582             TCGv t0 = tcg_temp_local_new();
1583             TCGv t1 = tcg_temp_new();
1584             TCGv t2 = tcg_temp_new();
1585             int l1 = gen_new_label();
1586
1587             gen_load_gpr(t1, rs);
1588             gen_load_gpr(t2, rt);
1589             tcg_gen_sub_tl(t0, t1, t2);
1590             tcg_gen_ext32s_tl(t0, t0);
1591             tcg_gen_xor_tl(t2, t1, t2);
1592             tcg_gen_xor_tl(t1, t0, t1);
1593             tcg_gen_and_tl(t1, t1, t2);
1594             tcg_temp_free(t2);
1595             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1596             tcg_temp_free(t1);
1597             /* operands of same sign, result different sign */
1598             generate_exception(ctx, EXCP_OVERFLOW);
1599             gen_set_label(l1);
1600             gen_store_gpr(t0, rd);
1601             tcg_temp_free(t0);
1602         }
1603         opn = "sub";
1604         break;
1605     case OPC_SUBU:
1606         if (rs != 0 && rt != 0) {
1607             tcg_gen_sub_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1608             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1609         } else if (rs == 0 && rt != 0) {
1610             tcg_gen_neg_tl(cpu_gpr[rd], cpu_gpr[rt]);
1611         } else if (rs != 0 && rt == 0) {
1612             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1613         } else {
1614             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1615         }
1616         opn = "subu";
1617         break;
1618 #if defined(TARGET_MIPS64)
1619     case OPC_DADD:
1620         {
1621             TCGv t0 = tcg_temp_local_new();
1622             TCGv t1 = tcg_temp_new();
1623             TCGv t2 = tcg_temp_new();
1624             int l1 = gen_new_label();
1625
1626             gen_load_gpr(t1, rs);
1627             gen_load_gpr(t2, rt);
1628             tcg_gen_add_tl(t0, t1, t2);
1629             tcg_gen_xor_tl(t1, t1, t2);
1630             tcg_gen_not_tl(t1, t1);
1631             tcg_gen_xor_tl(t2, t0, t2);
1632             tcg_gen_and_tl(t1, t1, t2);
1633             tcg_temp_free(t2);
1634             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1635             tcg_temp_free(t1);
1636             /* operands of same sign, result different sign */
1637             generate_exception(ctx, EXCP_OVERFLOW);
1638             gen_set_label(l1);
1639             gen_store_gpr(t0, rd);
1640             tcg_temp_free(t0);
1641         }
1642         opn = "dadd";
1643         break;
1644     case OPC_DADDU:
1645         if (rs != 0 && rt != 0) {
1646             tcg_gen_add_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1647         } else if (rs == 0 && rt != 0) {
1648             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1649         } else if (rs != 0 && rt == 0) {
1650             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1651         } else {
1652             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1653         }
1654         opn = "daddu";
1655         break;
1656     case OPC_DSUB:
1657         {
1658             TCGv t0 = tcg_temp_local_new();
1659             TCGv t1 = tcg_temp_new();
1660             TCGv t2 = tcg_temp_new();
1661             int l1 = gen_new_label();
1662
1663             gen_load_gpr(t1, rs);
1664             gen_load_gpr(t2, rt);
1665             tcg_gen_sub_tl(t0, t1, t2);
1666             tcg_gen_xor_tl(t2, t1, t2);
1667             tcg_gen_xor_tl(t1, t0, t1);
1668             tcg_gen_and_tl(t1, t1, t2);
1669             tcg_temp_free(t2);
1670             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1671             tcg_temp_free(t1);
1672             /* operands of same sign, result different sign */
1673             generate_exception(ctx, EXCP_OVERFLOW);
1674             gen_set_label(l1);
1675             gen_store_gpr(t0, rd);
1676             tcg_temp_free(t0);
1677         }
1678         opn = "dsub";
1679         break;
1680     case OPC_DSUBU:
1681         if (rs != 0 && rt != 0) {
1682             tcg_gen_sub_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1683         } else if (rs == 0 && rt != 0) {
1684             tcg_gen_neg_tl(cpu_gpr[rd], cpu_gpr[rt]);
1685         } else if (rs != 0 && rt == 0) {
1686             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1687         } else {
1688             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1689         }
1690         opn = "dsubu";
1691         break;
1692 #endif
1693     case OPC_MUL:
1694         if (likely(rs != 0 && rt != 0)) {
1695             tcg_gen_mul_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1696             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1697         } else {
1698             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1699         }
1700         opn = "mul";
1701         break;
1702     }
1703     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1704 }
1705
1706 /* Conditional move */
1707 static void gen_cond_move (CPUState *env, uint32_t opc, int rd, int rs, int rt)
1708 {
1709     const char *opn = "cond move";
1710     int l1;
1711
1712     if (rd == 0) {
1713         /* If no destination, treat it as a NOP.
1714            For add & sub, we must generate the overflow exception when needed. */
1715         MIPS_DEBUG("NOP");
1716         return;
1717     }
1718
1719     l1 = gen_new_label();
1720     switch (opc) {
1721     case OPC_MOVN:
1722         if (likely(rt != 0))
1723             tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[rt], 0, l1);
1724         else
1725             tcg_gen_br(l1);
1726         opn = "movn";
1727         break;
1728     case OPC_MOVZ:
1729         if (likely(rt != 0))
1730             tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[rt], 0, l1);
1731         opn = "movz";
1732         break;
1733     }
1734     if (rs != 0)
1735         tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1736     else
1737         tcg_gen_movi_tl(cpu_gpr[rd], 0);
1738     gen_set_label(l1);
1739
1740     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1741 }
1742
1743 /* Logic */
1744 static void gen_logic (CPUState *env, uint32_t opc, int rd, int rs, int rt)
1745 {
1746     const char *opn = "logic";
1747
1748     if (rd == 0) {
1749         /* If no destination, treat it as a NOP. */
1750         MIPS_DEBUG("NOP");
1751         return;
1752     }
1753
1754     switch (opc) {
1755     case OPC_AND:
1756         if (likely(rs != 0 && rt != 0)) {
1757             tcg_gen_and_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1758         } else {
1759             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1760         }
1761         opn = "and";
1762         break;
1763     case OPC_NOR:
1764         if (rs != 0 && rt != 0) {
1765             tcg_gen_nor_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1766         } else if (rs == 0 && rt != 0) {
1767             tcg_gen_not_tl(cpu_gpr[rd], cpu_gpr[rt]);
1768         } else if (rs != 0 && rt == 0) {
1769             tcg_gen_not_tl(cpu_gpr[rd], cpu_gpr[rs]);
1770         } else {
1771             tcg_gen_movi_tl(cpu_gpr[rd], ~((target_ulong)0));
1772         }
1773         opn = "nor";
1774         break;
1775     case OPC_OR:
1776         if (likely(rs != 0 && rt != 0)) {
1777             tcg_gen_or_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1778         } else if (rs == 0 && rt != 0) {
1779             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1780         } else if (rs != 0 && rt == 0) {
1781             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1782         } else {
1783             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1784         }
1785         opn = "or";
1786         break;
1787     case OPC_XOR:
1788         if (likely(rs != 0 && rt != 0)) {
1789             tcg_gen_xor_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1790         } else if (rs == 0 && rt != 0) {
1791             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1792         } else if (rs != 0 && rt == 0) {
1793             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1794         } else {
1795             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1796         }
1797         opn = "xor";
1798         break;
1799     }
1800     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1801 }
1802
1803 /* Set on lower than */
1804 static void gen_slt (CPUState *env, uint32_t opc, int rd, int rs, int rt)
1805 {
1806     const char *opn = "slt";
1807     TCGv t0, t1;
1808
1809     if (rd == 0) {
1810         /* If no destination, treat it as a NOP. */
1811         MIPS_DEBUG("NOP");
1812         return;
1813     }
1814
1815     t0 = tcg_temp_new();
1816     t1 = tcg_temp_new();
1817     gen_load_gpr(t0, rs);
1818     gen_load_gpr(t1, rt);
1819     switch (opc) {
1820     case OPC_SLT:
1821         gen_op_lt(cpu_gpr[rd], t0, t1);
1822         opn = "slt";
1823         break;
1824     case OPC_SLTU:
1825         gen_op_ltu(cpu_gpr[rd], t0, t1);
1826         opn = "sltu";
1827         break;
1828     }
1829     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1830     tcg_temp_free(t0);
1831     tcg_temp_free(t1);
1832 }
1833
1834 /* Shifts */
1835 static void gen_shift (CPUState *env, DisasContext *ctx, uint32_t opc,
1836                        int rd, int rs, int rt)
1837 {
1838     const char *opn = "shifts";
1839     TCGv t0, t1;
1840
1841     if (rd == 0) {
1842         /* If no destination, treat it as a NOP.
1843            For add & sub, we must generate the overflow exception when needed. */
1844         MIPS_DEBUG("NOP");
1845         return;
1846     }
1847
1848     t0 = tcg_temp_new();
1849     t1 = tcg_temp_new();
1850     gen_load_gpr(t0, rs);
1851     gen_load_gpr(t1, rt);
1852     switch (opc) {
1853     case OPC_SLLV:
1854         tcg_gen_andi_tl(t0, t0, 0x1f);
1855         tcg_gen_shl_tl(t0, t1, t0);
1856         tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
1857         opn = "sllv";
1858         break;
1859     case OPC_SRAV:
1860         tcg_gen_ext32s_tl(t1, t1);
1861         tcg_gen_andi_tl(t0, t0, 0x1f);
1862         tcg_gen_sar_tl(cpu_gpr[rd], t1, t0);
1863         opn = "srav";
1864         break;
1865     case OPC_SRLV:
1866         switch ((ctx->opcode >> 6) & 0x1f) {
1867         case 0:
1868             tcg_gen_ext32u_tl(t1, t1);
1869             tcg_gen_andi_tl(t0, t0, 0x1f);
1870             tcg_gen_shr_tl(t0, t1, t0);
1871             tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
1872             opn = "srlv";
1873             break;
1874         case 1:
1875             /* rotrv is decoded as srlv on non-R2 CPUs */
1876             if (env->insn_flags & ISA_MIPS32R2) {
1877                 TCGv_i32 t2 = tcg_temp_new_i32();
1878                 TCGv_i32 t3 = tcg_temp_new_i32();
1879
1880                 tcg_gen_trunc_tl_i32(t2, t0);
1881                 tcg_gen_trunc_tl_i32(t3, t1);
1882                 tcg_gen_andi_i32(t2, t2, 0x1f);
1883                 tcg_gen_rotr_i32(t2, t3, t2);
1884                 tcg_gen_ext_i32_tl(cpu_gpr[rd], t2);
1885                 tcg_temp_free_i32(t2);
1886                 tcg_temp_free_i32(t3);
1887                 opn = "rotrv";
1888             } else {
1889                 tcg_gen_ext32u_tl(t1, t1);
1890                 tcg_gen_andi_tl(t0, t0, 0x1f);
1891                 tcg_gen_shr_tl(t0, t1, t0);
1892                 tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
1893                 opn = "srlv";
1894             }
1895             break;
1896         default:
1897             MIPS_INVAL("invalid srlv flag");
1898             generate_exception(ctx, EXCP_RI);
1899             break;
1900         }
1901         break;
1902 #if defined(TARGET_MIPS64)
1903     case OPC_DSLLV:
1904         tcg_gen_andi_tl(t0, t0, 0x3f);
1905         tcg_gen_shl_tl(cpu_gpr[rd], t1, t0);
1906         opn = "dsllv";
1907         break;
1908     case OPC_DSRAV:
1909         tcg_gen_andi_tl(t0, t0, 0x3f);
1910         tcg_gen_sar_tl(cpu_gpr[rd], t1, t0);
1911         opn = "dsrav";
1912         break;
1913     case OPC_DSRLV:
1914         switch ((ctx->opcode >> 6) & 0x1f) {
1915         case 0:
1916             tcg_gen_andi_tl(t0, t0, 0x3f);
1917             tcg_gen_shr_tl(cpu_gpr[rd], t1, t0);
1918             opn = "dsrlv";
1919             break;
1920         case 1:
1921             /* drotrv is decoded as dsrlv on non-R2 CPUs */
1922             if (env->insn_flags & ISA_MIPS32R2) {
1923                 tcg_gen_andi_tl(t0, t0, 0x3f);
1924                 tcg_gen_rotr_tl(cpu_gpr[rd], t1, t0);
1925                 opn = "drotrv";
1926             } else {
1927                 tcg_gen_andi_tl(t0, t0, 0x3f);
1928                 tcg_gen_shr_tl(t0, t1, t0);
1929                 opn = "dsrlv";
1930             }
1931             break;
1932         default:
1933             MIPS_INVAL("invalid dsrlv flag");
1934             generate_exception(ctx, EXCP_RI);
1935             break;
1936         }
1937         break;
1938 #endif
1939     }
1940     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1941     tcg_temp_free(t0);
1942     tcg_temp_free(t1);
1943 }
1944
1945 /* Arithmetic on HI/LO registers */
1946 static void gen_HILO (DisasContext *ctx, uint32_t opc, int reg)
1947 {
1948     const char *opn = "hilo";
1949
1950     if (reg == 0 && (opc == OPC_MFHI || opc == OPC_MFLO)) {
1951         /* Treat as NOP. */
1952         MIPS_DEBUG("NOP");
1953         return;
1954     }
1955     switch (opc) {
1956     case OPC_MFHI:
1957         tcg_gen_mov_tl(cpu_gpr[reg], cpu_HI[0]);
1958         opn = "mfhi";
1959         break;
1960     case OPC_MFLO:
1961         tcg_gen_mov_tl(cpu_gpr[reg], cpu_LO[0]);
1962         opn = "mflo";
1963         break;
1964     case OPC_MTHI:
1965         if (reg != 0)
1966             tcg_gen_mov_tl(cpu_HI[0], cpu_gpr[reg]);
1967         else
1968             tcg_gen_movi_tl(cpu_HI[0], 0);
1969         opn = "mthi";
1970         break;
1971     case OPC_MTLO:
1972         if (reg != 0)
1973             tcg_gen_mov_tl(cpu_LO[0], cpu_gpr[reg]);
1974         else
1975             tcg_gen_movi_tl(cpu_LO[0], 0);
1976         opn = "mtlo";
1977         break;
1978     }
1979     MIPS_DEBUG("%s %s", opn, regnames[reg]);
1980 }
1981
1982 static void gen_muldiv (DisasContext *ctx, uint32_t opc,
1983                         int rs, int rt)
1984 {
1985     const char *opn = "mul/div";
1986     TCGv t0, t1;
1987
1988     switch (opc) {
1989     case OPC_DIV:
1990     case OPC_DIVU:
1991 #if defined(TARGET_MIPS64)
1992     case OPC_DDIV:
1993     case OPC_DDIVU:
1994 #endif
1995         t0 = tcg_temp_local_new();
1996         t1 = tcg_temp_local_new();
1997         break;
1998     default:
1999         t0 = tcg_temp_new();
2000         t1 = tcg_temp_new();
2001         break;
2002     }
2003
2004     gen_load_gpr(t0, rs);
2005     gen_load_gpr(t1, rt);
2006     switch (opc) {
2007     case OPC_DIV:
2008         {
2009             int l1 = gen_new_label();
2010             int l2 = gen_new_label();
2011
2012             tcg_gen_ext32s_tl(t0, t0);
2013             tcg_gen_ext32s_tl(t1, t1);
2014             tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2015             tcg_gen_brcondi_tl(TCG_COND_NE, t0, INT_MIN, l2);
2016             tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1, l2);
2017
2018             tcg_gen_mov_tl(cpu_LO[0], t0);
2019             tcg_gen_movi_tl(cpu_HI[0], 0);
2020             tcg_gen_br(l1);
2021             gen_set_label(l2);
2022             tcg_gen_div_tl(cpu_LO[0], t0, t1);
2023             tcg_gen_rem_tl(cpu_HI[0], t0, t1);
2024             tcg_gen_ext32s_tl(cpu_LO[0], cpu_LO[0]);
2025             tcg_gen_ext32s_tl(cpu_HI[0], cpu_HI[0]);
2026             gen_set_label(l1);
2027         }
2028         opn = "div";
2029         break;
2030     case OPC_DIVU:
2031         {
2032             int l1 = gen_new_label();
2033
2034             tcg_gen_ext32u_tl(t0, t0);
2035             tcg_gen_ext32u_tl(t1, t1);
2036             tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2037             tcg_gen_divu_tl(cpu_LO[0], t0, t1);
2038             tcg_gen_remu_tl(cpu_HI[0], t0, t1);
2039             tcg_gen_ext32s_tl(cpu_LO[0], cpu_LO[0]);
2040             tcg_gen_ext32s_tl(cpu_HI[0], cpu_HI[0]);
2041             gen_set_label(l1);
2042         }
2043         opn = "divu";
2044         break;
2045     case OPC_MULT:
2046         {
2047             TCGv_i64 t2 = tcg_temp_new_i64();
2048             TCGv_i64 t3 = tcg_temp_new_i64();
2049
2050             tcg_gen_ext_tl_i64(t2, t0);
2051             tcg_gen_ext_tl_i64(t3, t1);
2052             tcg_gen_mul_i64(t2, t2, t3);
2053             tcg_temp_free_i64(t3);
2054             tcg_gen_trunc_i64_tl(t0, t2);
2055             tcg_gen_shri_i64(t2, t2, 32);
2056             tcg_gen_trunc_i64_tl(t1, t2);
2057             tcg_temp_free_i64(t2);
2058             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2059             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2060         }
2061         opn = "mult";
2062         break;
2063     case OPC_MULTU:
2064         {
2065             TCGv_i64 t2 = tcg_temp_new_i64();
2066             TCGv_i64 t3 = tcg_temp_new_i64();
2067
2068             tcg_gen_ext32u_tl(t0, t0);
2069             tcg_gen_ext32u_tl(t1, t1);
2070             tcg_gen_extu_tl_i64(t2, t0);
2071             tcg_gen_extu_tl_i64(t3, t1);
2072             tcg_gen_mul_i64(t2, t2, t3);
2073             tcg_temp_free_i64(t3);
2074             tcg_gen_trunc_i64_tl(t0, t2);
2075             tcg_gen_shri_i64(t2, t2, 32);
2076             tcg_gen_trunc_i64_tl(t1, t2);
2077             tcg_temp_free_i64(t2);
2078             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2079             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2080         }
2081         opn = "multu";
2082         break;
2083 #if defined(TARGET_MIPS64)
2084     case OPC_DDIV:
2085         {
2086             int l1 = gen_new_label();
2087             int l2 = gen_new_label();
2088
2089             tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2090             tcg_gen_brcondi_tl(TCG_COND_NE, t0, -1LL << 63, l2);
2091             tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1LL, l2);
2092             tcg_gen_mov_tl(cpu_LO[0], t0);
2093             tcg_gen_movi_tl(cpu_HI[0], 0);
2094             tcg_gen_br(l1);
2095             gen_set_label(l2);
2096             tcg_gen_div_i64(cpu_LO[0], t0, t1);
2097             tcg_gen_rem_i64(cpu_HI[0], t0, t1);
2098             gen_set_label(l1);
2099         }
2100         opn = "ddiv";
2101         break;
2102     case OPC_DDIVU:
2103         {
2104             int l1 = gen_new_label();
2105
2106             tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2107             tcg_gen_divu_i64(cpu_LO[0], t0, t1);
2108             tcg_gen_remu_i64(cpu_HI[0], t0, t1);
2109             gen_set_label(l1);
2110         }
2111         opn = "ddivu";
2112         break;
2113     case OPC_DMULT:
2114         gen_helper_dmult(t0, t1);
2115         opn = "dmult";
2116         break;
2117     case OPC_DMULTU:
2118         gen_helper_dmultu(t0, t1);
2119         opn = "dmultu";
2120         break;
2121 #endif
2122     case OPC_MADD:
2123         {
2124             TCGv_i64 t2 = tcg_temp_new_i64();
2125             TCGv_i64 t3 = tcg_temp_new_i64();
2126
2127             tcg_gen_ext_tl_i64(t2, t0);
2128             tcg_gen_ext_tl_i64(t3, t1);
2129             tcg_gen_mul_i64(t2, t2, t3);
2130             tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2131             tcg_gen_add_i64(t2, t2, t3);
2132             tcg_temp_free_i64(t3);
2133             tcg_gen_trunc_i64_tl(t0, t2);
2134             tcg_gen_shri_i64(t2, t2, 32);
2135             tcg_gen_trunc_i64_tl(t1, t2);
2136             tcg_temp_free_i64(t2);
2137             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2138             tcg_gen_ext32s_tl(cpu_LO[1], t1);
2139         }
2140         opn = "madd";
2141         break;
2142     case OPC_MADDU:
2143        {
2144             TCGv_i64 t2 = tcg_temp_new_i64();
2145             TCGv_i64 t3 = tcg_temp_new_i64();
2146
2147             tcg_gen_ext32u_tl(t0, t0);
2148             tcg_gen_ext32u_tl(t1, t1);
2149             tcg_gen_extu_tl_i64(t2, t0);
2150             tcg_gen_extu_tl_i64(t3, t1);
2151             tcg_gen_mul_i64(t2, t2, t3);
2152             tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2153             tcg_gen_add_i64(t2, t2, t3);
2154             tcg_temp_free_i64(t3);
2155             tcg_gen_trunc_i64_tl(t0, t2);
2156             tcg_gen_shri_i64(t2, t2, 32);
2157             tcg_gen_trunc_i64_tl(t1, t2);
2158             tcg_temp_free_i64(t2);
2159             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2160             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2161         }
2162         opn = "maddu";
2163         break;
2164     case OPC_MSUB:
2165         {
2166             TCGv_i64 t2 = tcg_temp_new_i64();
2167             TCGv_i64 t3 = tcg_temp_new_i64();
2168
2169             tcg_gen_ext_tl_i64(t2, t0);
2170             tcg_gen_ext_tl_i64(t3, t1);
2171             tcg_gen_mul_i64(t2, t2, t3);
2172             tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2173             tcg_gen_sub_i64(t2, t2, t3);
2174             tcg_temp_free_i64(t3);
2175             tcg_gen_trunc_i64_tl(t0, t2);
2176             tcg_gen_shri_i64(t2, t2, 32);
2177             tcg_gen_trunc_i64_tl(t1, t2);
2178             tcg_temp_free_i64(t2);
2179             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2180             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2181         }
2182         opn = "msub";
2183         break;
2184     case OPC_MSUBU:
2185         {
2186             TCGv_i64 t2 = tcg_temp_new_i64();
2187             TCGv_i64 t3 = tcg_temp_new_i64();
2188
2189             tcg_gen_ext32u_tl(t0, t0);
2190             tcg_gen_ext32u_tl(t1, t1);
2191             tcg_gen_extu_tl_i64(t2, t0);
2192             tcg_gen_extu_tl_i64(t3, t1);
2193             tcg_gen_mul_i64(t2, t2, t3);
2194             tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2195             tcg_gen_sub_i64(t2, t2, t3);
2196             tcg_temp_free_i64(t3);
2197             tcg_gen_trunc_i64_tl(t0, t2);
2198             tcg_gen_shri_i64(t2, t2, 32);
2199             tcg_gen_trunc_i64_tl(t1, t2);
2200             tcg_temp_free_i64(t2);
2201             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2202             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2203         }
2204         opn = "msubu";
2205         break;
2206     default:
2207         MIPS_INVAL(opn);
2208         generate_exception(ctx, EXCP_RI);
2209         goto out;
2210     }
2211     MIPS_DEBUG("%s %s %s", opn, regnames[rs], regnames[rt]);
2212  out:
2213     tcg_temp_free(t0);
2214     tcg_temp_free(t1);
2215 }
2216
2217 static void gen_mul_vr54xx (DisasContext *ctx, uint32_t opc,
2218                             int rd, int rs, int rt)
2219 {
2220     const char *opn = "mul vr54xx";
2221     TCGv t0 = tcg_temp_new();
2222     TCGv t1 = tcg_temp_new();
2223
2224     gen_load_gpr(t0, rs);
2225     gen_load_gpr(t1, rt);
2226
2227     switch (opc) {
2228     case OPC_VR54XX_MULS:
2229         gen_helper_muls(t0, t0, t1);
2230         opn = "muls";
2231         break;
2232     case OPC_VR54XX_MULSU:
2233         gen_helper_mulsu(t0, t0, t1);
2234         opn = "mulsu";
2235         break;
2236     case OPC_VR54XX_MACC:
2237         gen_helper_macc(t0, t0, t1);
2238         opn = "macc";
2239         break;
2240     case OPC_VR54XX_MACCU:
2241         gen_helper_maccu(t0, t0, t1);
2242         opn = "maccu";
2243         break;
2244     case OPC_VR54XX_MSAC:
2245         gen_helper_msac(t0, t0, t1);
2246         opn = "msac";
2247         break;
2248     case OPC_VR54XX_MSACU:
2249         gen_helper_msacu(t0, t0, t1);
2250         opn = "msacu";
2251         break;
2252     case OPC_VR54XX_MULHI:
2253         gen_helper_mulhi(t0, t0, t1);
2254         opn = "mulhi";
2255         break;
2256     case OPC_VR54XX_MULHIU:
2257         gen_helper_mulhiu(t0, t0, t1);
2258         opn = "mulhiu";
2259         break;
2260     case OPC_VR54XX_MULSHI:
2261         gen_helper_mulshi(t0, t0, t1);
2262         opn = "mulshi";
2263         break;
2264     case OPC_VR54XX_MULSHIU:
2265         gen_helper_mulshiu(t0, t0, t1);
2266         opn = "mulshiu";
2267         break;
2268     case OPC_VR54XX_MACCHI:
2269         gen_helper_macchi(t0, t0, t1);
2270         opn = "macchi";
2271         break;
2272     case OPC_VR54XX_MACCHIU:
2273         gen_helper_macchiu(t0, t0, t1);
2274         opn = "macchiu";
2275         break;
2276     case OPC_VR54XX_MSACHI:
2277         gen_helper_msachi(t0, t0, t1);
2278         opn = "msachi";
2279         break;
2280     case OPC_VR54XX_MSACHIU:
2281         gen_helper_msachiu(t0, t0, t1);
2282         opn = "msachiu";
2283         break;
2284     default:
2285         MIPS_INVAL("mul vr54xx");
2286         generate_exception(ctx, EXCP_RI);
2287         goto out;
2288     }
2289     gen_store_gpr(t0, rd);
2290     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
2291
2292  out:
2293     tcg_temp_free(t0);
2294     tcg_temp_free(t1);
2295 }
2296
2297 static void gen_cl (DisasContext *ctx, uint32_t opc,
2298                     int rd, int rs)
2299 {
2300     const char *opn = "CLx";
2301     TCGv t0;
2302
2303     if (rd == 0) {
2304         /* Treat as NOP. */
2305         MIPS_DEBUG("NOP");
2306         return;
2307     }
2308     t0 = tcg_temp_new();
2309     gen_load_gpr(t0, rs);
2310     switch (opc) {
2311     case OPC_CLO:
2312         gen_helper_clo(cpu_gpr[rd], t0);
2313         opn = "clo";
2314         break;
2315     case OPC_CLZ:
2316         gen_helper_clz(cpu_gpr[rd], t0);
2317         opn = "clz";
2318         break;
2319 #if defined(TARGET_MIPS64)
2320     case OPC_DCLO:
2321         gen_helper_dclo(cpu_gpr[rd], t0);
2322         opn = "dclo";
2323         break;
2324     case OPC_DCLZ:
2325         gen_helper_dclz(cpu_gpr[rd], t0);
2326         opn = "dclz";
2327         break;
2328 #endif
2329     }
2330     MIPS_DEBUG("%s %s, %s", opn, regnames[rd], regnames[rs]);
2331     tcg_temp_free(t0);
2332 }
2333
2334 /* Traps */
2335 static void gen_trap (DisasContext *ctx, uint32_t opc,
2336                       int rs, int rt, int16_t imm)
2337 {
2338     int cond;
2339     TCGv t0 = tcg_temp_new();
2340     TCGv t1 = tcg_temp_new();
2341
2342     cond = 0;
2343     /* Load needed operands */
2344     switch (opc) {
2345     case OPC_TEQ:
2346     case OPC_TGE:
2347     case OPC_TGEU:
2348     case OPC_TLT:
2349     case OPC_TLTU:
2350     case OPC_TNE:
2351         /* Compare two registers */
2352         if (rs != rt) {
2353             gen_load_gpr(t0, rs);
2354             gen_load_gpr(t1, rt);
2355             cond = 1;
2356         }
2357         break;
2358     case OPC_TEQI:
2359     case OPC_TGEI:
2360     case OPC_TGEIU:
2361     case OPC_TLTI:
2362     case OPC_TLTIU:
2363     case OPC_TNEI:
2364         /* Compare register to immediate */
2365         if (rs != 0 || imm != 0) {
2366             gen_load_gpr(t0, rs);
2367             tcg_gen_movi_tl(t1, (int32_t)imm);
2368             cond = 1;
2369         }
2370         break;
2371     }
2372     if (cond == 0) {
2373         switch (opc) {
2374         case OPC_TEQ:   /* rs == rs */
2375         case OPC_TEQI:  /* r0 == 0  */
2376         case OPC_TGE:   /* rs >= rs */
2377         case OPC_TGEI:  /* r0 >= 0  */
2378         case OPC_TGEU:  /* rs >= rs unsigned */
2379         case OPC_TGEIU: /* r0 >= 0  unsigned */
2380             /* Always trap */
2381             generate_exception(ctx, EXCP_TRAP);
2382             break;
2383         case OPC_TLT:   /* rs < rs           */
2384         case OPC_TLTI:  /* r0 < 0            */
2385         case OPC_TLTU:  /* rs < rs unsigned  */
2386         case OPC_TLTIU: /* r0 < 0  unsigned  */
2387         case OPC_TNE:   /* rs != rs          */
2388         case OPC_TNEI:  /* r0 != 0           */
2389             /* Never trap: treat as NOP. */
2390             break;
2391         }
2392     } else {
2393         int l1 = gen_new_label();
2394
2395         switch (opc) {
2396         case OPC_TEQ:
2397         case OPC_TEQI:
2398             tcg_gen_brcond_tl(TCG_COND_NE, t0, t1, l1);
2399             break;
2400         case OPC_TGE:
2401         case OPC_TGEI:
2402             tcg_gen_brcond_tl(TCG_COND_LT, t0, t1, l1);
2403             break;
2404         case OPC_TGEU:
2405         case OPC_TGEIU:
2406             tcg_gen_brcond_tl(TCG_COND_LTU, t0, t1, l1);
2407             break;
2408         case OPC_TLT:
2409         case OPC_TLTI:
2410             tcg_gen_brcond_tl(TCG_COND_GE, t0, t1, l1);
2411             break;
2412         case OPC_TLTU:
2413         case OPC_TLTIU:
2414             tcg_gen_brcond_tl(TCG_COND_GEU, t0, t1, l1);
2415             break;
2416         case OPC_TNE:
2417         case OPC_TNEI:
2418             tcg_gen_brcond_tl(TCG_COND_EQ, t0, t1, l1);
2419             break;
2420         }
2421         generate_exception(ctx, EXCP_TRAP);
2422         gen_set_label(l1);
2423     }
2424     tcg_temp_free(t0);
2425     tcg_temp_free(t1);
2426 }
2427
2428 static inline void gen_goto_tb(DisasContext *ctx, int n, target_ulong dest)
2429 {
2430     TranslationBlock *tb;
2431     tb = ctx->tb;
2432     if ((tb->pc & TARGET_PAGE_MASK) == (dest & TARGET_PAGE_MASK)) {
2433         tcg_gen_goto_tb(n);
2434         gen_save_pc(dest);
2435         tcg_gen_exit_tb((long)tb + n);
2436     } else {
2437         gen_save_pc(dest);
2438         tcg_gen_exit_tb(0);
2439     }
2440 }
2441
2442 /* Branches (before delay slot) */
2443 static void gen_compute_branch (DisasContext *ctx, uint32_t opc,
2444                                 int rs, int rt, int32_t offset)
2445 {
2446     target_ulong btgt = -1;
2447     int blink = 0;
2448     int bcond_compute = 0;
2449     TCGv t0 = tcg_temp_new();
2450     TCGv t1 = tcg_temp_new();
2451
2452     if (ctx->hflags & MIPS_HFLAG_BMASK) {
2453 #ifdef MIPS_DEBUG_DISAS
2454         LOG_DISAS("Branch in delay slot at PC 0x" TARGET_FMT_lx "\n", ctx->pc);
2455 #endif
2456         generate_exception(ctx, EXCP_RI);
2457         goto out;
2458     }
2459
2460     /* Load needed operands */
2461     switch (opc) {
2462     case OPC_BEQ:
2463     case OPC_BEQL:
2464     case OPC_BNE:
2465     case OPC_BNEL:
2466         /* Compare two registers */
2467         if (rs != rt) {
2468             gen_load_gpr(t0, rs);
2469             gen_load_gpr(t1, rt);
2470             bcond_compute = 1;
2471         }
2472         btgt = ctx->pc + 4 + offset;
2473         break;
2474     case OPC_BGEZ:
2475     case OPC_BGEZAL:
2476     case OPC_BGEZALL:
2477     case OPC_BGEZL:
2478     case OPC_BGTZ:
2479     case OPC_BGTZL:
2480     case OPC_BLEZ:
2481     case OPC_BLEZL:
2482     case OPC_BLTZ:
2483     case OPC_BLTZAL:
2484     case OPC_BLTZALL:
2485     case OPC_BLTZL:
2486         /* Compare to zero */
2487         if (rs != 0) {
2488             gen_load_gpr(t0, rs);
2489             bcond_compute = 1;
2490         }
2491         btgt = ctx->pc + 4 + offset;
2492         break;
2493     case OPC_J:
2494     case OPC_JAL:
2495         /* Jump to immediate */
2496         btgt = ((ctx->pc + 4) & (int32_t)0xF0000000) | (uint32_t)offset;
2497         break;
2498     case OPC_JR:
2499     case OPC_JALR:
2500         /* Jump to register */
2501         if (offset != 0 && offset != 16) {
2502             /* Hint = 0 is JR/JALR, hint 16 is JR.HB/JALR.HB, the
2503                others are reserved. */
2504             MIPS_INVAL("jump hint");
2505             generate_exception(ctx, EXCP_RI);
2506             goto out;
2507         }
2508         gen_load_gpr(btarget, rs);
2509         break;
2510     default:
2511         MIPS_INVAL("branch/jump");
2512         generate_exception(ctx, EXCP_RI);
2513         goto out;
2514     }
2515     if (bcond_compute == 0) {
2516         /* No condition to be computed */
2517         switch (opc) {
2518         case OPC_BEQ:     /* rx == rx        */
2519         case OPC_BEQL:    /* rx == rx likely */
2520         case OPC_BGEZ:    /* 0 >= 0          */
2521         case OPC_BGEZL:   /* 0 >= 0 likely   */
2522         case OPC_BLEZ:    /* 0 <= 0          */
2523         case OPC_BLEZL:   /* 0 <= 0 likely   */
2524             /* Always take */
2525             ctx->hflags |= MIPS_HFLAG_B;
2526             MIPS_DEBUG("balways");
2527             break;
2528         case OPC_BGEZAL:  /* 0 >= 0          */
2529         case OPC_BGEZALL: /* 0 >= 0 likely   */
2530             /* Always take and link */
2531             blink = 31;
2532             ctx->hflags |= MIPS_HFLAG_B;
2533             MIPS_DEBUG("balways and link");
2534             break;
2535         case OPC_BNE:     /* rx != rx        */
2536         case OPC_BGTZ:    /* 0 > 0           */
2537         case OPC_BLTZ:    /* 0 < 0           */
2538             /* Treat as NOP. */
2539             MIPS_DEBUG("bnever (NOP)");
2540             goto out;
2541         case OPC_BLTZAL:  /* 0 < 0           */
2542             tcg_gen_movi_tl(cpu_gpr[31], ctx->pc + 8);
2543             MIPS_DEBUG("bnever and link");
2544             goto out;
2545         case OPC_BLTZALL: /* 0 < 0 likely */
2546             tcg_gen_movi_tl(cpu_gpr[31], ctx->pc + 8);
2547             /* Skip the instruction in the delay slot */
2548             MIPS_DEBUG("bnever, link and skip");
2549             ctx->pc += 4;
2550             goto out;
2551         case OPC_BNEL:    /* rx != rx likely */
2552         case OPC_BGTZL:   /* 0 > 0 likely */
2553         case OPC_BLTZL:   /* 0 < 0 likely */
2554             /* Skip the instruction in the delay slot */
2555             MIPS_DEBUG("bnever and skip");
2556             ctx->pc += 4;
2557             goto out;
2558         case OPC_J:
2559             ctx->hflags |= MIPS_HFLAG_B;
2560             MIPS_DEBUG("j " TARGET_FMT_lx, btgt);
2561             break;
2562         case OPC_JAL:
2563             blink = 31;
2564             ctx->hflags |= MIPS_HFLAG_B;
2565             MIPS_DEBUG("jal " TARGET_FMT_lx, btgt);
2566             break;
2567         case OPC_JR:
2568             ctx->hflags |= MIPS_HFLAG_BR;
2569             MIPS_DEBUG("jr %s", regnames[rs]);
2570             break;
2571         case OPC_JALR:
2572             blink = rt;
2573             ctx->hflags |= MIPS_HFLAG_BR;
2574             MIPS_DEBUG("jalr %s, %s", regnames[rt], regnames[rs]);
2575             break;
2576         default:
2577             MIPS_INVAL("branch/jump");
2578             generate_exception(ctx, EXCP_RI);
2579             goto out;
2580         }
2581     } else {
2582         switch (opc) {
2583         case OPC_BEQ:
2584             gen_op_eq(bcond, t0, t1);
2585             MIPS_DEBUG("beq %s, %s, " TARGET_FMT_lx,
2586                        regnames[rs], regnames[rt], btgt);
2587             goto not_likely;
2588         case OPC_BEQL:
2589             gen_op_eq(bcond, t0, t1);
2590             MIPS_DEBUG("beql %s, %s, " TARGET_FMT_lx,
2591                        regnames[rs], regnames[rt], btgt);
2592             goto likely;
2593         case OPC_BNE:
2594             gen_op_ne(bcond, t0, t1);
2595             MIPS_DEBUG("bne %s, %s, " TARGET_FMT_lx,
2596                        regnames[rs], regnames[rt], btgt);
2597             goto not_likely;
2598         case OPC_BNEL:
2599             gen_op_ne(bcond, t0, t1);
2600             MIPS_DEBUG("bnel %s, %s, " TARGET_FMT_lx,
2601                        regnames[rs], regnames[rt], btgt);
2602             goto likely;
2603         case OPC_BGEZ:
2604             gen_op_gez(bcond, t0);
2605             MIPS_DEBUG("bgez %s, " TARGET_FMT_lx, regnames[rs], btgt);
2606             goto not_likely;
2607         case OPC_BGEZL:
2608             gen_op_gez(bcond, t0);
2609             MIPS_DEBUG("bgezl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2610             goto likely;
2611         case OPC_BGEZAL:
2612             gen_op_gez(bcond, t0);
2613             MIPS_DEBUG("bgezal %s, " TARGET_FMT_lx, regnames[rs], btgt);
2614             blink = 31;
2615             goto not_likely;
2616         case OPC_BGEZALL:
2617             gen_op_gez(bcond, t0);
2618             blink = 31;
2619             MIPS_DEBUG("bgezall %s, " TARGET_FMT_lx, regnames[rs], btgt);
2620             goto likely;
2621         case OPC_BGTZ:
2622             gen_op_gtz(bcond, t0);
2623             MIPS_DEBUG("bgtz %s, " TARGET_FMT_lx, regnames[rs], btgt);
2624             goto not_likely;
2625         case OPC_BGTZL:
2626             gen_op_gtz(bcond, t0);
2627             MIPS_DEBUG("bgtzl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2628             goto likely;
2629         case OPC_BLEZ:
2630             gen_op_lez(bcond, t0);
2631             MIPS_DEBUG("blez %s, " TARGET_FMT_lx, regnames[rs], btgt);
2632             goto not_likely;
2633         case OPC_BLEZL:
2634             gen_op_lez(bcond, t0);
2635             MIPS_DEBUG("blezl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2636             goto likely;
2637         case OPC_BLTZ:
2638             gen_op_ltz(bcond, t0);
2639             MIPS_DEBUG("bltz %s, " TARGET_FMT_lx, regnames[rs], btgt);
2640             goto not_likely;
2641         case OPC_BLTZL:
2642             gen_op_ltz(bcond, t0);
2643             MIPS_DEBUG("bltzl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2644             goto likely;
2645         case OPC_BLTZAL:
2646             gen_op_ltz(bcond, t0);
2647             blink = 31;
2648             MIPS_DEBUG("bltzal %s, " TARGET_FMT_lx, regnames[rs], btgt);
2649         not_likely:
2650             ctx->hflags |= MIPS_HFLAG_BC;
2651             break;
2652         case OPC_BLTZALL:
2653             gen_op_ltz(bcond, t0);
2654             blink = 31;
2655             MIPS_DEBUG("bltzall %s, " TARGET_FMT_lx, regnames[rs], btgt);
2656         likely:
2657             ctx->hflags |= MIPS_HFLAG_BL;
2658             break;
2659         default:
2660             MIPS_INVAL("conditional branch/jump");
2661             generate_exception(ctx, EXCP_RI);
2662             goto out;
2663         }
2664     }
2665     MIPS_DEBUG("enter ds: link %d cond %02x target " TARGET_FMT_lx,
2666                blink, ctx->hflags, btgt);
2667
2668     ctx->btarget = btgt;
2669     if (blink > 0) {
2670         tcg_gen_movi_tl(cpu_gpr[blink], ctx->pc + 8);
2671     }
2672
2673  out:
2674     tcg_temp_free(t0);
2675     tcg_temp_free(t1);
2676 }
2677
2678 /* special3 bitfield operations */
2679 static void gen_bitops (DisasContext *ctx, uint32_t opc, int rt,
2680                         int rs, int lsb, int msb)
2681 {
2682     TCGv t0 = tcg_temp_new();
2683     TCGv t1 = tcg_temp_new();
2684     target_ulong mask;
2685
2686     gen_load_gpr(t1, rs);
2687     switch (opc) {
2688     case OPC_EXT:
2689         if (lsb + msb > 31)
2690             goto fail;
2691         tcg_gen_shri_tl(t0, t1, lsb);
2692         if (msb != 31) {
2693             tcg_gen_andi_tl(t0, t0, (1 << (msb + 1)) - 1);
2694         } else {
2695             tcg_gen_ext32s_tl(t0, t0);
2696         }
2697         break;
2698 #if defined(TARGET_MIPS64)
2699     case OPC_DEXTM:
2700         tcg_gen_shri_tl(t0, t1, lsb);
2701         if (msb != 31) {
2702             tcg_gen_andi_tl(t0, t0, (1ULL << (msb + 1 + 32)) - 1);
2703         }
2704         break;
2705     case OPC_DEXTU:
2706         tcg_gen_shri_tl(t0, t1, lsb + 32);
2707         tcg_gen_andi_tl(t0, t0, (1ULL << (msb + 1)) - 1);
2708         break;
2709     case OPC_DEXT:
2710         tcg_gen_shri_tl(t0, t1, lsb);
2711         tcg_gen_andi_tl(t0, t0, (1ULL << (msb + 1)) - 1);
2712         break;
2713 #endif
2714     case OPC_INS:
2715         if (lsb > msb)
2716             goto fail;
2717         mask = ((msb - lsb + 1 < 32) ? ((1 << (msb - lsb + 1)) - 1) : ~0) << lsb;
2718         gen_load_gpr(t0, rt);
2719         tcg_gen_andi_tl(t0, t0, ~mask);
2720         tcg_gen_shli_tl(t1, t1, lsb);
2721         tcg_gen_andi_tl(t1, t1, mask);
2722         tcg_gen_or_tl(t0, t0, t1);
2723         tcg_gen_ext32s_tl(t0, t0);
2724         break;
2725 #if defined(TARGET_MIPS64)
2726     case OPC_DINSM:
2727         if (lsb > msb)
2728             goto fail;
2729         mask = ((msb - lsb + 1 + 32 < 64) ? ((1ULL << (msb - lsb + 1 + 32)) - 1) : ~0ULL) << lsb;
2730         gen_load_gpr(t0, rt);
2731         tcg_gen_andi_tl(t0, t0, ~mask);
2732         tcg_gen_shli_tl(t1, t1, lsb);
2733         tcg_gen_andi_tl(t1, t1, mask);
2734         tcg_gen_or_tl(t0, t0, t1);
2735         break;
2736     case OPC_DINSU:
2737         if (lsb > msb)
2738             goto fail;
2739         mask = ((1ULL << (msb - lsb + 1)) - 1) << lsb;
2740         gen_load_gpr(t0, rt);
2741         tcg_gen_andi_tl(t0, t0, ~mask);
2742         tcg_gen_shli_tl(t1, t1, lsb + 32);
2743         tcg_gen_andi_tl(t1, t1, mask);
2744         tcg_gen_or_tl(t0, t0, t1);
2745         break;
2746     case OPC_DINS:
2747         if (lsb > msb)
2748             goto fail;
2749         gen_load_gpr(t0, rt);
2750         mask = ((1ULL << (msb - lsb + 1)) - 1) << lsb;
2751         gen_load_gpr(t0, rt);
2752         tcg_gen_andi_tl(t0, t0, ~mask);
2753         tcg_gen_shli_tl(t1, t1, lsb);
2754         tcg_gen_andi_tl(t1, t1, mask);
2755         tcg_gen_or_tl(t0, t0, t1);
2756         break;
2757 #endif
2758     default:
2759 fail:
2760         MIPS_INVAL("bitops");
2761         generate_exception(ctx, EXCP_RI);
2762         tcg_temp_free(t0);
2763         tcg_temp_free(t1);
2764         return;
2765     }
2766     gen_store_gpr(t0, rt);
2767     tcg_temp_free(t0);
2768     tcg_temp_free(t1);
2769 }
2770
2771 static void gen_bshfl (DisasContext *ctx, uint32_t op2, int rt, int rd)
2772 {
2773     TCGv t0;
2774
2775     if (rd == 0) {
2776         /* If no destination, treat it as a NOP. */
2777         MIPS_DEBUG("NOP");
2778         return;
2779     }
2780
2781     t0 = tcg_temp_new();
2782     gen_load_gpr(t0, rt);
2783     switch (op2) {
2784     case OPC_WSBH:
2785         {
2786             TCGv t1 = tcg_temp_new();
2787
2788             tcg_gen_shri_tl(t1, t0, 8);
2789             tcg_gen_andi_tl(t1, t1, 0x00FF00FF);
2790             tcg_gen_shli_tl(t0, t0, 8);
2791             tcg_gen_andi_tl(t0, t0, ~0x00FF00FF);
2792             tcg_gen_or_tl(t0, t0, t1);
2793             tcg_temp_free(t1);
2794             tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
2795         }
2796         break;
2797     case OPC_SEB:
2798         tcg_gen_ext8s_tl(cpu_gpr[rd], t0);
2799         break;
2800     case OPC_SEH:
2801         tcg_gen_ext16s_tl(cpu_gpr[rd], t0);
2802         break;
2803 #if defined(TARGET_MIPS64)
2804     case OPC_DSBH:
2805         {
2806             TCGv t1 = tcg_temp_new();
2807
2808             tcg_gen_shri_tl(t1, t0, 8);
2809             tcg_gen_andi_tl(t1, t1, 0x00FF00FF00FF00FFULL);
2810             tcg_gen_shli_tl(t0, t0, 8);
2811             tcg_gen_andi_tl(t0, t0, ~0x00FF00FF00FF00FFULL);
2812             tcg_gen_or_tl(cpu_gpr[rd], t0, t1);
2813             tcg_temp_free(t1);
2814         }
2815         break;
2816     case OPC_DSHD:
2817         {
2818             TCGv t1 = tcg_temp_new();
2819
2820             tcg_gen_shri_tl(t1, t0, 16);
2821             tcg_gen_andi_tl(t1, t1, 0x0000FFFF0000FFFFULL);
2822             tcg_gen_shli_tl(t0, t0, 16);
2823             tcg_gen_andi_tl(t0, t0, ~0x0000FFFF0000FFFFULL);
2824             tcg_gen_or_tl(t0, t0, t1);
2825             tcg_gen_shri_tl(t1, t0, 32);
2826             tcg_gen_shli_tl(t0, t0, 32);
2827             tcg_gen_or_tl(cpu_gpr[rd], t0, t1);
2828             tcg_temp_free(t1);
2829         }
2830         break;
2831 #endif
2832     default:
2833         MIPS_INVAL("bsfhl");
2834         generate_exception(ctx, EXCP_RI);
2835         tcg_temp_free(t0);
2836         return;
2837     }
2838     tcg_temp_free(t0);
2839 }
2840
2841 #ifndef CONFIG_USER_ONLY
2842 /* CP0 (MMU and control) */
2843 static inline void gen_mfc0_load32 (TCGv t, target_ulong off)
2844 {
2845     TCGv_i32 r_tmp = tcg_temp_new_i32();
2846
2847     tcg_gen_ld_i32(r_tmp, cpu_env, off);
2848     tcg_gen_ext_i32_tl(t, r_tmp);
2849     tcg_temp_free_i32(r_tmp);
2850 }
2851
2852 static inline void gen_mfc0_load64 (TCGv t, target_ulong off)
2853 {
2854     tcg_gen_ld_tl(t, cpu_env, off);
2855     tcg_gen_ext32s_tl(t, t);
2856 }
2857
2858 static inline void gen_mtc0_store32 (TCGv t, target_ulong off)
2859 {
2860     TCGv_i32 r_tmp = tcg_temp_new_i32();
2861
2862     tcg_gen_trunc_tl_i32(r_tmp, t);
2863     tcg_gen_st_i32(r_tmp, cpu_env, off);
2864     tcg_temp_free_i32(r_tmp);
2865 }
2866
2867 static inline void gen_mtc0_store64 (TCGv t, target_ulong off)
2868 {
2869     tcg_gen_ext32s_tl(t, t);
2870     tcg_gen_st_tl(t, cpu_env, off);
2871 }
2872
2873 static void gen_mfc0 (CPUState *env, DisasContext *ctx, TCGv t0, int reg, int sel)
2874 {
2875     const char *rn = "invalid";
2876
2877     if (sel != 0)
2878         check_insn(env, ctx, ISA_MIPS32);
2879
2880     switch (reg) {
2881     case 0:
2882         switch (sel) {
2883         case 0:
2884             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Index));
2885             rn = "Index";
2886             break;
2887         case 1:
2888             check_insn(env, ctx, ASE_MT);
2889             gen_helper_mfc0_mvpcontrol(t0);
2890             rn = "MVPControl";
2891             break;
2892         case 2:
2893             check_insn(env, ctx, ASE_MT);
2894             gen_helper_mfc0_mvpconf0(t0);
2895             rn = "MVPConf0";
2896             break;
2897         case 3:
2898             check_insn(env, ctx, ASE_MT);
2899             gen_helper_mfc0_mvpconf1(t0);
2900             rn = "MVPConf1";
2901             break;
2902         default:
2903             goto die;
2904         }
2905         break;
2906     case 1:
2907         switch (sel) {
2908         case 0:
2909             gen_helper_mfc0_random(t0);
2910             rn = "Random";
2911             break;
2912         case 1:
2913             check_insn(env, ctx, ASE_MT);
2914             gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEControl));
2915             rn = "VPEControl";
2916             break;
2917         case 2:
2918             check_insn(env, ctx, ASE_MT);
2919             gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEConf0));
2920             rn = "VPEConf0";
2921             break;
2922         case 3:
2923             check_insn(env, ctx, ASE_MT);
2924             gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEConf1));
2925             rn = "VPEConf1";
2926             break;
2927         case 4:
2928             check_insn(env, ctx, ASE_MT);
2929             gen_mfc0_load64(t0, offsetof(CPUState, CP0_YQMask));
2930             rn = "YQMask";
2931             break;
2932         case 5:
2933             check_insn(env, ctx, ASE_MT);
2934             gen_mfc0_load64(t0, offsetof(CPUState, CP0_VPESchedule));
2935             rn = "VPESchedule";
2936             break;
2937         case 6:
2938             check_insn(env, ctx, ASE_MT);
2939             gen_mfc0_load64(t0, offsetof(CPUState, CP0_VPEScheFBack));
2940             rn = "VPEScheFBack";
2941             break;
2942         case 7:
2943             check_insn(env, ctx, ASE_MT);
2944             gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEOpt));
2945             rn = "VPEOpt";
2946             break;
2947         default:
2948             goto die;
2949         }
2950         break;
2951     case 2:
2952         switch (sel) {
2953         case 0:
2954             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryLo0));
2955             tcg_gen_ext32s_tl(t0, t0);
2956             rn = "EntryLo0";
2957             break;
2958         case 1:
2959             check_insn(env, ctx, ASE_MT);
2960             gen_helper_mfc0_tcstatus(t0);
2961             rn = "TCStatus";
2962             break;
2963         case 2:
2964             check_insn(env, ctx, ASE_MT);
2965             gen_helper_mfc0_tcbind(t0);
2966             rn = "TCBind";
2967             break;
2968         case 3:
2969             check_insn(env, ctx, ASE_MT);
2970             gen_helper_mfc0_tcrestart(t0);
2971             rn = "TCRestart";
2972             break;
2973         case 4:
2974             check_insn(env, ctx, ASE_MT);
2975             gen_helper_mfc0_tchalt(t0);
2976             rn = "TCHalt";
2977             break;
2978         case 5:
2979             check_insn(env, ctx, ASE_MT);
2980             gen_helper_mfc0_tccontext(t0);
2981             rn = "TCContext";
2982             break;
2983         case 6:
2984             check_insn(env, ctx, ASE_MT);
2985             gen_helper_mfc0_tcschedule(t0);
2986             rn = "TCSchedule";
2987             break;
2988         case 7:
2989             check_insn(env, ctx, ASE_MT);
2990             gen_helper_mfc0_tcschefback(t0);
2991             rn = "TCScheFBack";
2992             break;
2993         default:
2994             goto die;
2995         }
2996         break;
2997     case 3:
2998         switch (sel) {
2999         case 0:
3000             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryLo1));
3001             tcg_gen_ext32s_tl(t0, t0);
3002             rn = "EntryLo1";
3003             break;
3004         default:
3005             goto die;
3006         }
3007         break;
3008     case 4:
3009         switch (sel) {
3010         case 0:
3011             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_Context));
3012             tcg_gen_ext32s_tl(t0, t0);
3013             rn = "Context";
3014             break;
3015         case 1:
3016 //            gen_helper_mfc0_contextconfig(t0); /* SmartMIPS ASE */
3017             rn = "ContextConfig";
3018 //            break;
3019         default:
3020             goto die;
3021         }
3022         break;
3023     case 5:
3024         switch (sel) {
3025         case 0:
3026             gen_mfc0_load32(t0, offsetof(CPUState, CP0_PageMask));
3027             rn = "PageMask";
3028             break;
3029         case 1:
3030             check_insn(env, ctx, ISA_MIPS32R2);
3031             gen_mfc0_load32(t0, offsetof(CPUState, CP0_PageGrain));
3032             rn = "PageGrain";
3033             break;
3034         default:
3035             goto die;
3036         }
3037         break;
3038     case 6:
3039         switch (sel) {
3040         case 0:
3041             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Wired));
3042             rn = "Wired";
3043             break;
3044         case 1:
3045             check_insn(env, ctx, ISA_MIPS32R2);
3046             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf0));
3047             rn = "SRSConf0";
3048             break;
3049         case 2:
3050             check_insn(env, ctx, ISA_MIPS32R2);
3051             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf1));
3052             rn = "SRSConf1";
3053             break;
3054         case 3:
3055             check_insn(env, ctx, ISA_MIPS32R2);
3056             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf2));
3057             rn = "SRSConf2";
3058             break;
3059         case 4:
3060             check_insn(env, ctx, ISA_MIPS32R2);
3061             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf3));
3062             rn = "SRSConf3";
3063             break;
3064         case 5:
3065             check_insn(env, ctx, ISA_MIPS32R2);
3066             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf4));
3067             rn = "SRSConf4";
3068             break;
3069         default:
3070             goto die;
3071         }
3072         break;
3073     case 7:
3074         switch (sel) {
3075         case 0:
3076             check_insn(env, ctx, ISA_MIPS32R2);
3077             gen_mfc0_load32(t0, offsetof(CPUState, CP0_HWREna));
3078             rn = "HWREna";
3079             break;
3080         default:
3081             goto die;
3082         }
3083         break;
3084     case 8:
3085         switch (sel) {
3086         case 0:
3087             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_BadVAddr));
3088             tcg_gen_ext32s_tl(t0, t0);
3089             rn = "BadVAddr";
3090             break;
3091         default:
3092             goto die;
3093        }
3094         break;
3095     case 9:
3096         switch (sel) {
3097         case 0:
3098             /* Mark as an IO operation because we read the time.  */
3099             if (use_icount)
3100                 gen_io_start();
3101             gen_helper_mfc0_count(t0);
3102             if (use_icount) {
3103                 gen_io_end();
3104                 ctx->bstate = BS_STOP;
3105             }
3106             rn = "Count";
3107             break;
3108         /* 6,7 are implementation dependent */
3109         default:
3110             goto die;
3111         }
3112         break;
3113     case 10:
3114         switch (sel) {
3115         case 0:
3116             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryHi));
3117             tcg_gen_ext32s_tl(t0, t0);
3118             rn = "EntryHi";
3119             break;
3120         default:
3121             goto die;
3122         }
3123         break;
3124     case 11:
3125         switch (sel) {
3126         case 0:
3127             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Compare));
3128             rn = "Compare";
3129             break;
3130         /* 6,7 are implementation dependent */
3131         default:
3132             goto die;
3133         }
3134         break;
3135     case 12:
3136         switch (sel) {
3137         case 0:
3138             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Status));
3139             rn = "Status";
3140             break;
3141         case 1:
3142             check_insn(env, ctx, ISA_MIPS32R2);
3143             gen_mfc0_load32(t0, offsetof(CPUState, CP0_IntCtl));
3144             rn = "IntCtl";
3145             break;
3146         case 2:
3147             check_insn(env, ctx, ISA_MIPS32R2);
3148             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSCtl));
3149             rn = "SRSCtl";
3150             break;
3151         case 3:
3152             check_insn(env, ctx, ISA_MIPS32R2);
3153             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSMap));
3154             rn = "SRSMap";
3155             break;
3156         default:
3157             goto die;
3158        }
3159         break;
3160     case 13:
3161         switch (sel) {
3162         case 0:
3163             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Cause));
3164             rn = "Cause";
3165             break;
3166         default:
3167             goto die;
3168        }
3169         break;
3170     case 14:
3171         switch (sel) {
3172         case 0:
3173             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EPC));
3174             tcg_gen_ext32s_tl(t0, t0);
3175             rn = "EPC";
3176             break;
3177         default:
3178             goto die;
3179         }
3180         break;
3181     case 15:
3182         switch (sel) {
3183         case 0:
3184             gen_mfc0_load32(t0, offsetof(CPUState, CP0_PRid));
3185             rn = "PRid";
3186             break;
3187         case 1:
3188             check_insn(env, ctx, ISA_MIPS32R2);
3189             gen_mfc0_load32(t0, offsetof(CPUState, CP0_EBase));
3190             rn = "EBase";
3191             break;
3192         default:
3193             goto die;
3194        }
3195         break;
3196     case 16:
3197         switch (sel) {
3198         case 0:
3199             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config0));
3200             rn = "Config";
3201             break;
3202         case 1:
3203             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config1));
3204             rn = "Config1";
3205             break;
3206         case 2:
3207             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config2));
3208             rn = "Config2";
3209             break;
3210         case 3:
3211             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config3));
3212             rn = "Config3";
3213             break;
3214         /* 4,5 are reserved */
3215         /* 6,7 are implementation dependent */
3216         case 6:
3217             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config6));
3218             rn = "Config6";
3219             break;
3220         case 7:
3221             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config7));
3222             rn = "Config7";
3223             break;
3224         default:
3225             goto die;
3226         }
3227         break;
3228     case 17:
3229         switch (sel) {
3230         case 0:
3231             gen_helper_mfc0_lladdr(t0);
3232             rn = "LLAddr";
3233             break;
3234         default:
3235             goto die;
3236         }
3237         break;
3238     case 18:
3239         switch (sel) {
3240         case 0 ... 7:
3241             gen_helper_1i(mfc0_watchlo, t0, sel);
3242             rn = "WatchLo";
3243             break;
3244         default:
3245             goto die;
3246         }
3247         break;
3248     case 19:
3249         switch (sel) {
3250         case 0 ...7:
3251             gen_helper_1i(mfc0_watchhi, t0, sel);
3252             rn = "WatchHi";
3253             break;
3254         default:
3255             goto die;
3256         }
3257         break;
3258     case 20:
3259         switch (sel) {
3260         case 0:
3261 #if defined(TARGET_MIPS64)
3262             check_insn(env, ctx, ISA_MIPS3);
3263             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_XContext));
3264             tcg_gen_ext32s_tl(t0, t0);
3265             rn = "XContext";
3266             break;
3267 #endif
3268         default:
3269             goto die;
3270         }
3271         break;
3272     case 21:
3273        /* Officially reserved, but sel 0 is used for R1x000 framemask */
3274         switch (sel) {
3275         case 0:
3276             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Framemask));
3277             rn = "Framemask";
3278             break;
3279         default:
3280             goto die;
3281         }
3282         break;
3283     case 22:
3284         tcg_gen_movi_tl(t0, 0); /* unimplemented */
3285         rn = "'Diagnostic"; /* implementation dependent */
3286         break;
3287     case 23:
3288         switch (sel) {
3289         case 0:
3290             gen_helper_mfc0_debug(t0); /* EJTAG support */
3291             rn = "Debug";
3292             break;
3293         case 1:
3294 //            gen_helper_mfc0_tracecontrol(t0); /* PDtrace support */
3295             rn = "TraceControl";
3296 //            break;
3297         case 2:
3298 //            gen_helper_mfc0_tracecontrol2(t0); /* PDtrace support */
3299             rn = "TraceControl2";
3300 //            break;
3301         case 3:
3302 //            gen_helper_mfc0_usertracedata(t0); /* PDtrace support */
3303             rn = "UserTraceData";
3304 //            break;
3305         case 4:
3306 //            gen_helper_mfc0_tracebpc(t0); /* PDtrace support */
3307             rn = "TraceBPC";
3308 //            break;
3309         default:
3310             goto die;
3311         }
3312         break;
3313     case 24:
3314         switch (sel) {
3315         case 0:
3316             /* EJTAG support */
3317             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_DEPC));
3318             tcg_gen_ext32s_tl(t0, t0);
3319             rn = "DEPC";
3320             break;
3321         default:
3322             goto die;
3323         }
3324         break;
3325     case 25:
3326         switch (sel) {
3327         case 0:
3328             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Performance0));
3329             rn = "Performance0";
3330             break;
3331         case 1:
3332 //            gen_helper_mfc0_performance1(t0);
3333             rn = "Performance1";
3334 //            break;
3335         case 2:
3336 //            gen_helper_mfc0_performance2(t0);
3337             rn = "Performance2";
3338 //            break;
3339         case 3:
3340 //            gen_helper_mfc0_performance3(t0);
3341             rn = "Performance3";
3342 //            break;
3343         case 4:
3344 //            gen_helper_mfc0_performance4(t0);
3345             rn = "Performance4";
3346 //            break;
3347         case 5:
3348 //            gen_helper_mfc0_performance5(t0);
3349             rn = "Performance5";
3350 //            break;
3351         case 6:
3352 //            gen_helper_mfc0_performance6(t0);
3353             rn = "Performance6";
3354 //            break;
3355         case 7:
3356 //            gen_helper_mfc0_performance7(t0);
3357             rn = "Performance7";
3358 //            break;
3359         default:
3360             goto die;
3361         }
3362         break;
3363     case 26:
3364         tcg_gen_movi_tl(t0, 0); /* unimplemented */
3365         rn = "ECC";
3366         break;
3367     case 27:
3368         switch (sel) {
3369         case 0 ... 3:
3370             tcg_gen_movi_tl(t0, 0); /* unimplemented */
3371             rn = "CacheErr";
3372             break;
3373         default:
3374             goto die;
3375         }
3376         break;
3377     case 28:
3378         switch (sel) {
3379         case 0:
3380         case 2:
3381         case 4:
3382         case 6:
3383             gen_mfc0_load32(t0, offsetof(CPUState, CP0_TagLo));
3384             rn = "TagLo";
3385             break;
3386         case 1:
3387         case 3:
3388         case 5:
3389         case 7:
3390             gen_mfc0_load32(t0, offsetof(CPUState, CP0_DataLo));
3391             rn = "DataLo";
3392             break;
3393         default:
3394             goto die;
3395         }
3396         break;
3397     case 29:
3398         switch (sel) {
3399         case 0:
3400         case 2:
3401         case 4:
3402         case 6:
3403             gen_mfc0_load32(t0, offsetof(CPUState, CP0_TagHi));
3404             rn = "TagHi";
3405             break;
3406         case 1:
3407         case 3:
3408         case 5:
3409         case 7:
3410             gen_mfc0_load32(t0, offsetof(CPUState, CP0_DataHi));
3411             rn = "DataHi";
3412             break;
3413         default:
3414             goto die;
3415         }
3416         break;
3417     case 30:
3418         switch (sel) {
3419         case 0:
3420             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_ErrorEPC));
3421             tcg_gen_ext32s_tl(t0, t0);
3422             rn = "ErrorEPC";
3423             break;
3424         default:
3425             goto die;
3426         }
3427         break;
3428     case 31:
3429         switch (sel) {
3430         case 0:
3431             /* EJTAG support */
3432             gen_mfc0_load32(t0, offsetof(CPUState, CP0_DESAVE));
3433             rn = "DESAVE";
3434             break;
3435         default:
3436             goto die;
3437         }
3438         break;
3439     default:
3440        goto die;
3441     }
3442     LOG_DISAS("mfc0 %s (reg %d sel %d)\n", rn, reg, sel);
3443     return;
3444
3445 die:
3446     LOG_DISAS("mfc0 %s (reg %d sel %d)\n", rn, reg, sel);
3447     generate_exception(ctx, EXCP_RI);
3448 }
3449
3450 static void gen_mtc0 (CPUState *env, DisasContext *ctx, TCGv t0, int reg, int sel)
3451 {
3452     const char *rn = "invalid";
3453
3454     if (sel != 0)
3455         check_insn(env, ctx, ISA_MIPS32);
3456
3457     if (use_icount)
3458         gen_io_start();
3459
3460     switch (reg) {
3461     case 0:
3462         switch (sel) {
3463         case 0:
3464             gen_helper_mtc0_index(t0);
3465             rn = "Index";
3466             break;
3467         case 1:
3468             check_insn(env, ctx, ASE_MT);
3469             gen_helper_mtc0_mvpcontrol(t0);
3470             rn = "MVPControl";
3471             break;
3472         case 2:
3473             check_insn(env, ctx, ASE_MT);
3474             /* ignored */
3475             rn = "MVPConf0";
3476             break;
3477         case 3:
3478             check_insn(env, ctx, ASE_MT);
3479             /* ignored */
3480             rn = "MVPConf1";
3481             break;
3482         default:
3483             goto die;
3484         }
3485         break;
3486     case 1:
3487         switch (sel) {
3488         case 0:
3489             /* ignored */
3490             rn = "Random";
3491             break;
3492         case 1:
3493             check_insn(env, ctx, ASE_MT);
3494             gen_helper_mtc0_vpecontrol(t0);
3495             rn = "VPEControl";
3496             break;
3497         case 2:
3498             check_insn(env, ctx, ASE_MT);
3499             gen_helper_mtc0_vpeconf0(t0);
3500             rn = "VPEConf0";
3501             break;
3502         case 3:
3503             check_insn(env, ctx, ASE_MT);
3504             gen_helper_mtc0_vpeconf1(t0);
3505             rn = "VPEConf1";
3506             break;
3507         case 4:
3508             check_insn(env, ctx, ASE_MT);
3509             gen_helper_mtc0_yqmask(t0);
3510             rn = "YQMask";
3511             break;
3512         case 5:
3513             check_insn(env, ctx, ASE_MT);
3514             gen_mtc0_store64(t0, offsetof(CPUState, CP0_VPESchedule));
3515             rn = "VPESchedule";
3516             break;
3517         case 6:
3518             check_insn(env, ctx, ASE_MT);
3519             gen_mtc0_store64(t0, offsetof(CPUState, CP0_VPEScheFBack));
3520             rn = "VPEScheFBack";
3521             break;
3522         case 7:
3523             check_insn(env, ctx, ASE_MT);
3524             gen_helper_mtc0_vpeopt(t0);
3525             rn = "VPEOpt";
3526             break;
3527         default:
3528             goto die;
3529         }
3530         break;
3531     case 2:
3532         switch (sel) {
3533         case 0:
3534             gen_helper_mtc0_entrylo0(t0);
3535             rn = "EntryLo0";
3536             break;
3537         case 1:
3538             check_insn(env, ctx, ASE_MT);
3539             gen_helper_mtc0_tcstatus(t0);
3540             rn = "TCStatus";
3541             break;
3542         case 2:
3543             check_insn(env, ctx, ASE_MT);
3544             gen_helper_mtc0_tcbind(t0);
3545             rn = "TCBind";
3546             break;
3547         case 3:
3548             check_insn(env, ctx, ASE_MT);
3549             gen_helper_mtc0_tcrestart(t0);
3550             rn = "TCRestart";
3551             break;
3552         case 4:
3553             check_insn(env, ctx, ASE_MT);
3554             gen_helper_mtc0_tchalt(t0);
3555             rn = "TCHalt";
3556             break;
3557         case 5:
3558             check_insn(env, ctx, ASE_MT);
3559             gen_helper_mtc0_tccontext(t0);
3560             rn = "TCContext";
3561             break;
3562         case 6:
3563             check_insn(env, ctx, ASE_MT);
3564             gen_helper_mtc0_tcschedule(t0);
3565             rn = "TCSchedule";
3566             break;
3567         case 7:
3568             check_insn(env, ctx, ASE_MT);
3569             gen_helper_mtc0_tcschefback(t0);
3570             rn = "TCScheFBack";
3571             break;
3572         default:
3573             goto die;
3574         }
3575         break;
3576     case 3:
3577         switch (sel) {
3578         case 0:
3579             gen_helper_mtc0_entrylo1(t0);
3580             rn = "EntryLo1";
3581             break;
3582         default:
3583             goto die;
3584         }
3585         break;
3586     case 4:
3587         switch (sel) {
3588         case 0:
3589             gen_helper_mtc0_context(t0);
3590             rn = "Context";
3591             break;
3592         case 1:
3593 //            gen_helper_mtc0_contextconfig(t0); /* SmartMIPS ASE */
3594             rn = "ContextConfig";
3595 //            break;
3596         default:
3597             goto die;
3598         }
3599         break;
3600     case 5:
3601         switch (sel) {
3602         case 0:
3603             gen_helper_mtc0_pagemask(t0);
3604             rn = "PageMask";
3605             break;
3606         case 1:
3607             check_insn(env, ctx, ISA_MIPS32R2);
3608             gen_helper_mtc0_pagegrain(t0);
3609             rn = "PageGrain";
3610             break;
3611         default:
3612             goto die;
3613         }
3614         break;
3615     case 6:
3616         switch (sel) {
3617         case 0:
3618             gen_helper_mtc0_wired(t0);
3619             rn = "Wired";
3620             break;
3621         case 1:
3622             check_insn(env, ctx, ISA_MIPS32R2);
3623             gen_helper_mtc0_srsconf0(t0);
3624             rn = "SRSConf0";
3625             break;
3626         case 2:
3627             check_insn(env, ctx, ISA_MIPS32R2);
3628             gen_helper_mtc0_srsconf1(t0);
3629             rn = "SRSConf1";
3630             break;
3631         case 3:
3632             check_insn(env, ctx, ISA_MIPS32R2);
3633             gen_helper_mtc0_srsconf2(t0);
3634             rn = "SRSConf2";
3635             break;
3636         case 4:
3637             check_insn(env, ctx, ISA_MIPS32R2);
3638             gen_helper_mtc0_srsconf3(t0);
3639             rn = "SRSConf3";
3640             break;
3641         case 5:
3642             check_insn(env, ctx, ISA_MIPS32R2);
3643             gen_helper_mtc0_srsconf4(t0);
3644             rn = "SRSConf4";
3645             break;
3646         default:
3647             goto die;
3648         }
3649         break;
3650     case 7:
3651         switch (sel) {
3652         case 0:
3653             check_insn(env, ctx, ISA_MIPS32R2);
3654             gen_helper_mtc0_hwrena(t0);
3655             rn = "HWREna";
3656             break;
3657         default:
3658             goto die;
3659         }
3660         break;
3661     case 8:
3662         /* ignored */
3663         rn = "BadVAddr";
3664         break;
3665     case 9:
3666         switch (sel) {
3667         case 0:
3668             gen_helper_mtc0_count(t0);
3669             rn = "Count";
3670             break;
3671         /* 6,7 are implementation dependent */
3672         default:
3673             goto die;
3674         }
3675         break;
3676     case 10:
3677         switch (sel) {
3678         case 0:
3679             gen_helper_mtc0_entryhi(t0);
3680             rn = "EntryHi";
3681             break;
3682         default:
3683             goto die;
3684         }
3685         break;
3686     case 11:
3687         switch (sel) {
3688         case 0:
3689             gen_helper_mtc0_compare(t0);
3690             rn = "Compare";
3691             break;
3692         /* 6,7 are implementation dependent */
3693         default:
3694             goto die;
3695         }
3696         break;
3697     case 12:
3698         switch (sel) {
3699         case 0:
3700             save_cpu_state(ctx, 1);
3701             gen_helper_mtc0_status(t0);
3702             /* BS_STOP isn't good enough here, hflags may have changed. */
3703             gen_save_pc(ctx->pc + 4);
3704             ctx->bstate = BS_EXCP;
3705             rn = "Status";
3706             break;
3707         case 1:
3708             check_insn(env, ctx, ISA_MIPS32R2);
3709             gen_helper_mtc0_intctl(t0);
3710             /* Stop translation as we may have switched the execution mode */
3711             ctx->bstate = BS_STOP;
3712             rn = "IntCtl";
3713             break;
3714         case 2:
3715             check_insn(env, ctx, ISA_MIPS32R2);
3716             gen_helper_mtc0_srsctl(t0);
3717             /* Stop translation as we may have switched the execution mode */
3718             ctx->bstate = BS_STOP;
3719             rn = "SRSCtl";
3720             break;
3721         case 3:
3722             check_insn(env, ctx, ISA_MIPS32R2);
3723             gen_mtc0_store32(t0, offsetof(CPUState, CP0_SRSMap));
3724             /* Stop translation as we may have switched the execution mode */
3725             ctx->bstate = BS_STOP;
3726             rn = "SRSMap";
3727             break;
3728         default:
3729             goto die;
3730         }
3731         break;
3732     case 13:
3733         switch (sel) {
3734         case 0:
3735             save_cpu_state(ctx, 1);
3736             gen_helper_mtc0_cause(t0);
3737             rn = "Cause";
3738             break;
3739         default:
3740             goto die;
3741         }
3742         break;
3743     case 14:
3744         switch (sel) {
3745         case 0:
3746             gen_mtc0_store64(t0, offsetof(CPUState, CP0_EPC));
3747             rn = "EPC";
3748             break;
3749         default:
3750             goto die;
3751         }
3752         break;
3753     case 15:
3754         switch (sel) {
3755         case 0:
3756             /* ignored */
3757             rn = "PRid";
3758             break;
3759         case 1:
3760             check_insn(env, ctx, ISA_MIPS32R2);
3761             gen_helper_mtc0_ebase(t0);
3762             rn = "EBase";
3763             break;
3764         default:
3765             goto die;
3766         }
3767         break;
3768     case 16:
3769         switch (sel) {
3770         case 0:
3771             gen_helper_mtc0_config0(t0);
3772             rn = "Config";
3773             /* Stop translation as we may have switched the execution mode */
3774             ctx->bstate = BS_STOP;
3775             break;
3776         case 1:
3777             /* ignored, read only */
3778             rn = "Config1";
3779             break;
3780         case 2:
3781             gen_helper_mtc0_config2(t0);
3782             rn = "Config2";
3783             /* Stop translation as we may have switched the execution mode */
3784             ctx->bstate = BS_STOP;
3785             break;
3786         case 3:
3787             /* ignored, read only */
3788             rn = "Config3";
3789             break;
3790         /* 4,5 are reserved */
3791         /* 6,7 are implementation dependent */
3792         case 6:
3793             /* ignored */
3794             rn = "Config6";
3795             break;
3796         case 7:
3797             /* ignored */
3798             rn = "Config7";
3799             break;
3800         default:
3801             rn = "Invalid config selector";
3802             goto die;
3803         }
3804         break;
3805     case 17:
3806         switch (sel) {
3807         case 0:
3808             /* ignored */
3809             rn = "LLAddr";
3810             break;
3811         default:
3812             goto die;
3813         }
3814         break;
3815     case 18:
3816         switch (sel) {
3817         case 0 ... 7:
3818             gen_helper_1i(mtc0_watchlo, t0, sel);
3819             rn = "WatchLo";
3820             break;
3821         default:
3822             goto die;
3823         }
3824         break;
3825     case 19:
3826         switch (sel) {
3827         case 0 ... 7:
3828             gen_helper_1i(mtc0_watchhi, t0, sel);
3829             rn = "WatchHi";
3830             break;
3831         default:
3832             goto die;
3833         }
3834         break;
3835     case 20:
3836         switch (sel) {
3837         case 0:
3838 #if defined(TARGET_MIPS64)
3839             check_insn(env, ctx, ISA_MIPS3);
3840             gen_helper_mtc0_xcontext(t0);
3841             rn = "XContext";
3842             break;
3843 #endif
3844         default:
3845             goto die;
3846         }
3847         break;
3848     case 21:
3849        /* Officially reserved, but sel 0 is used for R1x000 framemask */
3850         switch (sel) {
3851         case 0:
3852             gen_helper_mtc0_framemask(t0);
3853             rn = "Framemask";
3854             break;
3855         default:
3856             goto die;
3857         }
3858         break;
3859     case 22:
3860         /* ignored */
3861         rn = "Diagnostic"; /* implementation dependent */
3862         break;
3863     case 23:
3864         switch (sel) {
3865         case 0:
3866             gen_helper_mtc0_debug(t0); /* EJTAG support */
3867             /* BS_STOP isn't good enough here, hflags may have changed. */
3868             gen_save_pc(ctx->pc + 4);
3869             ctx->bstate = BS_EXCP;
3870             rn = "Debug";
3871             break;
3872         case 1:
3873 //            gen_helper_mtc0_tracecontrol(t0); /* PDtrace support */
3874             rn = "TraceControl";
3875             /* Stop translation as we may have switched the execution mode */
3876             ctx->bstate = BS_STOP;
3877 //            break;
3878         case 2:
3879 //            gen_helper_mtc0_tracecontrol2(t0); /* PDtrace support */
3880             rn = "TraceControl2";
3881             /* Stop translation as we may have switched the execution mode */
3882             ctx->bstate = BS_STOP;
3883 //            break;
3884         case 3:
3885             /* Stop translation as we may have switched the execution mode */
3886             ctx->bstate = BS_STOP;
3887 //            gen_helper_mtc0_usertracedata(t0); /* PDtrace support */
3888             rn = "UserTraceData";
3889             /* Stop translation as we may have switched the execution mode */
3890             ctx->bstate = BS_STOP;
3891 //            break;
3892         case 4:
3893 //            gen_helper_mtc0_tracebpc(t0); /* PDtrace support */
3894             /* Stop translation as we may have switched the execution mode */
3895             ctx->bstate = BS_STOP;
3896             rn = "TraceBPC";
3897 //            break;
3898         default:
3899             goto die;
3900         }
3901         break;
3902     case 24:
3903         switch (sel) {
3904         case 0:
3905             /* EJTAG support */
3906             gen_mtc0_store64(t0, offsetof(CPUState, CP0_DEPC));
3907             rn = "DEPC";
3908             break;
3909         default:
3910             goto die;
3911         }
3912         break;
3913     case 25:
3914         switch (sel) {
3915         case 0:
3916             gen_helper_mtc0_performance0(t0);
3917             rn = "Performance0";
3918             break;
3919         case 1:
3920 //            gen_helper_mtc0_performance1(t0);
3921             rn = "Performance1";
3922 //            break;
3923         case 2:
3924 //            gen_helper_mtc0_performance2(t0);
3925             rn = "Performance2";
3926 //            break;
3927         case 3:
3928 //            gen_helper_mtc0_performance3(t0);
3929             rn = "Performance3";
3930 //            break;
3931         case 4:
3932 //            gen_helper_mtc0_performance4(t0);
3933             rn = "Performance4";
3934 //            break;
3935         case 5:
3936 //            gen_helper_mtc0_performance5(t0);
3937             rn = "Performance5";
3938 //            break;
3939         case 6:
3940 //            gen_helper_mtc0_performance6(t0);
3941             rn = "Performance6";
3942 //            break;
3943         case 7:
3944 //            gen_helper_mtc0_performance7(t0);
3945             rn = "Performance7";
3946 //            break;
3947         default:
3948             goto die;
3949         }
3950        break;
3951     case 26:
3952         /* ignored */
3953         rn = "ECC";
3954         break;
3955     case 27:
3956         switch (sel) {
3957         case 0 ... 3:
3958             /* ignored */
3959             rn = "CacheErr";
3960             break;
3961         default:
3962             goto die;
3963         }
3964        break;
3965     case 28:
3966         switch (sel) {
3967         case 0:
3968         case 2:
3969         case 4:
3970         case 6:
3971             gen_helper_mtc0_taglo(t0);
3972             rn = "TagLo";
3973             break;
3974         case 1:
3975         case 3:
3976         case 5:
3977         case 7:
3978             gen_helper_mtc0_datalo(t0);
3979             rn = "DataLo";
3980             break;
3981         default:
3982             goto die;
3983         }
3984         break;
3985     case 29:
3986         switch (sel) {
3987         case 0:
3988         case 2:
3989         case 4:
3990         case 6:
3991             gen_helper_mtc0_taghi(t0);
3992             rn = "TagHi";
3993             break;
3994         case 1:
3995         case 3:
3996         case 5:
3997         case 7:
3998             gen_helper_mtc0_datahi(t0);
3999             rn = "DataHi";
4000             break;
4001         default:
4002             rn = "invalid sel";
4003             goto die;
4004         }
4005        break;
4006     case 30:
4007         switch (sel) {
4008         case 0:
4009             gen_mtc0_store64(t0, offsetof(CPUState, CP0_ErrorEPC));
4010             rn = "ErrorEPC";
4011             break;
4012         default:
4013             goto die;
4014         }
4015         break;
4016     case 31:
4017         switch (sel) {
4018         case 0:
4019             /* EJTAG support */
4020             gen_mtc0_store32(t0, offsetof(CPUState, CP0_DESAVE));
4021             rn = "DESAVE";
4022             break;
4023         default:
4024             goto die;
4025         }
4026         /* Stop translation as we may have switched the execution mode */
4027         ctx->bstate = BS_STOP;
4028         break;
4029     default:
4030        goto die;
4031     }
4032     LOG_DISAS("mtc0 %s (reg %d sel %d)\n", rn, reg, sel);
4033     /* For simplicity assume that all writes can cause interrupts.  */
4034     if (use_icount) {
4035         gen_io_end();
4036         ctx->bstate = BS_STOP;
4037     }
4038     return;
4039
4040 die:
4041     LOG_DISAS("mtc0 %s (reg %d sel %d)\n", rn, reg, sel);
4042     generate_exception(ctx, EXCP_RI);
4043 }
4044
4045 #if defined(TARGET_MIPS64)
4046 static void gen_dmfc0 (CPUState *env, DisasContext *ctx, TCGv t0, int reg, int sel)
4047 {
4048     const char *rn = "invalid";
4049
4050     if (sel != 0)
4051         check_insn(env, ctx, ISA_MIPS64);
4052
4053     switch (reg) {
4054     case 0:
4055         switch (sel) {
4056         case 0:
4057             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Index));
4058             rn = "Index";
4059             break;
4060         case 1:
4061             check_insn(env, ctx, ASE_MT);
4062             gen_helper_mfc0_mvpcontrol(t0);
4063             rn = "MVPControl";
4064             break;
4065         case 2:
4066             check_insn(env, ctx, ASE_MT);
4067             gen_helper_mfc0_mvpconf0(t0);
4068             rn = "MVPConf0";
4069             break;
4070         case 3:
4071             check_insn(env, ctx, ASE_MT);
4072             gen_helper_mfc0_mvpconf1(t0);
4073             rn = "MVPConf1";
4074             break;
4075         default:
4076             goto die;
4077         }
4078         break;
4079     case 1:
4080         switch (sel) {
4081         case 0:
4082             gen_helper_mfc0_random(t0);
4083             rn = "Random";
4084             break;
4085         case 1:
4086             check_insn(env, ctx, ASE_MT);
4087             gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEControl));
4088             rn = "VPEControl";
4089             break;
4090         case 2:
4091             check_insn(env, ctx, ASE_MT);
4092             gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEConf0));
4093             rn = "VPEConf0";
4094             break;
4095         case 3:
4096             check_insn(env, ctx, ASE_MT);
4097             gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEConf1));
4098             rn = "VPEConf1";
4099             break;
4100         case 4:
4101             check_insn(env, ctx, ASE_MT);
4102             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_YQMask));
4103             rn = "YQMask";
4104             break;
4105         case 5:
4106             check_insn(env, ctx, ASE_MT);
4107             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_VPESchedule));
4108             rn = "VPESchedule";
4109             break;
4110         case 6:
4111             check_insn(env, ctx, ASE_MT);
4112             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_VPEScheFBack));
4113             rn = "VPEScheFBack";
4114             break;
4115         case 7:
4116             check_insn(env, ctx, ASE_MT);
4117             gen_mfc0_load32(t0, offsetof(CPUState, CP0_VPEOpt));
4118             rn = "VPEOpt";
4119             break;
4120         default:
4121             goto die;
4122         }
4123         break;
4124     case 2:
4125         switch (sel) {
4126         case 0:
4127             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryLo0));
4128             rn = "EntryLo0";
4129             break;
4130         case 1:
4131             check_insn(env, ctx, ASE_MT);
4132             gen_helper_mfc0_tcstatus(t0);
4133             rn = "TCStatus";
4134             break;
4135         case 2:
4136             check_insn(env, ctx, ASE_MT);
4137             gen_helper_mfc0_tcbind(t0);
4138             rn = "TCBind";
4139             break;
4140         case 3:
4141             check_insn(env, ctx, ASE_MT);
4142             gen_helper_dmfc0_tcrestart(t0);
4143             rn = "TCRestart";
4144             break;
4145         case 4:
4146             check_insn(env, ctx, ASE_MT);
4147             gen_helper_dmfc0_tchalt(t0);
4148             rn = "TCHalt";
4149             break;
4150         case 5:
4151             check_insn(env, ctx, ASE_MT);
4152             gen_helper_dmfc0_tccontext(t0);
4153             rn = "TCContext";
4154             break;
4155         case 6:
4156             check_insn(env, ctx, ASE_MT);
4157             gen_helper_dmfc0_tcschedule(t0);
4158             rn = "TCSchedule";
4159             break;
4160         case 7:
4161             check_insn(env, ctx, ASE_MT);
4162             gen_helper_dmfc0_tcschefback(t0);
4163             rn = "TCScheFBack";
4164             break;
4165         default:
4166             goto die;
4167         }
4168         break;
4169     case 3:
4170         switch (sel) {
4171         case 0:
4172             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryLo1));
4173             rn = "EntryLo1";
4174             break;
4175         default:
4176             goto die;
4177         }
4178         break;
4179     case 4:
4180         switch (sel) {
4181         case 0:
4182             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_Context));
4183             rn = "Context";
4184             break;
4185         case 1:
4186 //            gen_helper_dmfc0_contextconfig(t0); /* SmartMIPS ASE */
4187             rn = "ContextConfig";
4188 //            break;
4189         default:
4190             goto die;
4191         }
4192         break;
4193     case 5:
4194         switch (sel) {
4195         case 0:
4196             gen_mfc0_load32(t0, offsetof(CPUState, CP0_PageMask));
4197             rn = "PageMask";
4198             break;
4199         case 1:
4200             check_insn(env, ctx, ISA_MIPS32R2);
4201             gen_mfc0_load32(t0, offsetof(CPUState, CP0_PageGrain));
4202             rn = "PageGrain";
4203             break;
4204         default:
4205             goto die;
4206         }
4207         break;
4208     case 6:
4209         switch (sel) {
4210         case 0:
4211             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Wired));
4212             rn = "Wired";
4213             break;
4214         case 1:
4215             check_insn(env, ctx, ISA_MIPS32R2);
4216             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf0));
4217             rn = "SRSConf0";
4218             break;
4219         case 2:
4220             check_insn(env, ctx, ISA_MIPS32R2);
4221             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf1));
4222             rn = "SRSConf1";
4223             break;
4224         case 3:
4225             check_insn(env, ctx, ISA_MIPS32R2);
4226             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf2));
4227             rn = "SRSConf2";
4228             break;
4229         case 4:
4230             check_insn(env, ctx, ISA_MIPS32R2);
4231             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf3));
4232             rn = "SRSConf3";
4233             break;
4234         case 5:
4235             check_insn(env, ctx, ISA_MIPS32R2);
4236             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSConf4));
4237             rn = "SRSConf4";
4238             break;
4239         default:
4240             goto die;
4241         }
4242         break;
4243     case 7:
4244         switch (sel) {
4245         case 0:
4246             check_insn(env, ctx, ISA_MIPS32R2);
4247             gen_mfc0_load32(t0, offsetof(CPUState, CP0_HWREna));
4248             rn = "HWREna";
4249             break;
4250         default:
4251             goto die;
4252         }
4253         break;
4254     case 8:
4255         switch (sel) {
4256         case 0:
4257             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_BadVAddr));
4258             rn = "BadVAddr";
4259             break;
4260         default:
4261             goto die;
4262         }
4263         break;
4264     case 9:
4265         switch (sel) {
4266         case 0:
4267             /* Mark as an IO operation because we read the time.  */
4268             if (use_icount)
4269                 gen_io_start();
4270             gen_helper_mfc0_count(t0);
4271             if (use_icount) {
4272                 gen_io_end();
4273                 ctx->bstate = BS_STOP;
4274             }
4275             rn = "Count";
4276             break;
4277         /* 6,7 are implementation dependent */
4278         default:
4279             goto die;
4280         }
4281         break;
4282     case 10:
4283         switch (sel) {
4284         case 0:
4285             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EntryHi));
4286             rn = "EntryHi";
4287             break;
4288         default:
4289             goto die;
4290         }
4291         break;
4292     case 11:
4293         switch (sel) {
4294         case 0:
4295             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Compare));
4296             rn = "Compare";
4297             break;
4298         /* 6,7 are implementation dependent */
4299         default:
4300             goto die;
4301         }
4302         break;
4303     case 12:
4304         switch (sel) {
4305         case 0:
4306             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Status));
4307             rn = "Status";
4308             break;
4309         case 1:
4310             check_insn(env, ctx, ISA_MIPS32R2);
4311             gen_mfc0_load32(t0, offsetof(CPUState, CP0_IntCtl));
4312             rn = "IntCtl";
4313             break;
4314         case 2:
4315             check_insn(env, ctx, ISA_MIPS32R2);
4316             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSCtl));
4317             rn = "SRSCtl";
4318             break;
4319         case 3:
4320             check_insn(env, ctx, ISA_MIPS32R2);
4321             gen_mfc0_load32(t0, offsetof(CPUState, CP0_SRSMap));
4322             rn = "SRSMap";
4323             break;
4324         default:
4325             goto die;
4326         }
4327         break;
4328     case 13:
4329         switch (sel) {
4330         case 0:
4331             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Cause));
4332             rn = "Cause";
4333             break;
4334         default:
4335             goto die;
4336         }
4337         break;
4338     case 14:
4339         switch (sel) {
4340         case 0:
4341             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_EPC));
4342             rn = "EPC";
4343             break;
4344         default:
4345             goto die;
4346         }
4347         break;
4348     case 15:
4349         switch (sel) {
4350         case 0:
4351             gen_mfc0_load32(t0, offsetof(CPUState, CP0_PRid));
4352             rn = "PRid";
4353             break;
4354         case 1:
4355             check_insn(env, ctx, ISA_MIPS32R2);
4356             gen_mfc0_load32(t0, offsetof(CPUState, CP0_EBase));
4357             rn = "EBase";
4358             break;
4359         default:
4360             goto die;
4361         }
4362         break;
4363     case 16:
4364         switch (sel) {
4365         case 0:
4366             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config0));
4367             rn = "Config";
4368             break;
4369         case 1:
4370             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config1));
4371             rn = "Config1";
4372             break;
4373         case 2:
4374             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config2));
4375             rn = "Config2";
4376             break;
4377         case 3:
4378             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config3));
4379             rn = "Config3";
4380             break;
4381        /* 6,7 are implementation dependent */
4382         case 6:
4383             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config6));
4384             rn = "Config6";
4385             break;
4386         case 7:
4387             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Config7));
4388             rn = "Config7";
4389             break;
4390         default:
4391             goto die;
4392         }
4393         break;
4394     case 17:
4395         switch (sel) {
4396         case 0:
4397             gen_helper_dmfc0_lladdr(t0);
4398             rn = "LLAddr";
4399             break;
4400         default:
4401             goto die;
4402         }
4403         break;
4404     case 18:
4405         switch (sel) {
4406         case 0 ... 7:
4407             gen_helper_1i(dmfc0_watchlo, t0, sel);
4408             rn = "WatchLo";
4409             break;
4410         default:
4411             goto die;
4412         }
4413         break;
4414     case 19:
4415         switch (sel) {
4416         case 0 ... 7:
4417             gen_helper_1i(mfc0_watchhi, t0, sel);
4418             rn = "WatchHi";
4419             break;
4420         default:
4421             goto die;
4422         }
4423         break;
4424     case 20:
4425         switch (sel) {
4426         case 0:
4427             check_insn(env, ctx, ISA_MIPS3);
4428             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_XContext));
4429             rn = "XContext";
4430             break;
4431         default:
4432             goto die;
4433         }
4434         break;
4435     case 21:
4436        /* Officially reserved, but sel 0 is used for R1x000 framemask */
4437         switch (sel) {
4438         case 0:
4439             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Framemask));
4440             rn = "Framemask";
4441             break;
4442         default:
4443             goto die;
4444         }
4445         break;
4446     case 22:
4447         tcg_gen_movi_tl(t0, 0); /* unimplemented */
4448         rn = "'Diagnostic"; /* implementation dependent */
4449         break;
4450     case 23:
4451         switch (sel) {
4452         case 0:
4453             gen_helper_mfc0_debug(t0); /* EJTAG support */
4454             rn = "Debug";
4455             break;
4456         case 1:
4457 //            gen_helper_dmfc0_tracecontrol(t0); /* PDtrace support */
4458             rn = "TraceControl";
4459 //            break;
4460         case 2:
4461 //            gen_helper_dmfc0_tracecontrol2(t0); /* PDtrace support */
4462             rn = "TraceControl2";
4463 //            break;
4464         case 3:
4465 //            gen_helper_dmfc0_usertracedata(t0); /* PDtrace support */
4466             rn = "UserTraceData";
4467 //            break;
4468         case 4:
4469 //            gen_helper_dmfc0_tracebpc(t0); /* PDtrace support */
4470             rn = "TraceBPC";
4471 //            break;
4472         default:
4473             goto die;
4474         }
4475         break;
4476     case 24:
4477         switch (sel) {
4478         case 0:
4479             /* EJTAG support */
4480             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_DEPC));
4481             rn = "DEPC";
4482             break;
4483         default:
4484             goto die;
4485         }
4486         break;
4487     case 25:
4488         switch (sel) {
4489         case 0:
4490             gen_mfc0_load32(t0, offsetof(CPUState, CP0_Performance0));
4491             rn = "Performance0";
4492             break;
4493         case 1:
4494 //            gen_helper_dmfc0_performance1(t0);
4495             rn = "Performance1";
4496 //            break;
4497         case 2:
4498 //            gen_helper_dmfc0_performance2(t0);
4499             rn = "Performance2";
4500 //            break;
4501         case 3:
4502 //            gen_helper_dmfc0_performance3(t0);
4503             rn = "Performance3";
4504 //            break;
4505         case 4:
4506 //            gen_helper_dmfc0_performance4(t0);
4507             rn = "Performance4";
4508 //            break;
4509         case 5:
4510 //            gen_helper_dmfc0_performance5(t0);
4511             rn = "Performance5";
4512 //            break;
4513         case 6:
4514 //            gen_helper_dmfc0_performance6(t0);
4515             rn = "Performance6";
4516 //            break;
4517         case 7:
4518 //            gen_helper_dmfc0_performance7(t0);
4519             rn = "Performance7";
4520 //            break;
4521         default:
4522             goto die;
4523         }
4524         break;
4525     case 26:
4526         tcg_gen_movi_tl(t0, 0); /* unimplemented */
4527         rn = "ECC";
4528         break;
4529     case 27:
4530         switch (sel) {
4531         /* ignored */
4532         case 0 ... 3:
4533             tcg_gen_movi_tl(t0, 0); /* unimplemented */
4534             rn = "CacheErr";
4535             break;
4536         default:
4537             goto die;
4538         }
4539         break;
4540     case 28:
4541         switch (sel) {
4542         case 0:
4543         case 2:
4544         case 4:
4545         case 6:
4546             gen_mfc0_load32(t0, offsetof(CPUState, CP0_TagLo));
4547             rn = "TagLo";
4548             break;
4549         case 1:
4550         case 3:
4551         case 5:
4552         case 7:
4553             gen_mfc0_load32(t0, offsetof(CPUState, CP0_DataLo));
4554             rn = "DataLo";
4555             break;
4556         default:
4557             goto die;
4558         }
4559         break;
4560     case 29:
4561         switch (sel) {
4562         case 0:
4563         case 2:
4564         case 4:
4565         case 6:
4566             gen_mfc0_load32(t0, offsetof(CPUState, CP0_TagHi));
4567             rn = "TagHi";
4568             break;
4569         case 1:
4570         case 3:
4571         case 5:
4572         case 7:
4573             gen_mfc0_load32(t0, offsetof(CPUState, CP0_DataHi));
4574             rn = "DataHi";
4575             break;
4576         default:
4577             goto die;
4578         }
4579         break;
4580     case 30:
4581         switch (sel) {
4582         case 0:
4583             tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, CP0_ErrorEPC));
4584             rn = "ErrorEPC";
4585             break;
4586         default:
4587             goto die;
4588         }
4589         break;
4590     case 31:
4591         switch (sel) {
4592         case 0:
4593             /* EJTAG support */
4594             gen_mfc0_load32(t0, offsetof(CPUState, CP0_DESAVE));
4595             rn = "DESAVE";
4596             break;
4597         default:
4598             goto die;
4599         }
4600         break;
4601     default:
4602         goto die;
4603     }
4604     LOG_DISAS("dmfc0 %s (reg %d sel %d)\n", rn, reg, sel);
4605     return;
4606
4607 die:
4608     LOG_DISAS("dmfc0 %s (reg %d sel %d)\n", rn, reg, sel);
4609     generate_exception(ctx, EXCP_RI);
4610 }
4611
4612 static void gen_dmtc0 (CPUState *env, DisasContext *ctx, TCGv t0, int reg, int sel)
4613 {
4614     const char *rn = "invalid";
4615
4616     if (sel != 0)
4617         check_insn(env, ctx, ISA_MIPS64);
4618
4619     if (use_icount)
4620         gen_io_start();
4621
4622     switch (reg) {
4623     case 0:
4624         switch (sel) {
4625         case 0:
4626             gen_helper_mtc0_index(t0);
4627             rn = "Index";
4628             break;
4629         case 1:
4630             check_insn(env, ctx, ASE_MT);
4631             gen_helper_mtc0_mvpcontrol(t0);
4632             rn = "MVPControl";
4633             break;
4634         case 2:
4635             check_insn(env, ctx, ASE_MT);
4636             /* ignored */
4637             rn = "MVPConf0";
4638             break;
4639         case 3:
4640             check_insn(env, ctx, ASE_MT);
4641             /* ignored */
4642             rn = "MVPConf1";
4643             break;
4644         default:
4645             goto die;
4646         }
4647         break;
4648     case 1:
4649         switch (sel) {
4650         case 0:
4651             /* ignored */
4652             rn = "Random";
4653             break;
4654         case 1:
4655             check_insn(env, ctx, ASE_MT);
4656             gen_helper_mtc0_vpecontrol(t0);
4657             rn = "VPEControl";
4658             break;
4659         case 2:
4660             check_insn(env, ctx, ASE_MT);
4661             gen_helper_mtc0_vpeconf0(t0);
4662             rn = "VPEConf0";
4663             break;
4664         case 3:
4665             check_insn(env, ctx, ASE_MT);
4666             gen_helper_mtc0_vpeconf1(t0);
4667             rn = "VPEConf1";
4668             break;
4669         case 4:
4670             check_insn(env, ctx, ASE_MT);
4671             gen_helper_mtc0_yqmask(t0);
4672             rn = "YQMask";
4673             break;
4674         case 5:
4675             check_insn(env, ctx, ASE_MT);
4676             tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_VPESchedule));
4677             rn = "VPESchedule";
4678             break;
4679         case 6:
4680             check_insn(env, ctx, ASE_MT);
4681             tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_VPEScheFBack));
4682             rn = "VPEScheFBack";
4683             break;
4684         case 7:
4685             check_insn(env, ctx, ASE_MT);
4686             gen_helper_mtc0_vpeopt(t0);
4687             rn = "VPEOpt";
4688             break;
4689         default:
4690             goto die;
4691         }
4692         break;
4693     case 2:
4694         switch (sel) {
4695         case 0:
4696             gen_helper_mtc0_entrylo0(t0);
4697             rn = "EntryLo0";
4698             break;
4699         case 1:
4700             check_insn(env, ctx, ASE_MT);
4701             gen_helper_mtc0_tcstatus(t0);
4702             rn = "TCStatus";
4703             break;
4704         case 2:
4705             check_insn(env, ctx, ASE_MT);
4706             gen_helper_mtc0_tcbind(t0);
4707             rn = "TCBind";
4708             break;
4709         case 3:
4710             check_insn(env, ctx, ASE_MT);
4711             gen_helper_mtc0_tcrestart(t0);
4712             rn = "TCRestart";
4713             break;
4714         case 4:
4715             check_insn(env, ctx, ASE_MT);
4716             gen_helper_mtc0_tchalt(t0);
4717             rn = "TCHalt";
4718             break;
4719         case 5:
4720             check_insn(env, ctx, ASE_MT);
4721             gen_helper_mtc0_tccontext(t0);
4722             rn = "TCContext";
4723             break;
4724         case 6:
4725             check_insn(env, ctx, ASE_MT);
4726             gen_helper_mtc0_tcschedule(t0);
4727             rn = "TCSchedule";
4728             break;
4729         case 7:
4730             check_insn(env, ctx, ASE_MT);
4731             gen_helper_mtc0_tcschefback(t0);
4732             rn = "TCScheFBack";
4733             break;
4734         default:
4735             goto die;
4736         }
4737         break;
4738     case 3:
4739         switch (sel) {
4740         case 0:
4741             gen_helper_mtc0_entrylo1(t0);
4742             rn = "EntryLo1";
4743             break;
4744         default:
4745             goto die;
4746         }
4747         break;
4748     case 4:
4749         switch (sel) {
4750         case 0:
4751             gen_helper_mtc0_context(t0);
4752             rn = "Context";
4753             break;
4754         case 1:
4755 //           gen_helper_mtc0_contextconfig(t0); /* SmartMIPS ASE */
4756             rn = "ContextConfig";
4757 //           break;
4758         default:
4759             goto die;
4760         }
4761         break;
4762     case 5:
4763         switch (sel) {
4764         case 0:
4765             gen_helper_mtc0_pagemask(t0);
4766             rn = "PageMask";
4767             break;
4768         case 1:
4769             check_insn(env, ctx, ISA_MIPS32R2);
4770             gen_helper_mtc0_pagegrain(t0);
4771             rn = "PageGrain";
4772             break;
4773         default:
4774             goto die;
4775         }
4776         break;
4777     case 6:
4778         switch (sel) {
4779         case 0:
4780             gen_helper_mtc0_wired(t0);
4781             rn = "Wired";
4782             break;
4783         case 1:
4784             check_insn(env, ctx, ISA_MIPS32R2);
4785             gen_helper_mtc0_srsconf0(t0);
4786             rn = "SRSConf0";
4787             break;
4788         case 2:
4789             check_insn(env, ctx, ISA_MIPS32R2);
4790             gen_helper_mtc0_srsconf1(t0);
4791             rn = "SRSConf1";
4792             break;
4793         case 3:
4794             check_insn(env, ctx, ISA_MIPS32R2);
4795             gen_helper_mtc0_srsconf2(t0);
4796             rn = "SRSConf2";
4797             break;
4798         case 4:
4799             check_insn(env, ctx, ISA_MIPS32R2);
4800             gen_helper_mtc0_srsconf3(t0);
4801             rn = "SRSConf3";
4802             break;
4803         case 5:
4804             check_insn(env, ctx, ISA_MIPS32R2);
4805             gen_helper_mtc0_srsconf4(t0);
4806             rn = "SRSConf4";
4807             break;
4808         default:
4809             goto die;
4810         }
4811         break;
4812     case 7:
4813         switch (sel) {
4814         case 0:
4815             check_insn(env, ctx, ISA_MIPS32R2);
4816             gen_helper_mtc0_hwrena(t0);
4817             rn = "HWREna";
4818             break;
4819         default:
4820             goto die;
4821         }
4822         break;
4823     case 8:
4824         /* ignored */
4825         rn = "BadVAddr";
4826         break;
4827     case 9:
4828         switch (sel) {
4829         case 0:
4830             gen_helper_mtc0_count(t0);
4831             rn = "Count";
4832             break;
4833         /* 6,7 are implementation dependent */
4834         default:
4835             goto die;
4836         }
4837         /* Stop translation as we may have switched the execution mode */
4838         ctx->bstate = BS_STOP;
4839         break;
4840     case 10:
4841         switch (sel) {
4842         case 0:
4843             gen_helper_mtc0_entryhi(t0);
4844             rn = "EntryHi";
4845             break;
4846         default:
4847             goto die;
4848         }
4849         break;
4850     case 11:
4851         switch (sel) {
4852         case 0:
4853             gen_helper_mtc0_compare(t0);
4854             rn = "Compare";
4855             break;
4856         /* 6,7 are implementation dependent */
4857         default:
4858             goto die;
4859         }
4860         /* Stop translation as we may have switched the execution mode */
4861         ctx->bstate = BS_STOP;
4862         break;
4863     case 12:
4864         switch (sel) {
4865         case 0:
4866             save_cpu_state(ctx, 1);
4867             gen_helper_mtc0_status(t0);
4868             /* BS_STOP isn't good enough here, hflags may have changed. */
4869             gen_save_pc(ctx->pc + 4);
4870             ctx->bstate = BS_EXCP;
4871             rn = "Status";
4872             break;
4873         case 1:
4874             check_insn(env, ctx, ISA_MIPS32R2);
4875             gen_helper_mtc0_intctl(t0);
4876             /* Stop translation as we may have switched the execution mode */
4877             ctx->bstate = BS_STOP;
4878             rn = "IntCtl";
4879             break;
4880         case 2:
4881             check_insn(env, ctx, ISA_MIPS32R2);
4882             gen_helper_mtc0_srsctl(t0);
4883             /* Stop translation as we may have switched the execution mode */
4884             ctx->bstate = BS_STOP;
4885             rn = "SRSCtl";
4886             break;
4887         case 3:
4888             check_insn(env, ctx, ISA_MIPS32R2);
4889             gen_mtc0_store32(t0, offsetof(CPUState, CP0_SRSMap));
4890             /* Stop translation as we may have switched the execution mode */
4891             ctx->bstate = BS_STOP;
4892             rn = "SRSMap";
4893             break;
4894         default:
4895             goto die;
4896         }
4897         break;
4898     case 13:
4899         switch (sel) {
4900         case 0:
4901             save_cpu_state(ctx, 1);
4902             gen_helper_mtc0_cause(t0);
4903             rn = "Cause";
4904             break;
4905         default:
4906             goto die;
4907         }
4908         break;
4909     case 14:
4910         switch (sel) {
4911         case 0:
4912             tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_EPC));
4913             rn = "EPC";
4914             break;
4915         default:
4916             goto die;
4917         }
4918         break;
4919     case 15:
4920         switch (sel) {
4921         case 0:
4922             /* ignored */
4923             rn = "PRid";
4924             break;
4925         case 1:
4926             check_insn(env, ctx, ISA_MIPS32R2);
4927             gen_helper_mtc0_ebase(t0);
4928             rn = "EBase";
4929             break;
4930         default:
4931             goto die;
4932         }
4933         break;
4934     case 16:
4935         switch (sel) {
4936         case 0:
4937             gen_helper_mtc0_config0(t0);
4938             rn = "Config";
4939             /* Stop translation as we may have switched the execution mode */
4940             ctx->bstate = BS_STOP;
4941             break;
4942         case 1:
4943             /* ignored, read only */
4944             rn = "Config1";
4945             break;
4946         case 2:
4947             gen_helper_mtc0_config2(t0);
4948             rn = "Config2";
4949             /* Stop translation as we may have switched the execution mode */
4950             ctx->bstate = BS_STOP;
4951             break;
4952         case 3:
4953             /* ignored */
4954             rn = "Config3";
4955             break;
4956         /* 6,7 are implementation dependent */
4957         default:
4958             rn = "Invalid config selector";
4959             goto die;
4960         }
4961         break;
4962     case 17:
4963         switch (sel) {
4964         case 0:
4965             /* ignored */
4966             rn = "LLAddr";
4967             break;
4968         default:
4969             goto die;
4970         }
4971         break;
4972     case 18:
4973         switch (sel) {
4974         case 0 ... 7:
4975             gen_helper_1i(mtc0_watchlo, t0, sel);
4976             rn = "WatchLo";
4977             break;
4978         default:
4979             goto die;
4980         }
4981         break;
4982     case 19:
4983         switch (sel) {
4984         case 0 ... 7:
4985             gen_helper_1i(mtc0_watchhi, t0, sel);
4986             rn = "WatchHi";
4987             break;
4988         default:
4989             goto die;
4990         }
4991         break;
4992     case 20:
4993         switch (sel) {
4994         case 0:
4995             check_insn(env, ctx, ISA_MIPS3);
4996             gen_helper_mtc0_xcontext(t0);
4997             rn = "XContext";
4998             break;
4999         default:
5000             goto die;
5001         }
5002         break;
5003     case 21:
5004        /* Officially reserved, but sel 0 is used for R1x000 framemask */
5005         switch (sel) {
5006         case 0:
5007             gen_helper_mtc0_framemask(t0);
5008             rn = "Framemask";
5009             break;
5010         default:
5011             goto die;
5012         }
5013         break;
5014     case 22:
5015         /* ignored */
5016         rn = "Diagnostic"; /* implementation dependent */
5017         break;
5018     case 23:
5019         switch (sel) {
5020         case 0:
5021             gen_helper_mtc0_debug(t0); /* EJTAG support */
5022             /* BS_STOP isn't good enough here, hflags may have changed. */
5023             gen_save_pc(ctx->pc + 4);
5024             ctx->bstate = BS_EXCP;
5025             rn = "Debug";
5026             break;
5027         case 1:
5028 //            gen_helper_mtc0_tracecontrol(t0); /* PDtrace support */
5029             /* Stop translation as we may have switched the execution mode */
5030             ctx->bstate = BS_STOP;
5031             rn = "TraceControl";
5032 //            break;
5033         case 2:
5034 //            gen_helper_mtc0_tracecontrol2(t0); /* PDtrace support */
5035             /* Stop translation as we may have switched the execution mode */
5036             ctx->bstate = BS_STOP;
5037             rn = "TraceControl2";
5038 //            break;
5039         case 3:
5040 //            gen_helper_mtc0_usertracedata(t0); /* PDtrace support */
5041             /* Stop translation as we may have switched the execution mode */
5042             ctx->bstate = BS_STOP;
5043             rn = "UserTraceData";
5044 //            break;
5045         case 4:
5046 //            gen_helper_mtc0_tracebpc(t0); /* PDtrace support */
5047             /* Stop translation as we may have switched the execution mode */
5048             ctx->bstate = BS_STOP;
5049             rn = "TraceBPC";
5050 //            break;
5051         default:
5052             goto die;
5053         }
5054         break;
5055     case 24:
5056         switch (sel) {
5057         case 0:
5058             /* EJTAG support */
5059             tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_DEPC));
5060             rn = "DEPC";
5061             break;
5062         default:
5063             goto die;
5064         }
5065         break;
5066     case 25:
5067         switch (sel) {
5068         case 0:
5069             gen_helper_mtc0_performance0(t0);
5070             rn = "Performance0";
5071             break;
5072         case 1:
5073 //            gen_helper_mtc0_performance1(t0);
5074             rn = "Performance1";
5075 //            break;
5076         case 2:
5077 //            gen_helper_mtc0_performance2(t0);
5078             rn = "Performance2";
5079 //            break;
5080         case 3:
5081 //            gen_helper_mtc0_performance3(t0);
5082             rn = "Performance3";
5083 //            break;
5084         case 4:
5085 //            gen_helper_mtc0_performance4(t0);
5086             rn = "Performance4";
5087 //            break;
5088         case 5:
5089 //            gen_helper_mtc0_performance5(t0);
5090             rn = "Performance5";
5091 //            break;
5092         case 6:
5093 //            gen_helper_mtc0_performance6(t0);
5094             rn = "Performance6";
5095 //            break;
5096         case 7:
5097 //            gen_helper_mtc0_performance7(t0);
5098             rn = "Performance7";
5099 //            break;
5100         default:
5101             goto die;
5102         }
5103         break;
5104     case 26:
5105         /* ignored */
5106         rn = "ECC";
5107         break;
5108     case 27:
5109         switch (sel) {
5110         case 0 ... 3:
5111             /* ignored */
5112             rn = "CacheErr";
5113             break;
5114         default:
5115             goto die;
5116         }
5117         break;
5118     case 28:
5119         switch (sel) {
5120         case 0:
5121         case 2:
5122         case 4:
5123         case 6:
5124             gen_helper_mtc0_taglo(t0);
5125             rn = "TagLo";
5126             break;
5127         case 1:
5128         case 3:
5129         case 5:
5130         case 7:
5131             gen_helper_mtc0_datalo(t0);
5132             rn = "DataLo";
5133             break;
5134         default:
5135             goto die;
5136         }
5137         break;
5138     case 29:
5139         switch (sel) {
5140         case 0:
5141         case 2:
5142         case 4:
5143         case 6:
5144             gen_helper_mtc0_taghi(t0);
5145             rn = "TagHi";
5146             break;
5147         case 1:
5148         case 3:
5149         case 5:
5150         case 7:
5151             gen_helper_mtc0_datahi(t0);
5152             rn = "DataHi";
5153             break;
5154         default:
5155             rn = "invalid sel";
5156             goto die;
5157         }
5158         break;
5159     case 30:
5160         switch (sel) {
5161         case 0:
5162             tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, CP0_ErrorEPC));
5163             rn = "ErrorEPC";
5164             break;
5165         default:
5166             goto die;
5167         }
5168         break;
5169     case 31:
5170         switch (sel) {
5171         case 0:
5172             /* EJTAG support */
5173             gen_mtc0_store32(t0, offsetof(CPUState, CP0_DESAVE));
5174             rn = "DESAVE";
5175             break;
5176         default:
5177             goto die;
5178         }
5179         /* Stop translation as we may have switched the execution mode */
5180         ctx->bstate = BS_STOP;
5181         break;
5182     default:
5183         goto die;
5184     }
5185     LOG_DISAS("dmtc0 %s (reg %d sel %d)\n", rn, reg, sel);
5186     /* For simplicity assume that all writes can cause interrupts.  */
5187     if (use_icount) {
5188         gen_io_end();
5189         ctx->bstate = BS_STOP;
5190     }
5191     return;
5192
5193 die:
5194     LOG_DISAS("dmtc0 %s (reg %d sel %d)\n", rn, reg, sel);
5195     generate_exception(ctx, EXCP_RI);
5196 }
5197 #endif /* TARGET_MIPS64 */
5198
5199 static void gen_mftr(CPUState *env, DisasContext *ctx, int rt, int rd,
5200                      int u, int sel, int h)
5201 {
5202     int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
5203     TCGv t0 = tcg_temp_local_new();
5204
5205     if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
5206         ((env->tcs[other_tc].CP0_TCBind & (0xf << CP0TCBd_CurVPE)) !=
5207          (env->active_tc.CP0_TCBind & (0xf << CP0TCBd_CurVPE))))
5208         tcg_gen_movi_tl(t0, -1);
5209     else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
5210              (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC)))
5211         tcg_gen_movi_tl(t0, -1);
5212     else if (u == 0) {
5213         switch (rt) {
5214         case 2:
5215             switch (sel) {
5216             case 1:
5217                 gen_helper_mftc0_tcstatus(t0);
5218                 break;
5219             case 2:
5220                 gen_helper_mftc0_tcbind(t0);
5221                 break;
5222             case 3:
5223                 gen_helper_mftc0_tcrestart(t0);
5224                 break;
5225             case 4:
5226                 gen_helper_mftc0_tchalt(t0);
5227                 break;
5228             case 5:
5229                 gen_helper_mftc0_tccontext(t0);
5230                 break;
5231             case 6:
5232                 gen_helper_mftc0_tcschedule(t0);
5233                 break;
5234             case 7:
5235                 gen_helper_mftc0_tcschefback(t0);
5236                 break;
5237             default:
5238                 gen_mfc0(env, ctx, t0, rt, sel);
5239                 break;
5240             }
5241             break;
5242         case 10:
5243             switch (sel) {
5244             case 0:
5245                 gen_helper_mftc0_entryhi(t0);
5246                 break;
5247             default:
5248                 gen_mfc0(env, ctx, t0, rt, sel);
5249                 break;
5250             }
5251         case 12:
5252             switch (sel) {
5253             case 0:
5254                 gen_helper_mftc0_status(t0);
5255                 break;
5256             default:
5257                 gen_mfc0(env, ctx, t0, rt, sel);
5258                 break;
5259             }
5260         case 23:
5261             switch (sel) {
5262             case 0:
5263                 gen_helper_mftc0_debug(t0);
5264                 break;
5265             default:
5266                 gen_mfc0(env, ctx, t0, rt, sel);
5267                 break;
5268             }
5269             break;
5270         default:
5271             gen_mfc0(env, ctx, t0, rt, sel);
5272         }
5273     } else switch (sel) {
5274     /* GPR registers. */
5275     case 0:
5276         gen_helper_1i(mftgpr, t0, rt);
5277         break;
5278     /* Auxiliary CPU registers */
5279     case 1:
5280         switch (rt) {
5281         case 0:
5282             gen_helper_1i(mftlo, t0, 0);
5283             break;
5284         case 1:
5285             gen_helper_1i(mfthi, t0, 0);
5286             break;
5287         case 2:
5288             gen_helper_1i(mftacx, t0, 0);
5289             break;
5290         case 4:
5291             gen_helper_1i(mftlo, t0, 1);
5292             break;
5293         case 5:
5294             gen_helper_1i(mfthi, t0, 1);
5295             break;
5296         case 6:
5297             gen_helper_1i(mftacx, t0, 1);
5298             break;
5299         case 8:
5300             gen_helper_1i(mftlo, t0, 2);
5301             break;
5302         case 9:
5303             gen_helper_1i(mfthi, t0, 2);
5304             break;
5305         case 10:
5306             gen_helper_1i(mftacx, t0, 2);
5307             break;
5308         case 12:
5309             gen_helper_1i(mftlo, t0, 3);
5310             break;
5311         case 13:
5312             gen_helper_1i(mfthi, t0, 3);
5313             break;
5314         case 14:
5315             gen_helper_1i(mftacx, t0, 3);
5316             break;
5317         case 16:
5318             gen_helper_mftdsp(t0);
5319             break;
5320         default:
5321             goto die;
5322         }
5323         break;
5324     /* Floating point (COP1). */
5325     case 2:
5326         /* XXX: For now we support only a single FPU context. */
5327         if (h == 0) {
5328             TCGv_i32 fp0 = tcg_temp_new_i32();
5329
5330             gen_load_fpr32(fp0, rt);
5331             tcg_gen_ext_i32_tl(t0, fp0);
5332             tcg_temp_free_i32(fp0);
5333         } else {
5334             TCGv_i32 fp0 = tcg_temp_new_i32();
5335
5336             gen_load_fpr32h(fp0, rt);
5337             tcg_gen_ext_i32_tl(t0, fp0);
5338             tcg_temp_free_i32(fp0);
5339         }
5340         break;
5341     case 3:
5342         /* XXX: For now we support only a single FPU context. */
5343         gen_helper_1i(cfc1, t0, rt);
5344         break;
5345     /* COP2: Not implemented. */
5346     case 4:
5347     case 5:
5348         /* fall through */
5349     default:
5350         goto die;
5351     }
5352     LOG_DISAS("mftr (reg %d u %d sel %d h %d)\n", rt, u, sel, h);
5353     gen_store_gpr(t0, rd);
5354     tcg_temp_free(t0);
5355     return;
5356
5357 die:
5358     tcg_temp_free(t0);
5359     LOG_DISAS("mftr (reg %d u %d sel %d h %d)\n", rt, u, sel, h);
5360     generate_exception(ctx, EXCP_RI);
5361 }
5362
5363 static void gen_mttr(CPUState *env, DisasContext *ctx, int rd, int rt,
5364                      int u, int sel, int h)
5365 {
5366     int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
5367     TCGv t0 = tcg_temp_local_new();
5368
5369     gen_load_gpr(t0, rt);
5370     if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
5371         ((env->tcs[other_tc].CP0_TCBind & (0xf << CP0TCBd_CurVPE)) !=
5372          (env->active_tc.CP0_TCBind & (0xf << CP0TCBd_CurVPE))))
5373         /* NOP */ ;
5374     else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
5375              (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC)))
5376         /* NOP */ ;
5377     else if (u == 0) {
5378         switch (rd) {
5379         case 2:
5380             switch (sel) {
5381             case 1:
5382                 gen_helper_mttc0_tcstatus(t0);
5383                 break;
5384             case 2:
5385                 gen_helper_mttc0_tcbind(t0);
5386                 break;
5387             case 3:
5388                 gen_helper_mttc0_tcrestart(t0);
5389                 break;
5390             case 4:
5391                 gen_helper_mttc0_tchalt(t0);
5392                 break;
5393             case 5:
5394                 gen_helper_mttc0_tccontext(t0);
5395                 break;
5396             case 6:
5397                 gen_helper_mttc0_tcschedule(t0);
5398                 break;
5399             case 7:
5400                 gen_helper_mttc0_tcschefback(t0);
5401                 break;
5402             default:
5403                 gen_mtc0(env, ctx, t0, rd, sel);
5404                 break;
5405             }
5406             break;
5407         case 10:
5408             switch (sel) {
5409             case 0:
5410                 gen_helper_mttc0_entryhi(t0);
5411                 break;
5412             default:
5413                 gen_mtc0(env, ctx, t0, rd, sel);
5414                 break;
5415             }
5416         case 12:
5417             switch (sel) {
5418             case 0:
5419                 gen_helper_mttc0_status(t0);
5420                 break;
5421             default:
5422                 gen_mtc0(env, ctx, t0, rd, sel);
5423                 break;
5424             }
5425         case 23:
5426             switch (sel) {
5427             case 0:
5428                 gen_helper_mttc0_debug(t0);
5429                 break;
5430             default:
5431                 gen_mtc0(env, ctx, t0, rd, sel);
5432                 break;
5433             }
5434             break;
5435         default:
5436             gen_mtc0(env, ctx, t0, rd, sel);
5437         }
5438     } else switch (sel) {
5439     /* GPR registers. */
5440     case 0:
5441         gen_helper_1i(mttgpr, t0, rd);
5442         break;
5443     /* Auxiliary CPU registers */
5444     case 1:
5445         switch (rd) {
5446         case 0:
5447             gen_helper_1i(mttlo, t0, 0);
5448             break;
5449         case 1:
5450             gen_helper_1i(mtthi, t0, 0);
5451             break;
5452         case 2:
5453             gen_helper_1i(mttacx, t0, 0);
5454             break;
5455         case 4:
5456             gen_helper_1i(mttlo, t0, 1);
5457             break;
5458         case 5:
5459             gen_helper_1i(mtthi, t0, 1);
5460             break;
5461         case 6:
5462             gen_helper_1i(mttacx, t0, 1);
5463             break;
5464         case 8:
5465             gen_helper_1i(mttlo, t0, 2);
5466             break;
5467         case 9:
5468             gen_helper_1i(mtthi, t0, 2);
5469             break;
5470         case 10:
5471             gen_helper_1i(mttacx, t0, 2);
5472             break;
5473         case 12:
5474             gen_helper_1i(mttlo, t0, 3);
5475             break;
5476         case 13:
5477             gen_helper_1i(mtthi, t0, 3);
5478             break;
5479         case 14:
5480             gen_helper_1i(mttacx, t0, 3);
5481             break;
5482         case 16:
5483             gen_helper_mttdsp(t0);
5484             break;
5485         default:
5486             goto die;
5487         }
5488         break;
5489     /* Floating point (COP1). */
5490     case 2:
5491         /* XXX: For now we support only a single FPU context. */
5492         if (h == 0) {
5493             TCGv_i32 fp0 = tcg_temp_new_i32();
5494
5495             tcg_gen_trunc_tl_i32(fp0, t0);
5496             gen_store_fpr32(fp0, rd);
5497             tcg_temp_free_i32(fp0);
5498         } else {
5499             TCGv_i32 fp0 = tcg_temp_new_i32();
5500
5501             tcg_gen_trunc_tl_i32(fp0, t0);
5502             gen_store_fpr32h(fp0, rd);
5503             tcg_temp_free_i32(fp0);
5504         }
5505         break;
5506     case 3:
5507         /* XXX: For now we support only a single FPU context. */
5508         gen_helper_1i(ctc1, t0, rd);
5509         break;
5510     /* COP2: Not implemented. */
5511     case 4:
5512     case 5:
5513         /* fall through */
5514     default:
5515         goto die;
5516     }
5517     LOG_DISAS("mttr (reg %d u %d sel %d h %d)\n", rd, u, sel, h);
5518     tcg_temp_free(t0);
5519     return;
5520
5521 die:
5522     tcg_temp_free(t0);
5523     LOG_DISAS("mttr (reg %d u %d sel %d h %d)\n", rd, u, sel, h);
5524     generate_exception(ctx, EXCP_RI);
5525 }
5526
5527 static void gen_cp0 (CPUState *env, DisasContext *ctx, uint32_t opc, int rt, int rd)
5528 {
5529     const char *opn = "ldst";
5530
5531     switch (opc) {
5532     case OPC_MFC0:
5533         if (rt == 0) {
5534             /* Treat as NOP. */
5535             return;
5536         }
5537         gen_mfc0(env, ctx, cpu_gpr[rt], rd, ctx->opcode & 0x7);
5538         opn = "mfc0";
5539         break;
5540     case OPC_MTC0:
5541         {
5542             TCGv t0 = tcg_temp_new();
5543
5544             gen_load_gpr(t0, rt);
5545             gen_mtc0(env, ctx, t0, rd, ctx->opcode & 0x7);
5546             tcg_temp_free(t0);
5547         }
5548         opn = "mtc0";
5549         break;
5550 #if defined(TARGET_MIPS64)
5551     case OPC_DMFC0:
5552         check_insn(env, ctx, ISA_MIPS3);
5553         if (rt == 0) {
5554             /* Treat as NOP. */
5555             return;
5556         }
5557         gen_dmfc0(env, ctx, cpu_gpr[rt], rd, ctx->opcode & 0x7);
5558         opn = "dmfc0";
5559         break;
5560     case OPC_DMTC0:
5561         check_insn(env, ctx, ISA_MIPS3);
5562         {
5563             TCGv t0 = tcg_temp_new();
5564
5565             gen_load_gpr(t0, rt);
5566             gen_dmtc0(env, ctx, t0, rd, ctx->opcode & 0x7);
5567             tcg_temp_free(t0);
5568         }
5569         opn = "dmtc0";
5570         break;
5571 #endif
5572     case OPC_MFTR:
5573         check_insn(env, ctx, ASE_MT);
5574         if (rd == 0) {
5575             /* Treat as NOP. */
5576             return;
5577         }
5578         gen_mftr(env, ctx, rt, rd, (ctx->opcode >> 5) & 1,
5579                  ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
5580         opn = "mftr";
5581         break;
5582     case OPC_MTTR:
5583         check_insn(env, ctx, ASE_MT);
5584         gen_mttr(env, ctx, rd, rt, (ctx->opcode >> 5) & 1,
5585                  ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
5586         opn = "mttr";
5587         break;
5588     case OPC_TLBWI:
5589         opn = "tlbwi";
5590         if (!env->tlb->helper_tlbwi)
5591             goto die;
5592         gen_helper_tlbwi();
5593         break;
5594     case OPC_TLBWR:
5595         opn = "tlbwr";
5596         if (!env->tlb->helper_tlbwr)
5597             goto die;
5598         gen_helper_tlbwr();
5599         break;
5600     case OPC_TLBP:
5601         opn = "tlbp";
5602         if (!env->tlb->helper_tlbp)
5603             goto die;
5604         gen_helper_tlbp();
5605         break;
5606     case OPC_TLBR:
5607         opn = "tlbr";
5608         if (!env->tlb->helper_tlbr)
5609             goto die;
5610         gen_helper_tlbr();
5611         break;
5612     case OPC_ERET:
5613         opn = "eret";
5614         check_insn(env, ctx, ISA_MIPS2);
5615         gen_helper_eret();
5616         ctx->bstate = BS_EXCP;
5617         break;
5618     case OPC_DERET:
5619         opn = "deret";
5620         check_insn(env, ctx, ISA_MIPS32);
5621         if (!(ctx->hflags & MIPS_HFLAG_DM)) {
5622             MIPS_INVAL(opn);
5623             generate_exception(ctx, EXCP_RI);
5624         } else {
5625             gen_helper_deret();
5626             ctx->bstate = BS_EXCP;
5627         }
5628         break;
5629     case OPC_WAIT:
5630         opn = "wait";
5631         check_insn(env, ctx, ISA_MIPS3 | ISA_MIPS32);
5632         /* If we get an exception, we want to restart at next instruction */
5633         ctx->pc += 4;
5634         save_cpu_state(ctx, 1);
5635         ctx->pc -= 4;
5636         gen_helper_wait();
5637         ctx->bstate = BS_EXCP;
5638         break;
5639     default:
5640  die:
5641         MIPS_INVAL(opn);
5642         generate_exception(ctx, EXCP_RI);
5643         return;
5644     }
5645     MIPS_DEBUG("%s %s %d", opn, regnames[rt], rd);
5646 }
5647 #endif /* !CONFIG_USER_ONLY */
5648
5649 /* CP1 Branches (before delay slot) */
5650 static void gen_compute_branch1 (CPUState *env, DisasContext *ctx, uint32_t op,
5651                                  int32_t cc, int32_t offset)
5652 {
5653     target_ulong btarget;
5654     const char *opn = "cp1 cond branch";
5655     TCGv_i32 t0 = tcg_temp_new_i32();
5656
5657     if (cc != 0)
5658         check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
5659
5660     btarget = ctx->pc + 4 + offset;
5661
5662     switch (op) {
5663     case OPC_BC1F:
5664         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
5665         tcg_gen_not_i32(t0, t0);
5666         tcg_gen_andi_i32(t0, t0, 1);
5667         tcg_gen_extu_i32_tl(bcond, t0);
5668         opn = "bc1f";
5669         goto not_likely;
5670     case OPC_BC1FL:
5671         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
5672         tcg_gen_not_i32(t0, t0);
5673         tcg_gen_andi_i32(t0, t0, 1);
5674         tcg_gen_extu_i32_tl(bcond, t0);
5675         opn = "bc1fl";
5676         goto likely;
5677     case OPC_BC1T:
5678         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
5679         tcg_gen_andi_i32(t0, t0, 1);
5680         tcg_gen_extu_i32_tl(bcond, t0);
5681         opn = "bc1t";
5682         goto not_likely;
5683     case OPC_BC1TL:
5684         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
5685         tcg_gen_andi_i32(t0, t0, 1);
5686         tcg_gen_extu_i32_tl(bcond, t0);
5687         opn = "bc1tl";
5688     likely:
5689         ctx->hflags |= MIPS_HFLAG_BL;
5690         break;
5691     case OPC_BC1FANY2:
5692         {
5693             TCGv_i32 t1 = tcg_temp_new_i32();
5694             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
5695             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
5696             tcg_gen_or_i32(t0, t0, t1);
5697             tcg_temp_free_i32(t1);
5698             tcg_gen_not_i32(t0, t0);
5699             tcg_gen_andi_i32(t0, t0, 1);
5700             tcg_gen_extu_i32_tl(bcond, t0);
5701         }
5702         opn = "bc1any2f";
5703         goto not_likely;
5704     case OPC_BC1TANY2:
5705         {
5706             TCGv_i32 t1 = tcg_temp_new_i32();
5707             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
5708             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
5709             tcg_gen_or_i32(t0, t0, t1);
5710             tcg_temp_free_i32(t1);
5711             tcg_gen_andi_i32(t0, t0, 1);
5712             tcg_gen_extu_i32_tl(bcond, t0);
5713         }
5714         opn = "bc1any2t";
5715         goto not_likely;
5716     case OPC_BC1FANY4:
5717         {
5718             TCGv_i32 t1 = tcg_temp_new_i32();
5719             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
5720             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
5721             tcg_gen_or_i32(t0, t0, t1);
5722             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+2));
5723             tcg_gen_or_i32(t0, t0, t1);
5724             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+3));
5725             tcg_gen_or_i32(t0, t0, t1);
5726             tcg_temp_free_i32(t1);
5727             tcg_gen_not_i32(t0, t0);
5728             tcg_gen_andi_i32(t0, t0, 1);
5729             tcg_gen_extu_i32_tl(bcond, t0);
5730         }
5731         opn = "bc1any4f";
5732         goto not_likely;
5733     case OPC_BC1TANY4:
5734         {
5735             TCGv_i32 t1 = tcg_temp_new_i32();
5736             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
5737             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
5738             tcg_gen_or_i32(t0, t0, t1);
5739             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+2));
5740             tcg_gen_or_i32(t0, t0, t1);
5741             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+3));
5742             tcg_gen_or_i32(t0, t0, t1);
5743             tcg_temp_free_i32(t1);
5744             tcg_gen_andi_i32(t0, t0, 1);
5745             tcg_gen_extu_i32_tl(bcond, t0);
5746         }
5747         opn = "bc1any4t";
5748     not_likely:
5749         ctx->hflags |= MIPS_HFLAG_BC;
5750         break;
5751     default:
5752         MIPS_INVAL(opn);
5753         generate_exception (ctx, EXCP_RI);
5754         goto out;
5755     }
5756     MIPS_DEBUG("%s: cond %02x target " TARGET_FMT_lx, opn,
5757                ctx->hflags, btarget);
5758     ctx->btarget = btarget;
5759
5760  out:
5761     tcg_temp_free_i32(t0);
5762 }
5763
5764 /* Coprocessor 1 (FPU) */
5765
5766 #define FOP(func, fmt) (((fmt) << 21) | (func))
5767
5768 static void gen_cp1 (DisasContext *ctx, uint32_t opc, int rt, int fs)
5769 {
5770     const char *opn = "cp1 move";
5771     TCGv t0 = tcg_temp_new();
5772
5773     switch (opc) {
5774     case OPC_MFC1:
5775         {
5776             TCGv_i32 fp0 = tcg_temp_new_i32();
5777
5778             gen_load_fpr32(fp0, fs);
5779             tcg_gen_ext_i32_tl(t0, fp0);
5780             tcg_temp_free_i32(fp0);
5781         }
5782         gen_store_gpr(t0, rt);
5783         opn = "mfc1";
5784         break;
5785     case OPC_MTC1:
5786         gen_load_gpr(t0, rt);
5787         {
5788             TCGv_i32 fp0 = tcg_temp_new_i32();
5789
5790             tcg_gen_trunc_tl_i32(fp0, t0);
5791             gen_store_fpr32(fp0, fs);
5792             tcg_temp_free_i32(fp0);
5793         }
5794         opn = "mtc1";
5795         break;
5796     case OPC_CFC1:
5797         gen_helper_1i(cfc1, t0, fs);
5798         gen_store_gpr(t0, rt);
5799         opn = "cfc1";
5800         break;
5801     case OPC_CTC1:
5802         gen_load_gpr(t0, rt);
5803         gen_helper_1i(ctc1, t0, fs);
5804         opn = "ctc1";
5805         break;
5806 #if defined(TARGET_MIPS64)
5807     case OPC_DMFC1:
5808         gen_load_fpr64(ctx, t0, fs);
5809         gen_store_gpr(t0, rt);
5810         opn = "dmfc1";
5811         break;
5812     case OPC_DMTC1:
5813         gen_load_gpr(t0, rt);
5814         gen_store_fpr64(ctx, t0, fs);
5815         opn = "dmtc1";
5816         break;
5817 #endif
5818     case OPC_MFHC1:
5819         {
5820             TCGv_i32 fp0 = tcg_temp_new_i32();
5821
5822             gen_load_fpr32h(fp0, fs);
5823             tcg_gen_ext_i32_tl(t0, fp0);
5824             tcg_temp_free_i32(fp0);
5825         }
5826         gen_store_gpr(t0, rt);
5827         opn = "mfhc1";
5828         break;
5829     case OPC_MTHC1:
5830         gen_load_gpr(t0, rt);
5831         {
5832             TCGv_i32 fp0 = tcg_temp_new_i32();
5833
5834             tcg_gen_trunc_tl_i32(fp0, t0);
5835             gen_store_fpr32h(fp0, fs);
5836             tcg_temp_free_i32(fp0);
5837         }
5838         opn = "mthc1";
5839         break;
5840     default:
5841         MIPS_INVAL(opn);
5842         generate_exception (ctx, EXCP_RI);
5843         goto out;
5844     }
5845     MIPS_DEBUG("%s %s %s", opn, regnames[rt], fregnames[fs]);
5846
5847  out:
5848     tcg_temp_free(t0);
5849 }
5850
5851 static void gen_movci (DisasContext *ctx, int rd, int rs, int cc, int tf)
5852 {
5853     int l1;
5854     TCGCond cond;
5855     TCGv_i32 t0;
5856
5857     if (rd == 0) {
5858         /* Treat as NOP. */
5859         return;
5860     }
5861
5862     if (tf)
5863         cond = TCG_COND_EQ;
5864     else
5865         cond = TCG_COND_NE;
5866
5867     l1 = gen_new_label();
5868     t0 = tcg_temp_new_i32();
5869     tcg_gen_andi_i32(t0, fpu_fcr31, get_fp_bit(cc));
5870     tcg_gen_brcondi_i32(cond, t0, 0, l1);
5871     tcg_temp_free_i32(t0);
5872     if (rs == 0) {
5873         tcg_gen_movi_tl(cpu_gpr[rd], 0);
5874     } else {
5875         tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
5876     }
5877     gen_set_label(l1);
5878 }
5879
5880 static inline void gen_movcf_s (int fs, int fd, int cc, int tf)
5881 {
5882     int cond;
5883     TCGv_i32 t0 = tcg_temp_new_i32();
5884     int l1 = gen_new_label();
5885
5886     if (tf)
5887         cond = TCG_COND_EQ;
5888     else
5889         cond = TCG_COND_NE;
5890
5891     tcg_gen_andi_i32(t0, fpu_fcr31, get_fp_bit(cc));
5892     tcg_gen_brcondi_i32(cond, t0, 0, l1);
5893     gen_load_fpr32(t0, fs);
5894     gen_store_fpr32(t0, fd);
5895     gen_set_label(l1);
5896     tcg_temp_free_i32(t0);
5897 }
5898
5899 static inline void gen_movcf_d (DisasContext *ctx, int fs, int fd, int cc, int tf)
5900 {
5901     int cond;
5902     TCGv_i32 t0 = tcg_temp_new_i32();
5903     TCGv_i64 fp0;
5904     int l1 = gen_new_label();
5905
5906     if (tf)
5907         cond = TCG_COND_EQ;
5908     else
5909         cond = TCG_COND_NE;
5910
5911     tcg_gen_andi_i32(t0, fpu_fcr31, get_fp_bit(cc));
5912     tcg_gen_brcondi_i32(cond, t0, 0, l1);
5913     tcg_temp_free_i32(t0);
5914     fp0 = tcg_temp_new_i64();
5915     gen_load_fpr64(ctx, fp0, fs);
5916     gen_store_fpr64(ctx, fp0, fd);
5917     tcg_temp_free_i64(fp0);
5918     gen_set_label(l1);
5919 }
5920
5921 static inline void gen_movcf_ps (int fs, int fd, int cc, int tf)
5922 {
5923     int cond;
5924     TCGv_i32 t0 = tcg_temp_new_i32();
5925     int l1 = gen_new_label();
5926     int l2 = gen_new_label();
5927
5928     if (tf)
5929         cond = TCG_COND_EQ;
5930     else
5931         cond = TCG_COND_NE;
5932
5933     tcg_gen_andi_i32(t0, fpu_fcr31, get_fp_bit(cc));
5934     tcg_gen_brcondi_i32(cond, t0, 0, l1);
5935     gen_load_fpr32(t0, fs);
5936     gen_store_fpr32(t0, fd);
5937     gen_set_label(l1);
5938
5939     tcg_gen_andi_i32(t0, fpu_fcr31, get_fp_bit(cc+1));
5940     tcg_gen_brcondi_i32(cond, t0, 0, l2);
5941     gen_load_fpr32h(t0, fs);
5942     gen_store_fpr32h(t0, fd);
5943     tcg_temp_free_i32(t0);
5944     gen_set_label(l2);
5945 }
5946
5947
5948 static void gen_farith (DisasContext *ctx, uint32_t op1,
5949                         int ft, int fs, int fd, int cc)
5950 {
5951     const char *opn = "farith";
5952     const char *condnames[] = {
5953             "c.f",
5954             "c.un",
5955             "c.eq",
5956             "c.ueq",
5957             "c.olt",
5958             "c.ult",
5959             "c.ole",
5960             "c.ule",
5961             "c.sf",
5962             "c.ngle",
5963             "c.seq",
5964             "c.ngl",
5965             "c.lt",
5966             "c.nge",
5967             "c.le",
5968             "c.ngt",
5969     };
5970     const char *condnames_abs[] = {
5971             "cabs.f",
5972             "cabs.un",
5973             "cabs.eq",
5974             "cabs.ueq",
5975             "cabs.olt",
5976             "cabs.ult",
5977             "cabs.ole",
5978             "cabs.ule",
5979             "cabs.sf",
5980             "cabs.ngle",
5981             "cabs.seq",
5982             "cabs.ngl",
5983             "cabs.lt",
5984             "cabs.nge",
5985             "cabs.le",
5986             "cabs.ngt",
5987     };
5988     enum { BINOP, CMPOP, OTHEROP } optype = OTHEROP;
5989     uint32_t func = ctx->opcode & 0x3f;
5990
5991     switch (ctx->opcode & FOP(0x3f, 0x1f)) {
5992     case FOP(0, 16):
5993         {
5994             TCGv_i32 fp0 = tcg_temp_new_i32();
5995             TCGv_i32 fp1 = tcg_temp_new_i32();
5996
5997             gen_load_fpr32(fp0, fs);
5998             gen_load_fpr32(fp1, ft);
5999             gen_helper_float_add_s(fp0, fp0, fp1);
6000             tcg_temp_free_i32(fp1);
6001             gen_store_fpr32(fp0, fd);
6002             tcg_temp_free_i32(fp0);
6003         }
6004         opn = "add.s";
6005         optype = BINOP;
6006         break;
6007     case FOP(1, 16):
6008         {
6009             TCGv_i32 fp0 = tcg_temp_new_i32();
6010             TCGv_i32 fp1 = tcg_temp_new_i32();
6011
6012             gen_load_fpr32(fp0, fs);
6013             gen_load_fpr32(fp1, ft);
6014             gen_helper_float_sub_s(fp0, fp0, fp1);
6015             tcg_temp_free_i32(fp1);
6016             gen_store_fpr32(fp0, fd);
6017             tcg_temp_free_i32(fp0);
6018         }
6019         opn = "sub.s";
6020         optype = BINOP;
6021         break;
6022     case FOP(2, 16):
6023         {
6024             TCGv_i32 fp0 = tcg_temp_new_i32();
6025             TCGv_i32 fp1 = tcg_temp_new_i32();
6026
6027             gen_load_fpr32(fp0, fs);
6028             gen_load_fpr32(fp1, ft);
6029             gen_helper_float_mul_s(fp0, fp0, fp1);
6030             tcg_temp_free_i32(fp1);
6031             gen_store_fpr32(fp0, fd);
6032             tcg_temp_free_i32(fp0);
6033         }
6034         opn = "mul.s";
6035         optype = BINOP;
6036         break;
6037     case FOP(3, 16):
6038         {
6039             TCGv_i32 fp0 = tcg_temp_new_i32();
6040             TCGv_i32 fp1 = tcg_temp_new_i32();
6041
6042             gen_load_fpr32(fp0, fs);
6043             gen_load_fpr32(fp1, ft);
6044             gen_helper_float_div_s(fp0, fp0, fp1);
6045             tcg_temp_free_i32(fp1);
6046             gen_store_fpr32(fp0, fd);
6047             tcg_temp_free_i32(fp0);
6048         }
6049         opn = "div.s";
6050         optype = BINOP;
6051         break;
6052     case FOP(4, 16):
6053         {
6054             TCGv_i32 fp0 = tcg_temp_new_i32();
6055
6056             gen_load_fpr32(fp0, fs);
6057             gen_helper_float_sqrt_s(fp0, fp0);
6058             gen_store_fpr32(fp0, fd);
6059             tcg_temp_free_i32(fp0);
6060         }
6061         opn = "sqrt.s";
6062         break;
6063     case FOP(5, 16):
6064         {
6065             TCGv_i32 fp0 = tcg_temp_new_i32();
6066
6067             gen_load_fpr32(fp0, fs);
6068             gen_helper_float_abs_s(fp0, fp0);
6069             gen_store_fpr32(fp0, fd);
6070             tcg_temp_free_i32(fp0);
6071         }
6072         opn = "abs.s";
6073         break;
6074     case FOP(6, 16):
6075         {
6076             TCGv_i32 fp0 = tcg_temp_new_i32();
6077
6078             gen_load_fpr32(fp0, fs);
6079             gen_store_fpr32(fp0, fd);
6080             tcg_temp_free_i32(fp0);
6081         }
6082         opn = "mov.s";
6083         break;
6084     case FOP(7, 16):
6085         {
6086             TCGv_i32 fp0 = tcg_temp_new_i32();
6087
6088             gen_load_fpr32(fp0, fs);
6089             gen_helper_float_chs_s(fp0, fp0);
6090             gen_store_fpr32(fp0, fd);
6091             tcg_temp_free_i32(fp0);
6092         }
6093         opn = "neg.s";
6094         break;
6095     case FOP(8, 16):
6096         check_cp1_64bitmode(ctx);
6097         {
6098             TCGv_i32 fp32 = tcg_temp_new_i32();
6099             TCGv_i64 fp64 = tcg_temp_new_i64();
6100
6101             gen_load_fpr32(fp32, fs);
6102             gen_helper_float_roundl_s(fp64, fp32);
6103             tcg_temp_free_i32(fp32);
6104             gen_store_fpr64(ctx, fp64, fd);
6105             tcg_temp_free_i64(fp64);
6106         }
6107         opn = "round.l.s";
6108         break;
6109     case FOP(9, 16):
6110         check_cp1_64bitmode(ctx);
6111         {
6112             TCGv_i32 fp32 = tcg_temp_new_i32();
6113             TCGv_i64 fp64 = tcg_temp_new_i64();
6114
6115             gen_load_fpr32(fp32, fs);
6116             gen_helper_float_truncl_s(fp64, fp32);
6117             tcg_temp_free_i32(fp32);
6118             gen_store_fpr64(ctx, fp64, fd);
6119             tcg_temp_free_i64(fp64);
6120         }
6121         opn = "trunc.l.s";
6122         break;
6123     case FOP(10, 16):
6124         check_cp1_64bitmode(ctx);
6125         {
6126             TCGv_i32 fp32 = tcg_temp_new_i32();
6127             TCGv_i64 fp64 = tcg_temp_new_i64();
6128
6129             gen_load_fpr32(fp32, fs);
6130             gen_helper_float_ceill_s(fp64, fp32);
6131             tcg_temp_free_i32(fp32);
6132             gen_store_fpr64(ctx, fp64, fd);
6133             tcg_temp_free_i64(fp64);
6134         }
6135         opn = "ceil.l.s";
6136         break;
6137     case FOP(11, 16):
6138         check_cp1_64bitmode(ctx);
6139         {
6140             TCGv_i32 fp32 = tcg_temp_new_i32();
6141             TCGv_i64 fp64 = tcg_temp_new_i64();
6142
6143             gen_load_fpr32(fp32, fs);
6144             gen_helper_float_floorl_s(fp64, fp32);
6145             tcg_temp_free_i32(fp32);
6146             gen_store_fpr64(ctx, fp64, fd);
6147             tcg_temp_free_i64(fp64);
6148         }
6149         opn = "floor.l.s";
6150         break;
6151     case FOP(12, 16):
6152         {
6153             TCGv_i32 fp0 = tcg_temp_new_i32();
6154
6155             gen_load_fpr32(fp0, fs);
6156             gen_helper_float_roundw_s(fp0, fp0);
6157             gen_store_fpr32(fp0, fd);
6158             tcg_temp_free_i32(fp0);
6159         }
6160         opn = "round.w.s";
6161         break;
6162     case FOP(13, 16):
6163         {
6164             TCGv_i32 fp0 = tcg_temp_new_i32();
6165
6166             gen_load_fpr32(fp0, fs);
6167             gen_helper_float_truncw_s(fp0, fp0);
6168             gen_store_fpr32(fp0, fd);
6169             tcg_temp_free_i32(fp0);
6170         }
6171         opn = "trunc.w.s";
6172         break;
6173     case FOP(14, 16):
6174         {
6175             TCGv_i32 fp0 = tcg_temp_new_i32();
6176
6177             gen_load_fpr32(fp0, fs);
6178             gen_helper_float_ceilw_s(fp0, fp0);
6179             gen_store_fpr32(fp0, fd);
6180             tcg_temp_free_i32(fp0);
6181         }
6182         opn = "ceil.w.s";
6183         break;
6184     case FOP(15, 16):
6185         {
6186             TCGv_i32 fp0 = tcg_temp_new_i32();
6187
6188             gen_load_fpr32(fp0, fs);
6189             gen_helper_float_floorw_s(fp0, fp0);
6190             gen_store_fpr32(fp0, fd);
6191             tcg_temp_free_i32(fp0);
6192         }
6193         opn = "floor.w.s";
6194         break;
6195     case FOP(17, 16):
6196         gen_movcf_s(fs, fd, (ft >> 2) & 0x7, ft & 0x1);
6197         opn = "movcf.s";
6198         break;
6199     case FOP(18, 16):
6200         {
6201             int l1 = gen_new_label();
6202             TCGv_i32 fp0;
6203
6204             if (ft != 0) {
6205                 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
6206             }
6207             fp0 = tcg_temp_new_i32();
6208             gen_load_fpr32(fp0, fs);
6209             gen_store_fpr32(fp0, fd);
6210             tcg_temp_free_i32(fp0);
6211             gen_set_label(l1);
6212         }
6213         opn = "movz.s";
6214         break;
6215     case FOP(19, 16):
6216         {
6217             int l1 = gen_new_label();
6218             TCGv_i32 fp0;
6219
6220             if (ft != 0) {
6221                 tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
6222                 fp0 = tcg_temp_new_i32();
6223                 gen_load_fpr32(fp0, fs);
6224                 gen_store_fpr32(fp0, fd);
6225                 tcg_temp_free_i32(fp0);
6226                 gen_set_label(l1);
6227             }
6228         }
6229         opn = "movn.s";
6230         break;
6231     case FOP(21, 16):
6232         check_cop1x(ctx);
6233         {
6234             TCGv_i32 fp0 = tcg_temp_new_i32();
6235
6236             gen_load_fpr32(fp0, fs);
6237             gen_helper_float_recip_s(fp0, fp0);
6238             gen_store_fpr32(fp0, fd);
6239             tcg_temp_free_i32(fp0);
6240         }
6241         opn = "recip.s";
6242         break;
6243     case FOP(22, 16):
6244         check_cop1x(ctx);
6245         {
6246             TCGv_i32 fp0 = tcg_temp_new_i32();
6247
6248             gen_load_fpr32(fp0, fs);
6249             gen_helper_float_rsqrt_s(fp0, fp0);
6250             gen_store_fpr32(fp0, fd);
6251             tcg_temp_free_i32(fp0);
6252         }
6253         opn = "rsqrt.s";
6254         break;
6255     case FOP(28, 16):
6256         check_cp1_64bitmode(ctx);
6257         {
6258             TCGv_i32 fp0 = tcg_temp_new_i32();
6259             TCGv_i32 fp1 = tcg_temp_new_i32();
6260
6261             gen_load_fpr32(fp0, fs);
6262             gen_load_fpr32(fp1, fd);
6263             gen_helper_float_recip2_s(fp0, fp0, fp1);
6264             tcg_temp_free_i32(fp1);
6265             gen_store_fpr32(fp0, fd);
6266             tcg_temp_free_i32(fp0);
6267         }
6268         opn = "recip2.s";
6269         break;
6270     case FOP(29, 16):
6271         check_cp1_64bitmode(ctx);
6272         {
6273             TCGv_i32 fp0 = tcg_temp_new_i32();
6274
6275             gen_load_fpr32(fp0, fs);
6276             gen_helper_float_recip1_s(fp0, fp0);
6277             gen_store_fpr32(fp0, fd);
6278             tcg_temp_free_i32(fp0);
6279         }
6280         opn = "recip1.s";
6281         break;
6282     case FOP(30, 16):
6283         check_cp1_64bitmode(ctx);
6284         {
6285             TCGv_i32 fp0 = tcg_temp_new_i32();
6286
6287             gen_load_fpr32(fp0, fs);
6288             gen_helper_float_rsqrt1_s(fp0, fp0);
6289             gen_store_fpr32(fp0, fd);
6290             tcg_temp_free_i32(fp0);
6291         }
6292         opn = "rsqrt1.s";
6293         break;
6294     case FOP(31, 16):
6295         check_cp1_64bitmode(ctx);
6296         {
6297             TCGv_i32 fp0 = tcg_temp_new_i32();
6298             TCGv_i32 fp1 = tcg_temp_new_i32();
6299
6300             gen_load_fpr32(fp0, fs);
6301             gen_load_fpr32(fp1, ft);
6302             gen_helper_float_rsqrt2_s(fp0, fp0, fp1);
6303             tcg_temp_free_i32(fp1);
6304             gen_store_fpr32(fp0, fd);
6305             tcg_temp_free_i32(fp0);
6306         }
6307         opn = "rsqrt2.s";
6308         break;
6309     case FOP(33, 16):
6310         check_cp1_registers(ctx, fd);
6311         {
6312             TCGv_i32 fp32 = tcg_temp_new_i32();
6313             TCGv_i64 fp64 = tcg_temp_new_i64();
6314
6315             gen_load_fpr32(fp32, fs);
6316             gen_helper_float_cvtd_s(fp64, fp32);
6317             tcg_temp_free_i32(fp32);
6318             gen_store_fpr64(ctx, fp64, fd);
6319             tcg_temp_free_i64(fp64);
6320         }
6321         opn = "cvt.d.s";
6322         break;
6323     case FOP(36, 16):
6324         {
6325             TCGv_i32 fp0 = tcg_temp_new_i32();
6326
6327             gen_load_fpr32(fp0, fs);
6328             gen_helper_float_cvtw_s(fp0, fp0);
6329             gen_store_fpr32(fp0, fd);
6330             tcg_temp_free_i32(fp0);
6331         }
6332         opn = "cvt.w.s";
6333         break;
6334     case FOP(37, 16):
6335         check_cp1_64bitmode(ctx);
6336         {
6337             TCGv_i32 fp32 = tcg_temp_new_i32();
6338             TCGv_i64 fp64 = tcg_temp_new_i64();
6339
6340             gen_load_fpr32(fp32, fs);
6341             gen_helper_float_cvtl_s(fp64, fp32);
6342             tcg_temp_free_i32(fp32);
6343             gen_store_fpr64(ctx, fp64, fd);
6344             tcg_temp_free_i64(fp64);
6345         }
6346         opn = "cvt.l.s";
6347         break;
6348     case FOP(38, 16):
6349         check_cp1_64bitmode(ctx);
6350         {
6351             TCGv_i64 fp64 = tcg_temp_new_i64();
6352             TCGv_i32 fp32_0 = tcg_temp_new_i32();
6353             TCGv_i32 fp32_1 = tcg_temp_new_i32();
6354
6355             gen_load_fpr32(fp32_0, fs);
6356             gen_load_fpr32(fp32_1, ft);
6357             tcg_gen_concat_i32_i64(fp64, fp32_0, fp32_1);
6358             tcg_temp_free_i32(fp32_1);
6359             tcg_temp_free_i32(fp32_0);
6360             gen_store_fpr64(ctx, fp64, fd);
6361             tcg_temp_free_i64(fp64);
6362         }
6363         opn = "cvt.ps.s";
6364         break;
6365     case FOP(48, 16):
6366     case FOP(49, 16):
6367     case FOP(50, 16):
6368     case FOP(51, 16):
6369     case FOP(52, 16):
6370     case FOP(53, 16):
6371     case FOP(54, 16):
6372     case FOP(55, 16):
6373     case FOP(56, 16):
6374     case FOP(57, 16):
6375     case FOP(58, 16):
6376     case FOP(59, 16):
6377     case FOP(60, 16):
6378     case FOP(61, 16):
6379     case FOP(62, 16):
6380     case FOP(63, 16):
6381         {
6382             TCGv_i32 fp0 = tcg_temp_new_i32();
6383             TCGv_i32 fp1 = tcg_temp_new_i32();
6384
6385             gen_load_fpr32(fp0, fs);
6386             gen_load_fpr32(fp1, ft);
6387             if (ctx->opcode & (1 << 6)) {
6388                 check_cop1x(ctx);
6389                 gen_cmpabs_s(func-48, fp0, fp1, cc);
6390                 opn = condnames_abs[func-48];
6391             } else {
6392                 gen_cmp_s(func-48, fp0, fp1, cc);
6393                 opn = condnames[func-48];
6394             }
6395             tcg_temp_free_i32(fp0);
6396             tcg_temp_free_i32(fp1);
6397         }
6398         break;
6399     case FOP(0, 17):
6400         check_cp1_registers(ctx, fs | ft | fd);
6401         {
6402             TCGv_i64 fp0 = tcg_temp_new_i64();
6403             TCGv_i64 fp1 = tcg_temp_new_i64();
6404
6405             gen_load_fpr64(ctx, fp0, fs);
6406             gen_load_fpr64(ctx, fp1, ft);
6407             gen_helper_float_add_d(fp0, fp0, fp1);
6408             tcg_temp_free_i64(fp1);
6409             gen_store_fpr64(ctx, fp0, fd);
6410             tcg_temp_free_i64(fp0);
6411         }
6412         opn = "add.d";
6413         optype = BINOP;
6414         break;
6415     case FOP(1, 17):
6416         check_cp1_registers(ctx, fs | ft | fd);
6417         {
6418             TCGv_i64 fp0 = tcg_temp_new_i64();
6419             TCGv_i64 fp1 = tcg_temp_new_i64();
6420
6421             gen_load_fpr64(ctx, fp0, fs);
6422             gen_load_fpr64(ctx, fp1, ft);
6423             gen_helper_float_sub_d(fp0, fp0, fp1);
6424             tcg_temp_free_i64(fp1);
6425             gen_store_fpr64(ctx, fp0, fd);
6426             tcg_temp_free_i64(fp0);
6427         }
6428         opn = "sub.d";
6429         optype = BINOP;
6430         break;
6431     case FOP(2, 17):
6432         check_cp1_registers(ctx, fs | ft | fd);
6433         {
6434             TCGv_i64 fp0 = tcg_temp_new_i64();
6435             TCGv_i64 fp1 = tcg_temp_new_i64();
6436
6437             gen_load_fpr64(ctx, fp0, fs);
6438             gen_load_fpr64(ctx, fp1, ft);
6439             gen_helper_float_mul_d(fp0, fp0, fp1);
6440             tcg_temp_free_i64(fp1);
6441             gen_store_fpr64(ctx, fp0, fd);
6442             tcg_temp_free_i64(fp0);
6443         }
6444         opn = "mul.d";
6445         optype = BINOP;
6446         break;
6447     case FOP(3, 17):
6448         check_cp1_registers(ctx, fs | ft | fd);
6449         {
6450             TCGv_i64 fp0 = tcg_temp_new_i64();
6451             TCGv_i64 fp1 = tcg_temp_new_i64();
6452
6453             gen_load_fpr64(ctx, fp0, fs);
6454             gen_load_fpr64(ctx, fp1, ft);
6455             gen_helper_float_div_d(fp0, fp0, fp1);
6456             tcg_temp_free_i64(fp1);
6457             gen_store_fpr64(ctx, fp0, fd);
6458             tcg_temp_free_i64(fp0);
6459         }
6460         opn = "div.d";
6461         optype = BINOP;
6462         break;
6463     case FOP(4, 17):
6464         check_cp1_registers(ctx, fs | fd);
6465         {
6466             TCGv_i64 fp0 = tcg_temp_new_i64();
6467
6468             gen_load_fpr64(ctx, fp0, fs);
6469             gen_helper_float_sqrt_d(fp0, fp0);
6470             gen_store_fpr64(ctx, fp0, fd);
6471             tcg_temp_free_i64(fp0);
6472         }
6473         opn = "sqrt.d";
6474         break;
6475     case FOP(5, 17):
6476         check_cp1_registers(ctx, fs | fd);
6477         {
6478             TCGv_i64 fp0 = tcg_temp_new_i64();
6479
6480             gen_load_fpr64(ctx, fp0, fs);
6481             gen_helper_float_abs_d(fp0, fp0);
6482             gen_store_fpr64(ctx, fp0, fd);
6483             tcg_temp_free_i64(fp0);
6484         }
6485         opn = "abs.d";
6486         break;
6487     case FOP(6, 17):
6488         check_cp1_registers(ctx, fs | fd);
6489         {
6490             TCGv_i64 fp0 = tcg_temp_new_i64();
6491
6492             gen_load_fpr64(ctx, fp0, fs);
6493             gen_store_fpr64(ctx, fp0, fd);
6494             tcg_temp_free_i64(fp0);
6495         }
6496         opn = "mov.d";
6497         break;
6498     case FOP(7, 17):
6499         check_cp1_registers(ctx, fs | fd);
6500         {
6501             TCGv_i64 fp0 = tcg_temp_new_i64();
6502
6503             gen_load_fpr64(ctx, fp0, fs);
6504             gen_helper_float_chs_d(fp0, fp0);
6505             gen_store_fpr64(ctx, fp0, fd);
6506             tcg_temp_free_i64(fp0);
6507         }
6508         opn = "neg.d";
6509         break;
6510     case FOP(8, 17):
6511         check_cp1_64bitmode(ctx);
6512         {
6513             TCGv_i64 fp0 = tcg_temp_new_i64();
6514
6515             gen_load_fpr64(ctx, fp0, fs);
6516             gen_helper_float_roundl_d(fp0, fp0);
6517             gen_store_fpr64(ctx, fp0, fd);
6518             tcg_temp_free_i64(fp0);
6519         }
6520         opn = "round.l.d";
6521         break;
6522     case FOP(9, 17):
6523         check_cp1_64bitmode(ctx);
6524         {
6525             TCGv_i64 fp0 = tcg_temp_new_i64();
6526
6527             gen_load_fpr64(ctx, fp0, fs);
6528             gen_helper_float_truncl_d(fp0, fp0);
6529             gen_store_fpr64(ctx, fp0, fd);
6530             tcg_temp_free_i64(fp0);
6531         }
6532         opn = "trunc.l.d";
6533         break;
6534     case FOP(10, 17):
6535         check_cp1_64bitmode(ctx);
6536         {
6537             TCGv_i64 fp0 = tcg_temp_new_i64();
6538
6539             gen_load_fpr64(ctx, fp0, fs);
6540             gen_helper_float_ceill_d(fp0, fp0);
6541             gen_store_fpr64(ctx, fp0, fd);
6542             tcg_temp_free_i64(fp0);
6543         }
6544         opn = "ceil.l.d";
6545         break;
6546     case FOP(11, 17):
6547         check_cp1_64bitmode(ctx);
6548         {
6549             TCGv_i64 fp0 = tcg_temp_new_i64();
6550
6551             gen_load_fpr64(ctx, fp0, fs);
6552             gen_helper_float_floorl_d(fp0, fp0);
6553             gen_store_fpr64(ctx, fp0, fd);
6554             tcg_temp_free_i64(fp0);
6555         }
6556         opn = "floor.l.d";
6557         break;
6558     case FOP(12, 17):
6559         check_cp1_registers(ctx, fs);
6560         {
6561             TCGv_i32 fp32 = tcg_temp_new_i32();
6562             TCGv_i64 fp64 = tcg_temp_new_i64();
6563
6564             gen_load_fpr64(ctx, fp64, fs);
6565             gen_helper_float_roundw_d(fp32, fp64);
6566             tcg_temp_free_i64(fp64);
6567             gen_store_fpr32(fp32, fd);
6568             tcg_temp_free_i32(fp32);
6569         }
6570         opn = "round.w.d";
6571         break;
6572     case FOP(13, 17):
6573         check_cp1_registers(ctx, fs);
6574         {
6575             TCGv_i32 fp32 = tcg_temp_new_i32();
6576             TCGv_i64 fp64 = tcg_temp_new_i64();
6577
6578             gen_load_fpr64(ctx, fp64, fs);
6579             gen_helper_float_truncw_d(fp32, fp64);
6580             tcg_temp_free_i64(fp64);
6581             gen_store_fpr32(fp32, fd);
6582             tcg_temp_free_i32(fp32);
6583         }
6584         opn = "trunc.w.d";
6585         break;
6586     case FOP(14, 17):
6587         check_cp1_registers(ctx, fs);
6588         {
6589             TCGv_i32 fp32 = tcg_temp_new_i32();
6590             TCGv_i64 fp64 = tcg_temp_new_i64();
6591
6592             gen_load_fpr64(ctx, fp64, fs);
6593             gen_helper_float_ceilw_d(fp32, fp64);
6594             tcg_temp_free_i64(fp64);
6595             gen_store_fpr32(fp32, fd);
6596             tcg_temp_free_i32(fp32);
6597         }
6598         opn = "ceil.w.d";
6599         break;
6600     case FOP(15, 17):
6601         check_cp1_registers(ctx, fs);
6602         {
6603             TCGv_i32 fp32 = tcg_temp_new_i32();
6604             TCGv_i64 fp64 = tcg_temp_new_i64();
6605
6606             gen_load_fpr64(ctx, fp64, fs);
6607             gen_helper_float_floorw_d(fp32, fp64);
6608             tcg_temp_free_i64(fp64);
6609             gen_store_fpr32(fp32, fd);
6610             tcg_temp_free_i32(fp32);
6611         }
6612         opn = "floor.w.d";
6613         break;
6614     case FOP(17, 17):
6615         gen_movcf_d(ctx, fs, fd, (ft >> 2) & 0x7, ft & 0x1);
6616         opn = "movcf.d";
6617         break;
6618     case FOP(18, 17):
6619         {
6620             int l1 = gen_new_label();
6621             TCGv_i64 fp0;
6622
6623             if (ft != 0) {
6624                 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
6625             }
6626             fp0 = tcg_temp_new_i64();
6627             gen_load_fpr64(ctx, fp0, fs);
6628             gen_store_fpr64(ctx, fp0, fd);
6629             tcg_temp_free_i64(fp0);
6630             gen_set_label(l1);
6631         }
6632         opn = "movz.d";
6633         break;
6634     case FOP(19, 17):
6635         {
6636             int l1 = gen_new_label();
6637             TCGv_i64 fp0;
6638
6639             if (ft != 0) {
6640                 tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
6641                 fp0 = tcg_temp_new_i64();
6642                 gen_load_fpr64(ctx, fp0, fs);
6643                 gen_store_fpr64(ctx, fp0, fd);
6644                 tcg_temp_free_i64(fp0);
6645                 gen_set_label(l1);
6646             }
6647         }
6648         opn = "movn.d";
6649         break;
6650     case FOP(21, 17):
6651         check_cp1_64bitmode(ctx);
6652         {
6653             TCGv_i64 fp0 = tcg_temp_new_i64();
6654
6655             gen_load_fpr64(ctx, fp0, fs);
6656             gen_helper_float_recip_d(fp0, fp0);
6657             gen_store_fpr64(ctx, fp0, fd);
6658             tcg_temp_free_i64(fp0);
6659         }
6660         opn = "recip.d";
6661         break;
6662     case FOP(22, 17):
6663         check_cp1_64bitmode(ctx);
6664         {
6665             TCGv_i64 fp0 = tcg_temp_new_i64();
6666
6667             gen_load_fpr64(ctx, fp0, fs);
6668             gen_helper_float_rsqrt_d(fp0, fp0);
6669             gen_store_fpr64(ctx, fp0, fd);
6670             tcg_temp_free_i64(fp0);
6671         }
6672         opn = "rsqrt.d";
6673         break;
6674     case FOP(28, 17):
6675         check_cp1_64bitmode(ctx);
6676         {
6677             TCGv_i64 fp0 = tcg_temp_new_i64();
6678             TCGv_i64 fp1 = tcg_temp_new_i64();
6679
6680             gen_load_fpr64(ctx, fp0, fs);
6681             gen_load_fpr64(ctx, fp1, ft);
6682             gen_helper_float_recip2_d(fp0, fp0, fp1);
6683             tcg_temp_free_i64(fp1);
6684             gen_store_fpr64(ctx, fp0, fd);
6685             tcg_temp_free_i64(fp0);
6686         }
6687         opn = "recip2.d";
6688         break;
6689     case FOP(29, 17):
6690         check_cp1_64bitmode(ctx);
6691         {
6692             TCGv_i64 fp0 = tcg_temp_new_i64();
6693
6694             gen_load_fpr64(ctx, fp0, fs);
6695             gen_helper_float_recip1_d(fp0, fp0);
6696             gen_store_fpr64(ctx, fp0, fd);
6697             tcg_temp_free_i64(fp0);
6698         }
6699         opn = "recip1.d";
6700         break;
6701     case FOP(30, 17):
6702         check_cp1_64bitmode(ctx);
6703         {
6704             TCGv_i64 fp0 = tcg_temp_new_i64();
6705
6706             gen_load_fpr64(ctx, fp0, fs);
6707             gen_helper_float_rsqrt1_d(fp0, fp0);
6708             gen_store_fpr64(ctx, fp0, fd);
6709             tcg_temp_free_i64(fp0);
6710         }
6711         opn = "rsqrt1.d";
6712         break;
6713     case FOP(31, 17):
6714         check_cp1_64bitmode(ctx);
6715         {
6716             TCGv_i64 fp0 = tcg_temp_new_i64();
6717             TCGv_i64 fp1 = tcg_temp_new_i64();
6718
6719             gen_load_fpr64(ctx, fp0, fs);
6720             gen_load_fpr64(ctx, fp1, ft);
6721             gen_helper_float_rsqrt2_d(fp0, fp0, fp1);
6722             tcg_temp_free_i64(fp1);
6723             gen_store_fpr64(ctx, fp0, fd);
6724             tcg_temp_free_i64(fp0);
6725         }
6726         opn = "rsqrt2.d";
6727         break;
6728     case FOP(48, 17):
6729     case FOP(49, 17):
6730     case FOP(50, 17):
6731     case FOP(51, 17):
6732     case FOP(52, 17):
6733     case FOP(53, 17):
6734     case FOP(54, 17):
6735     case FOP(55, 17):
6736     case FOP(56, 17):
6737     case FOP(57, 17):
6738     case FOP(58, 17):
6739     case FOP(59, 17):
6740     case FOP(60, 17):
6741     case FOP(61, 17):
6742     case FOP(62, 17):
6743     case FOP(63, 17):
6744         {
6745             TCGv_i64 fp0 = tcg_temp_new_i64();
6746             TCGv_i64 fp1 = tcg_temp_new_i64();
6747
6748             gen_load_fpr64(ctx, fp0, fs);
6749             gen_load_fpr64(ctx, fp1, ft);
6750             if (ctx->opcode & (1 << 6)) {
6751                 check_cop1x(ctx);
6752                 check_cp1_registers(ctx, fs | ft);
6753                 gen_cmpabs_d(func-48, fp0, fp1, cc);
6754                 opn = condnames_abs[func-48];
6755             } else {
6756                 check_cp1_registers(ctx, fs | ft);
6757                 gen_cmp_d(func-48, fp0, fp1, cc);
6758                 opn = condnames[func-48];
6759             }
6760             tcg_temp_free_i64(fp0);
6761             tcg_temp_free_i64(fp1);
6762         }
6763         break;
6764     case FOP(32, 17):
6765         check_cp1_registers(ctx, fs);
6766         {
6767             TCGv_i32 fp32 = tcg_temp_new_i32();
6768             TCGv_i64 fp64 = tcg_temp_new_i64();
6769
6770             gen_load_fpr64(ctx, fp64, fs);
6771             gen_helper_float_cvts_d(fp32, fp64);
6772             tcg_temp_free_i64(fp64);
6773             gen_store_fpr32(fp32, fd);
6774             tcg_temp_free_i32(fp32);
6775         }
6776         opn = "cvt.s.d";
6777         break;
6778     case FOP(36, 17):
6779         check_cp1_registers(ctx, fs);
6780         {
6781             TCGv_i32 fp32 = tcg_temp_new_i32();
6782             TCGv_i64 fp64 = tcg_temp_new_i64();
6783
6784             gen_load_fpr64(ctx, fp64, fs);
6785             gen_helper_float_cvtw_d(fp32, fp64);
6786             tcg_temp_free_i64(fp64);
6787             gen_store_fpr32(fp32, fd);
6788             tcg_temp_free_i32(fp32);
6789         }
6790         opn = "cvt.w.d";
6791         break;
6792     case FOP(37, 17):
6793         check_cp1_64bitmode(ctx);
6794         {
6795             TCGv_i64 fp0 = tcg_temp_new_i64();
6796
6797             gen_load_fpr64(ctx, fp0, fs);
6798             gen_helper_float_cvtl_d(fp0, fp0);
6799             gen_store_fpr64(ctx, fp0, fd);
6800             tcg_temp_free_i64(fp0);
6801         }
6802         opn = "cvt.l.d";
6803         break;
6804     case FOP(32, 20):
6805         {
6806             TCGv_i32 fp0 = tcg_temp_new_i32();
6807
6808             gen_load_fpr32(fp0, fs);
6809             gen_helper_float_cvts_w(fp0, fp0);
6810             gen_store_fpr32(fp0, fd);
6811             tcg_temp_free_i32(fp0);
6812         }
6813         opn = "cvt.s.w";
6814         break;
6815     case FOP(33, 20):
6816         check_cp1_registers(ctx, fd);
6817         {
6818             TCGv_i32 fp32 = tcg_temp_new_i32();
6819             TCGv_i64 fp64 = tcg_temp_new_i64();
6820
6821             gen_load_fpr32(fp32, fs);
6822             gen_helper_float_cvtd_w(fp64, fp32);
6823             tcg_temp_free_i32(fp32);
6824             gen_store_fpr64(ctx, fp64, fd);
6825             tcg_temp_free_i64(fp64);
6826         }
6827         opn = "cvt.d.w";
6828         break;
6829     case FOP(32, 21):
6830         check_cp1_64bitmode(ctx);
6831         {
6832             TCGv_i32 fp32 = tcg_temp_new_i32();
6833             TCGv_i64 fp64 = tcg_temp_new_i64();
6834
6835             gen_load_fpr64(ctx, fp64, fs);
6836             gen_helper_float_cvts_l(fp32, fp64);
6837             tcg_temp_free_i64(fp64);
6838             gen_store_fpr32(fp32, fd);
6839             tcg_temp_free_i32(fp32);
6840         }
6841         opn = "cvt.s.l";
6842         break;
6843     case FOP(33, 21):
6844         check_cp1_64bitmode(ctx);
6845         {
6846             TCGv_i64 fp0 = tcg_temp_new_i64();
6847
6848             gen_load_fpr64(ctx, fp0, fs);
6849             gen_helper_float_cvtd_l(fp0, fp0);
6850             gen_store_fpr64(ctx, fp0, fd);
6851             tcg_temp_free_i64(fp0);
6852         }
6853         opn = "cvt.d.l";
6854         break;
6855     case FOP(38, 20):
6856         check_cp1_64bitmode(ctx);
6857         {
6858             TCGv_i64 fp0 = tcg_temp_new_i64();
6859
6860             gen_load_fpr64(ctx, fp0, fs);
6861             gen_helper_float_cvtps_pw(fp0, fp0);
6862             gen_store_fpr64(ctx, fp0, fd);
6863             tcg_temp_free_i64(fp0);
6864         }
6865         opn = "cvt.ps.pw";
6866         break;
6867     case FOP(0, 22):
6868         check_cp1_64bitmode(ctx);
6869         {
6870             TCGv_i64 fp0 = tcg_temp_new_i64();
6871             TCGv_i64 fp1 = tcg_temp_new_i64();
6872
6873             gen_load_fpr64(ctx, fp0, fs);
6874             gen_load_fpr64(ctx, fp1, ft);
6875             gen_helper_float_add_ps(fp0, fp0, fp1);
6876             tcg_temp_free_i64(fp1);
6877             gen_store_fpr64(ctx, fp0, fd);
6878             tcg_temp_free_i64(fp0);
6879         }
6880         opn = "add.ps";
6881         break;
6882     case FOP(1, 22):
6883         check_cp1_64bitmode(ctx);
6884         {
6885             TCGv_i64 fp0 = tcg_temp_new_i64();
6886             TCGv_i64 fp1 = tcg_temp_new_i64();
6887
6888             gen_load_fpr64(ctx, fp0, fs);
6889             gen_load_fpr64(ctx, fp1, ft);
6890             gen_helper_float_sub_ps(fp0, fp0, fp1);
6891             tcg_temp_free_i64(fp1);
6892             gen_store_fpr64(ctx, fp0, fd);
6893             tcg_temp_free_i64(fp0);
6894         }
6895         opn = "sub.ps";
6896         break;
6897     case FOP(2, 22):
6898         check_cp1_64bitmode(ctx);
6899         {
6900             TCGv_i64 fp0 = tcg_temp_new_i64();
6901             TCGv_i64 fp1 = tcg_temp_new_i64();
6902
6903             gen_load_fpr64(ctx, fp0, fs);
6904             gen_load_fpr64(ctx, fp1, ft);
6905             gen_helper_float_mul_ps(fp0, fp0, fp1);
6906             tcg_temp_free_i64(fp1);
6907             gen_store_fpr64(ctx, fp0, fd);
6908             tcg_temp_free_i64(fp0);
6909         }
6910         opn = "mul.ps";
6911         break;
6912     case FOP(5, 22):
6913         check_cp1_64bitmode(ctx);
6914         {
6915             TCGv_i64 fp0 = tcg_temp_new_i64();
6916
6917             gen_load_fpr64(ctx, fp0, fs);
6918             gen_helper_float_abs_ps(fp0, fp0);
6919             gen_store_fpr64(ctx, fp0, fd);
6920             tcg_temp_free_i64(fp0);
6921         }
6922         opn = "abs.ps";
6923         break;
6924     case FOP(6, 22):
6925         check_cp1_64bitmode(ctx);
6926         {
6927             TCGv_i64 fp0 = tcg_temp_new_i64();
6928
6929             gen_load_fpr64(ctx, fp0, fs);
6930             gen_store_fpr64(ctx, fp0, fd);
6931             tcg_temp_free_i64(fp0);
6932         }
6933         opn = "mov.ps";
6934         break;
6935     case FOP(7, 22):
6936         check_cp1_64bitmode(ctx);
6937         {
6938             TCGv_i64 fp0 = tcg_temp_new_i64();
6939
6940             gen_load_fpr64(ctx, fp0, fs);
6941             gen_helper_float_chs_ps(fp0, fp0);
6942             gen_store_fpr64(ctx, fp0, fd);
6943             tcg_temp_free_i64(fp0);
6944         }
6945         opn = "neg.ps";
6946         break;
6947     case FOP(17, 22):
6948         check_cp1_64bitmode(ctx);
6949         gen_movcf_ps(fs, fd, (ft >> 2) & 0x7, ft & 0x1);
6950         opn = "movcf.ps";
6951         break;
6952     case FOP(18, 22):
6953         check_cp1_64bitmode(ctx);
6954         {
6955             int l1 = gen_new_label();
6956             TCGv_i64 fp0;
6957
6958             if (ft != 0)
6959                 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
6960             fp0 = tcg_temp_new_i64();
6961             gen_load_fpr64(ctx, fp0, fs);
6962             gen_store_fpr64(ctx, fp0, fd);
6963             tcg_temp_free_i64(fp0);
6964             gen_set_label(l1);
6965         }
6966         opn = "movz.ps";
6967         break;
6968     case FOP(19, 22):
6969         check_cp1_64bitmode(ctx);
6970         {
6971             int l1 = gen_new_label();
6972             TCGv_i64 fp0;
6973
6974             if (ft != 0) {
6975                 tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
6976                 fp0 = tcg_temp_new_i64();
6977                 gen_load_fpr64(ctx, fp0, fs);
6978                 gen_store_fpr64(ctx, fp0, fd);
6979                 tcg_temp_free_i64(fp0);
6980                 gen_set_label(l1);
6981             }
6982         }
6983         opn = "movn.ps";
6984         break;
6985     case FOP(24, 22):
6986         check_cp1_64bitmode(ctx);
6987         {
6988             TCGv_i64 fp0 = tcg_temp_new_i64();
6989             TCGv_i64 fp1 = tcg_temp_new_i64();
6990
6991             gen_load_fpr64(ctx, fp0, ft);
6992             gen_load_fpr64(ctx, fp1, fs);
6993             gen_helper_float_addr_ps(fp0, fp0, fp1);
6994             tcg_temp_free_i64(fp1);
6995             gen_store_fpr64(ctx, fp0, fd);
6996             tcg_temp_free_i64(fp0);
6997         }
6998         opn = "addr.ps";
6999         break;
7000     case FOP(26, 22):
7001         check_cp1_64bitmode(ctx);
7002         {
7003             TCGv_i64 fp0 = tcg_temp_new_i64();
7004             TCGv_i64 fp1 = tcg_temp_new_i64();
7005
7006             gen_load_fpr64(ctx, fp0, ft);
7007             gen_load_fpr64(ctx, fp1, fs);
7008             gen_helper_float_mulr_ps(fp0, fp0, fp1);
7009             tcg_temp_free_i64(fp1);
7010             gen_store_fpr64(ctx, fp0, fd);
7011             tcg_temp_free_i64(fp0);
7012         }
7013         opn = "mulr.ps";
7014         break;
7015     case FOP(28, 22):
7016         check_cp1_64bitmode(ctx);
7017         {
7018             TCGv_i64 fp0 = tcg_temp_new_i64();
7019             TCGv_i64 fp1 = tcg_temp_new_i64();
7020
7021             gen_load_fpr64(ctx, fp0, fs);
7022             gen_load_fpr64(ctx, fp1, fd);
7023             gen_helper_float_recip2_ps(fp0, fp0, fp1);
7024             tcg_temp_free_i64(fp1);
7025             gen_store_fpr64(ctx, fp0, fd);
7026             tcg_temp_free_i64(fp0);
7027         }
7028         opn = "recip2.ps";
7029         break;
7030     case FOP(29, 22):
7031         check_cp1_64bitmode(ctx);
7032         {
7033             TCGv_i64 fp0 = tcg_temp_new_i64();
7034
7035             gen_load_fpr64(ctx, fp0, fs);
7036             gen_helper_float_recip1_ps(fp0, fp0);
7037             gen_store_fpr64(ctx, fp0, fd);
7038             tcg_temp_free_i64(fp0);
7039         }
7040         opn = "recip1.ps";
7041         break;
7042     case FOP(30, 22):
7043         check_cp1_64bitmode(ctx);
7044         {
7045             TCGv_i64 fp0 = tcg_temp_new_i64();
7046
7047             gen_load_fpr64(ctx, fp0, fs);
7048             gen_helper_float_rsqrt1_ps(fp0, fp0);
7049             gen_store_fpr64(ctx, fp0, fd);
7050             tcg_temp_free_i64(fp0);
7051         }
7052         opn = "rsqrt1.ps";
7053         break;
7054     case FOP(31, 22):
7055         check_cp1_64bitmode(ctx);
7056         {
7057             TCGv_i64 fp0 = tcg_temp_new_i64();
7058             TCGv_i64 fp1 = tcg_temp_new_i64();
7059
7060             gen_load_fpr64(ctx, fp0, fs);
7061             gen_load_fpr64(ctx, fp1, ft);
7062             gen_helper_float_rsqrt2_ps(fp0, fp0, fp1);
7063             tcg_temp_free_i64(fp1);
7064             gen_store_fpr64(ctx, fp0, fd);
7065             tcg_temp_free_i64(fp0);
7066         }
7067         opn = "rsqrt2.ps";
7068         break;
7069     case FOP(32, 22):
7070         check_cp1_64bitmode(ctx);
7071         {
7072             TCGv_i32 fp0 = tcg_temp_new_i32();
7073
7074             gen_load_fpr32h(fp0, fs);
7075             gen_helper_float_cvts_pu(fp0, fp0);
7076             gen_store_fpr32(fp0, fd);
7077             tcg_temp_free_i32(fp0);
7078         }
7079         opn = "cvt.s.pu";
7080         break;
7081     case FOP(36, 22):
7082         check_cp1_64bitmode(ctx);
7083         {
7084             TCGv_i64 fp0 = tcg_temp_new_i64();
7085
7086             gen_load_fpr64(ctx, fp0, fs);
7087             gen_helper_float_cvtpw_ps(fp0, fp0);
7088             gen_store_fpr64(ctx, fp0, fd);
7089             tcg_temp_free_i64(fp0);
7090         }
7091         opn = "cvt.pw.ps";
7092         break;
7093     case FOP(40, 22):
7094         check_cp1_64bitmode(ctx);
7095         {
7096             TCGv_i32 fp0 = tcg_temp_new_i32();
7097
7098             gen_load_fpr32(fp0, fs);
7099             gen_helper_float_cvts_pl(fp0, fp0);
7100             gen_store_fpr32(fp0, fd);
7101             tcg_temp_free_i32(fp0);
7102         }
7103         opn = "cvt.s.pl";
7104         break;
7105     case FOP(44, 22):
7106         check_cp1_64bitmode(ctx);
7107         {
7108             TCGv_i32 fp0 = tcg_temp_new_i32();
7109             TCGv_i32 fp1 = tcg_temp_new_i32();
7110
7111             gen_load_fpr32(fp0, fs);
7112             gen_load_fpr32(fp1, ft);
7113             gen_store_fpr32h(fp0, fd);
7114             gen_store_fpr32(fp1, fd);
7115             tcg_temp_free_i32(fp0);
7116             tcg_temp_free_i32(fp1);
7117         }
7118         opn = "pll.ps";
7119         break;
7120     case FOP(45, 22):
7121         check_cp1_64bitmode(ctx);
7122         {
7123             TCGv_i32 fp0 = tcg_temp_new_i32();
7124             TCGv_i32 fp1 = tcg_temp_new_i32();
7125
7126             gen_load_fpr32(fp0, fs);
7127             gen_load_fpr32h(fp1, ft);
7128             gen_store_fpr32(fp1, fd);
7129             gen_store_fpr32h(fp0, fd);
7130             tcg_temp_free_i32(fp0);
7131             tcg_temp_free_i32(fp1);
7132         }
7133         opn = "plu.ps";
7134         break;
7135     case FOP(46, 22):
7136         check_cp1_64bitmode(ctx);
7137         {
7138             TCGv_i32 fp0 = tcg_temp_new_i32();
7139             TCGv_i32 fp1 = tcg_temp_new_i32();
7140
7141             gen_load_fpr32h(fp0, fs);
7142             gen_load_fpr32(fp1, ft);
7143             gen_store_fpr32(fp1, fd);
7144             gen_store_fpr32h(fp0, fd);
7145             tcg_temp_free_i32(fp0);
7146             tcg_temp_free_i32(fp1);
7147         }
7148         opn = "pul.ps";
7149         break;
7150     case FOP(47, 22):
7151         check_cp1_64bitmode(ctx);
7152         {
7153             TCGv_i32 fp0 = tcg_temp_new_i32();
7154             TCGv_i32 fp1 = tcg_temp_new_i32();
7155
7156             gen_load_fpr32h(fp0, fs);
7157             gen_load_fpr32h(fp1, ft);
7158             gen_store_fpr32(fp1, fd);
7159             gen_store_fpr32h(fp0, fd);
7160             tcg_temp_free_i32(fp0);
7161             tcg_temp_free_i32(fp1);
7162         }
7163         opn = "puu.ps";
7164         break;
7165     case FOP(48, 22):
7166     case FOP(49, 22):
7167     case FOP(50, 22):
7168     case FOP(51, 22):
7169     case FOP(52, 22):
7170     case FOP(53, 22):
7171     case FOP(54, 22):
7172     case FOP(55, 22):
7173     case FOP(56, 22):
7174     case FOP(57, 22):
7175     case FOP(58, 22):
7176     case FOP(59, 22):
7177     case FOP(60, 22):
7178     case FOP(61, 22):
7179     case FOP(62, 22):
7180     case FOP(63, 22):
7181         check_cp1_64bitmode(ctx);
7182         {
7183             TCGv_i64 fp0 = tcg_temp_new_i64();
7184             TCGv_i64 fp1 = tcg_temp_new_i64();
7185
7186             gen_load_fpr64(ctx, fp0, fs);
7187             gen_load_fpr64(ctx, fp1, ft);
7188             if (ctx->opcode & (1 << 6)) {
7189                 gen_cmpabs_ps(func-48, fp0, fp1, cc);
7190                 opn = condnames_abs[func-48];
7191             } else {
7192                 gen_cmp_ps(func-48, fp0, fp1, cc);
7193                 opn = condnames[func-48];
7194             }
7195             tcg_temp_free_i64(fp0);
7196             tcg_temp_free_i64(fp1);
7197         }
7198         break;
7199     default:
7200         MIPS_INVAL(opn);
7201         generate_exception (ctx, EXCP_RI);
7202         return;
7203     }
7204     switch (optype) {
7205     case BINOP:
7206         MIPS_DEBUG("%s %s, %s, %s", opn, fregnames[fd], fregnames[fs], fregnames[ft]);
7207         break;
7208     case CMPOP:
7209         MIPS_DEBUG("%s %s,%s", opn, fregnames[fs], fregnames[ft]);
7210         break;
7211     default:
7212         MIPS_DEBUG("%s %s,%s", opn, fregnames[fd], fregnames[fs]);
7213         break;
7214     }
7215 }
7216
7217 /* Coprocessor 3 (FPU) */
7218 static void gen_flt3_ldst (DisasContext *ctx, uint32_t opc,
7219                            int fd, int fs, int base, int index)
7220 {
7221     const char *opn = "extended float load/store";
7222     int store = 0;
7223     TCGv t0 = tcg_temp_new();
7224     TCGv t1 = tcg_temp_new();
7225
7226     if (base == 0) {
7227         gen_load_gpr(t0, index);
7228     } else if (index == 0) {
7229         gen_load_gpr(t0, base);
7230     } else {
7231         gen_load_gpr(t0, index);
7232         gen_op_addr_add(ctx, t0, cpu_gpr[base]);
7233     }
7234     /* Don't do NOP if destination is zero: we must perform the actual
7235        memory access. */
7236     save_cpu_state(ctx, 0);
7237     switch (opc) {
7238     case OPC_LWXC1:
7239         check_cop1x(ctx);
7240         {
7241             TCGv_i32 fp0 = tcg_temp_new_i32();
7242
7243             tcg_gen_qemu_ld32s(t1, t0, ctx->mem_idx);
7244             tcg_gen_trunc_tl_i32(fp0, t1);
7245             gen_store_fpr32(fp0, fd);
7246             tcg_temp_free_i32(fp0);
7247         }
7248         opn = "lwxc1";
7249         break;
7250     case OPC_LDXC1:
7251         check_cop1x(ctx);
7252         check_cp1_registers(ctx, fd);
7253         {
7254             TCGv_i64 fp0 = tcg_temp_new_i64();
7255
7256             tcg_gen_qemu_ld64(fp0, t0, ctx->mem_idx);
7257             gen_store_fpr64(ctx, fp0, fd);
7258             tcg_temp_free_i64(fp0);
7259         }
7260         opn = "ldxc1";
7261         break;
7262     case OPC_LUXC1:
7263         check_cp1_64bitmode(ctx);
7264         tcg_gen_andi_tl(t0, t0, ~0x7);
7265         {
7266             TCGv_i64 fp0 = tcg_temp_new_i64();
7267
7268             tcg_gen_qemu_ld64(fp0, t0, ctx->mem_idx);
7269             gen_store_fpr64(ctx, fp0, fd);
7270             tcg_temp_free_i64(fp0);
7271         }
7272         opn = "luxc1";
7273         break;
7274     case OPC_SWXC1:
7275         check_cop1x(ctx);
7276         {
7277             TCGv_i32 fp0 = tcg_temp_new_i32();
7278
7279             gen_load_fpr32(fp0, fs);
7280             tcg_gen_extu_i32_tl(t1, fp0);
7281             tcg_gen_qemu_st32(t1, t0, ctx->mem_idx);
7282             tcg_temp_free_i32(fp0);
7283         }
7284         opn = "swxc1";
7285         store = 1;
7286         break;
7287     case OPC_SDXC1:
7288         check_cop1x(ctx);
7289         check_cp1_registers(ctx, fs);
7290         {
7291             TCGv_i64 fp0 = tcg_temp_new_i64();
7292
7293             gen_load_fpr64(ctx, fp0, fs);
7294             tcg_gen_qemu_st64(fp0, t0, ctx->mem_idx);
7295             tcg_temp_free_i64(fp0);
7296         }
7297         opn = "sdxc1";
7298         store = 1;
7299         break;
7300     case OPC_SUXC1:
7301         check_cp1_64bitmode(ctx);
7302         tcg_gen_andi_tl(t0, t0, ~0x7);
7303         {
7304             TCGv_i64 fp0 = tcg_temp_new_i64();
7305
7306             gen_load_fpr64(ctx, fp0, fs);
7307             tcg_gen_qemu_st64(fp0, t0, ctx->mem_idx);
7308             tcg_temp_free_i64(fp0);
7309         }
7310         opn = "suxc1";
7311         store = 1;
7312         break;
7313     }
7314     tcg_temp_free(t0);
7315     tcg_temp_free(t1);
7316     MIPS_DEBUG("%s %s, %s(%s)", opn, fregnames[store ? fs : fd],
7317                regnames[index], regnames[base]);
7318 }
7319
7320 static void gen_flt3_arith (DisasContext *ctx, uint32_t opc,
7321                             int fd, int fr, int fs, int ft)
7322 {
7323     const char *opn = "flt3_arith";
7324
7325     switch (opc) {
7326     case OPC_ALNV_PS:
7327         check_cp1_64bitmode(ctx);
7328         {
7329             TCGv t0 = tcg_temp_local_new();
7330             TCGv_i32 fp = tcg_temp_new_i32();
7331             TCGv_i32 fph = tcg_temp_new_i32();
7332             int l1 = gen_new_label();
7333             int l2 = gen_new_label();
7334
7335             gen_load_gpr(t0, fr);
7336             tcg_gen_andi_tl(t0, t0, 0x7);
7337
7338             tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
7339             gen_load_fpr32(fp, fs);
7340             gen_load_fpr32h(fph, fs);
7341             gen_store_fpr32(fp, fd);
7342             gen_store_fpr32h(fph, fd);
7343             tcg_gen_br(l2);
7344             gen_set_label(l1);
7345             tcg_gen_brcondi_tl(TCG_COND_NE, t0, 4, l2);
7346             tcg_temp_free(t0);
7347 #ifdef TARGET_WORDS_BIGENDIAN
7348             gen_load_fpr32(fp, fs);
7349             gen_load_fpr32h(fph, ft);
7350             gen_store_fpr32h(fp, fd);
7351             gen_store_fpr32(fph, fd);
7352 #else
7353             gen_load_fpr32h(fph, fs);
7354             gen_load_fpr32(fp, ft);
7355             gen_store_fpr32(fph, fd);
7356             gen_store_fpr32h(fp, fd);
7357 #endif
7358             gen_set_label(l2);
7359             tcg_temp_free_i32(fp);
7360             tcg_temp_free_i32(fph);
7361         }
7362         opn = "alnv.ps";
7363         break;
7364     case OPC_MADD_S:
7365         check_cop1x(ctx);
7366         {
7367             TCGv_i32 fp0 = tcg_temp_new_i32();
7368             TCGv_i32 fp1 = tcg_temp_new_i32();
7369             TCGv_i32 fp2 = tcg_temp_new_i32();
7370
7371             gen_load_fpr32(fp0, fs);
7372             gen_load_fpr32(fp1, ft);
7373             gen_load_fpr32(fp2, fr);
7374             gen_helper_float_muladd_s(fp2, fp0, fp1, fp2);
7375             tcg_temp_free_i32(fp0);
7376             tcg_temp_free_i32(fp1);
7377             gen_store_fpr32(fp2, fd);
7378             tcg_temp_free_i32(fp2);
7379         }
7380         opn = "madd.s";
7381         break;
7382     case OPC_MADD_D:
7383         check_cop1x(ctx);
7384         check_cp1_registers(ctx, fd | fs | ft | fr);
7385         {
7386             TCGv_i64 fp0 = tcg_temp_new_i64();
7387             TCGv_i64 fp1 = tcg_temp_new_i64();
7388             TCGv_i64 fp2 = tcg_temp_new_i64();
7389
7390             gen_load_fpr64(ctx, fp0, fs);
7391             gen_load_fpr64(ctx, fp1, ft);
7392             gen_load_fpr64(ctx, fp2, fr);
7393             gen_helper_float_muladd_d(fp2, fp0, fp1, fp2);
7394             tcg_temp_free_i64(fp0);
7395             tcg_temp_free_i64(fp1);
7396             gen_store_fpr64(ctx, fp2, fd);
7397             tcg_temp_free_i64(fp2);
7398         }
7399         opn = "madd.d";
7400         break;
7401     case OPC_MADD_PS:
7402         check_cp1_64bitmode(ctx);
7403         {
7404             TCGv_i64 fp0 = tcg_temp_new_i64();
7405             TCGv_i64 fp1 = tcg_temp_new_i64();
7406             TCGv_i64 fp2 = tcg_temp_new_i64();
7407
7408             gen_load_fpr64(ctx, fp0, fs);
7409             gen_load_fpr64(ctx, fp1, ft);
7410             gen_load_fpr64(ctx, fp2, fr);
7411             gen_helper_float_muladd_ps(fp2, fp0, fp1, fp2);
7412             tcg_temp_free_i64(fp0);
7413             tcg_temp_free_i64(fp1);
7414             gen_store_fpr64(ctx, fp2, fd);
7415             tcg_temp_free_i64(fp2);
7416         }
7417         opn = "madd.ps";
7418         break;
7419     case OPC_MSUB_S:
7420         check_cop1x(ctx);
7421         {
7422             TCGv_i32 fp0 = tcg_temp_new_i32();
7423             TCGv_i32 fp1 = tcg_temp_new_i32();
7424             TCGv_i32 fp2 = tcg_temp_new_i32();
7425
7426             gen_load_fpr32(fp0, fs);
7427             gen_load_fpr32(fp1, ft);
7428             gen_load_fpr32(fp2, fr);
7429             gen_helper_float_mulsub_s(fp2, fp0, fp1, fp2);
7430             tcg_temp_free_i32(fp0);
7431             tcg_temp_free_i32(fp1);
7432             gen_store_fpr32(fp2, fd);
7433             tcg_temp_free_i32(fp2);
7434         }
7435         opn = "msub.s";
7436         break;
7437     case OPC_MSUB_D:
7438         check_cop1x(ctx);
7439         check_cp1_registers(ctx, fd | fs | ft | fr);
7440         {
7441             TCGv_i64 fp0 = tcg_temp_new_i64();
7442             TCGv_i64 fp1 = tcg_temp_new_i64();
7443             TCGv_i64 fp2 = tcg_temp_new_i64();
7444
7445             gen_load_fpr64(ctx, fp0, fs);
7446             gen_load_fpr64(ctx, fp1, ft);
7447             gen_load_fpr64(ctx, fp2, fr);
7448             gen_helper_float_mulsub_d(fp2, fp0, fp1, fp2);
7449             tcg_temp_free_i64(fp0);
7450             tcg_temp_free_i64(fp1);
7451             gen_store_fpr64(ctx, fp2, fd);
7452             tcg_temp_free_i64(fp2);
7453         }
7454         opn = "msub.d";
7455         break;
7456     case OPC_MSUB_PS:
7457         check_cp1_64bitmode(ctx);
7458         {
7459             TCGv_i64 fp0 = tcg_temp_new_i64();
7460             TCGv_i64 fp1 = tcg_temp_new_i64();
7461             TCGv_i64 fp2 = tcg_temp_new_i64();
7462
7463             gen_load_fpr64(ctx, fp0, fs);
7464             gen_load_fpr64(ctx, fp1, ft);
7465             gen_load_fpr64(ctx, fp2, fr);
7466             gen_helper_float_mulsub_ps(fp2, fp0, fp1, fp2);
7467             tcg_temp_free_i64(fp0);
7468             tcg_temp_free_i64(fp1);
7469             gen_store_fpr64(ctx, fp2, fd);
7470             tcg_temp_free_i64(fp2);
7471         }
7472         opn = "msub.ps";
7473         break;
7474     case OPC_NMADD_S:
7475         check_cop1x(ctx);
7476         {
7477             TCGv_i32 fp0 = tcg_temp_new_i32();
7478             TCGv_i32 fp1 = tcg_temp_new_i32();
7479             TCGv_i32 fp2 = tcg_temp_new_i32();
7480
7481             gen_load_fpr32(fp0, fs);
7482             gen_load_fpr32(fp1, ft);
7483             gen_load_fpr32(fp2, fr);
7484             gen_helper_float_nmuladd_s(fp2, fp0, fp1, fp2);
7485             tcg_temp_free_i32(fp0);
7486             tcg_temp_free_i32(fp1);
7487             gen_store_fpr32(fp2, fd);
7488             tcg_temp_free_i32(fp2);
7489         }
7490         opn = "nmadd.s";
7491         break;
7492     case OPC_NMADD_D:
7493         check_cop1x(ctx);
7494         check_cp1_registers(ctx, fd | fs | ft | fr);
7495         {
7496             TCGv_i64 fp0 = tcg_temp_new_i64();
7497             TCGv_i64 fp1 = tcg_temp_new_i64();
7498             TCGv_i64 fp2 = tcg_temp_new_i64();
7499
7500             gen_load_fpr64(ctx, fp0, fs);
7501             gen_load_fpr64(ctx, fp1, ft);
7502             gen_load_fpr64(ctx, fp2, fr);
7503             gen_helper_float_nmuladd_d(fp2, fp0, fp1, fp2);
7504             tcg_temp_free_i64(fp0);
7505             tcg_temp_free_i64(fp1);
7506             gen_store_fpr64(ctx, fp2, fd);
7507             tcg_temp_free_i64(fp2);
7508         }
7509         opn = "nmadd.d";
7510         break;
7511     case OPC_NMADD_PS:
7512         check_cp1_64bitmode(ctx);
7513         {
7514             TCGv_i64 fp0 = tcg_temp_new_i64();
7515             TCGv_i64 fp1 = tcg_temp_new_i64();
7516             TCGv_i64 fp2 = tcg_temp_new_i64();
7517
7518             gen_load_fpr64(ctx, fp0, fs);
7519             gen_load_fpr64(ctx, fp1, ft);
7520             gen_load_fpr64(ctx, fp2, fr);
7521             gen_helper_float_nmuladd_ps(fp2, fp0, fp1, fp2);
7522             tcg_temp_free_i64(fp0);
7523             tcg_temp_free_i64(fp1);
7524             gen_store_fpr64(ctx, fp2, fd);
7525             tcg_temp_free_i64(fp2);
7526         }
7527         opn = "nmadd.ps";
7528         break;
7529     case OPC_NMSUB_S:
7530         check_cop1x(ctx);
7531         {
7532             TCGv_i32 fp0 = tcg_temp_new_i32();
7533             TCGv_i32 fp1 = tcg_temp_new_i32();
7534             TCGv_i32 fp2 = tcg_temp_new_i32();
7535
7536             gen_load_fpr32(fp0, fs);
7537             gen_load_fpr32(fp1, ft);
7538             gen_load_fpr32(fp2, fr);
7539             gen_helper_float_nmulsub_s(fp2, fp0, fp1, fp2);
7540             tcg_temp_free_i32(fp0);
7541             tcg_temp_free_i32(fp1);
7542             gen_store_fpr32(fp2, fd);
7543             tcg_temp_free_i32(fp2);
7544         }
7545         opn = "nmsub.s";
7546         break;
7547     case OPC_NMSUB_D:
7548         check_cop1x(ctx);
7549         check_cp1_registers(ctx, fd | fs | ft | fr);
7550         {
7551             TCGv_i64 fp0 = tcg_temp_new_i64();
7552             TCGv_i64 fp1 = tcg_temp_new_i64();
7553             TCGv_i64 fp2 = tcg_temp_new_i64();
7554
7555             gen_load_fpr64(ctx, fp0, fs);
7556             gen_load_fpr64(ctx, fp1, ft);
7557             gen_load_fpr64(ctx, fp2, fr);
7558             gen_helper_float_nmulsub_d(fp2, fp0, fp1, fp2);
7559             tcg_temp_free_i64(fp0);
7560             tcg_temp_free_i64(fp1);
7561             gen_store_fpr64(ctx, fp2, fd);
7562             tcg_temp_free_i64(fp2);
7563         }
7564         opn = "nmsub.d";
7565         break;
7566     case OPC_NMSUB_PS:
7567         check_cp1_64bitmode(ctx);
7568         {
7569             TCGv_i64 fp0 = tcg_temp_new_i64();
7570             TCGv_i64 fp1 = tcg_temp_new_i64();
7571             TCGv_i64 fp2 = tcg_temp_new_i64();
7572
7573             gen_load_fpr64(ctx, fp0, fs);
7574             gen_load_fpr64(ctx, fp1, ft);
7575             gen_load_fpr64(ctx, fp2, fr);
7576             gen_helper_float_nmulsub_ps(fp2, fp0, fp1, fp2);
7577             tcg_temp_free_i64(fp0);
7578             tcg_temp_free_i64(fp1);
7579             gen_store_fpr64(ctx, fp2, fd);
7580             tcg_temp_free_i64(fp2);
7581         }
7582         opn = "nmsub.ps";
7583         break;
7584     default:
7585         MIPS_INVAL(opn);
7586         generate_exception (ctx, EXCP_RI);
7587         return;
7588     }
7589     MIPS_DEBUG("%s %s, %s, %s, %s", opn, fregnames[fd], fregnames[fr],
7590                fregnames[fs], fregnames[ft]);
7591 }
7592
7593 /* ISA extensions (ASEs) */
7594 /* MIPS16 extension to MIPS32 */
7595 /* SmartMIPS extension to MIPS32 */
7596
7597 #if defined(TARGET_MIPS64)
7598
7599 /* MDMX extension to MIPS64 */
7600
7601 #endif
7602
7603 static void decode_opc (CPUState *env, DisasContext *ctx)
7604 {
7605     int32_t offset;
7606     int rs, rt, rd, sa;
7607     uint32_t op, op1, op2;
7608     int16_t imm;
7609
7610     /* make sure instructions are on a word boundary */
7611     if (ctx->pc & 0x3) {
7612         env->CP0_BadVAddr = ctx->pc;
7613         generate_exception(ctx, EXCP_AdEL);
7614         return;
7615     }
7616
7617     /* Handle blikely not taken case */
7618     if ((ctx->hflags & MIPS_HFLAG_BMASK) == MIPS_HFLAG_BL) {
7619         int l1 = gen_new_label();
7620
7621         MIPS_DEBUG("blikely condition (" TARGET_FMT_lx ")", ctx->pc + 4);
7622         tcg_gen_brcondi_tl(TCG_COND_NE, bcond, 0, l1);
7623         tcg_gen_movi_i32(hflags, ctx->hflags & ~MIPS_HFLAG_BMASK);
7624         gen_goto_tb(ctx, 1, ctx->pc + 4);
7625         gen_set_label(l1);
7626     }
7627     op = MASK_OP_MAJOR(ctx->opcode);
7628     rs = (ctx->opcode >> 21) & 0x1f;
7629     rt = (ctx->opcode >> 16) & 0x1f;
7630     rd = (ctx->opcode >> 11) & 0x1f;
7631     sa = (ctx->opcode >> 6) & 0x1f;
7632     imm = (int16_t)ctx->opcode;
7633     switch (op) {
7634     case OPC_SPECIAL:
7635         op1 = MASK_SPECIAL(ctx->opcode);
7636         switch (op1) {
7637         case OPC_SLL:          /* Shift with immediate */
7638         case OPC_SRA:
7639         case OPC_SRL:
7640             gen_shift_imm(env, ctx, op1, rd, rt, sa);
7641             break;
7642         case OPC_MOVN:         /* Conditional move */
7643         case OPC_MOVZ:
7644             check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
7645             gen_cond_move(env, op1, rd, rs, rt);
7646             break;
7647         case OPC_ADD ... OPC_SUBU:
7648             gen_arith(env, ctx, op1, rd, rs, rt);
7649             break;
7650         case OPC_SLLV:         /* Shifts */
7651         case OPC_SRLV:
7652         case OPC_SRAV:
7653             gen_shift(env, ctx, op1, rd, rs, rt);
7654             break;
7655         case OPC_SLT:          /* Set on less than */
7656         case OPC_SLTU:
7657             gen_slt(env, op1, rd, rs, rt);
7658             break;
7659         case OPC_AND:          /* Logic*/
7660         case OPC_OR:
7661         case OPC_NOR:
7662         case OPC_XOR:
7663             gen_logic(env, op1, rd, rs, rt);
7664             break;
7665         case OPC_MULT ... OPC_DIVU:
7666             if (sa) {
7667                 check_insn(env, ctx, INSN_VR54XX);
7668                 op1 = MASK_MUL_VR54XX(ctx->opcode);
7669                 gen_mul_vr54xx(ctx, op1, rd, rs, rt);
7670             } else
7671                 gen_muldiv(ctx, op1, rs, rt);
7672             break;
7673         case OPC_JR ... OPC_JALR:
7674             gen_compute_branch(ctx, op1, rs, rd, sa);
7675             return;
7676         case OPC_TGE ... OPC_TEQ: /* Traps */
7677         case OPC_TNE:
7678             gen_trap(ctx, op1, rs, rt, -1);
7679             break;
7680         case OPC_MFHI:          /* Move from HI/LO */
7681         case OPC_MFLO:
7682             gen_HILO(ctx, op1, rd);
7683             break;
7684         case OPC_MTHI:
7685         case OPC_MTLO:          /* Move to HI/LO */
7686             gen_HILO(ctx, op1, rs);
7687             break;
7688         case OPC_PMON:          /* Pmon entry point, also R4010 selsl */
7689 #ifdef MIPS_STRICT_STANDARD
7690             MIPS_INVAL("PMON / selsl");
7691             generate_exception(ctx, EXCP_RI);
7692 #else
7693             gen_helper_0i(pmon, sa);
7694 #endif
7695             break;
7696         case OPC_SYSCALL:
7697             generate_exception(ctx, EXCP_SYSCALL);
7698             break;
7699         case OPC_BREAK:
7700             generate_exception(ctx, EXCP_BREAK);
7701             break;
7702         case OPC_SPIM:
7703 #ifdef MIPS_STRICT_STANDARD
7704             MIPS_INVAL("SPIM");
7705             generate_exception(ctx, EXCP_RI);
7706 #else
7707            /* Implemented as RI exception for now. */
7708             MIPS_INVAL("spim (unofficial)");
7709             generate_exception(ctx, EXCP_RI);
7710 #endif
7711             break;
7712         case OPC_SYNC:
7713             /* Treat as NOP. */
7714             break;
7715
7716         case OPC_MOVCI:
7717             check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
7718             if (env->CP0_Config1 & (1 << CP0C1_FP)) {
7719                 check_cp1_enabled(ctx);
7720                 gen_movci(ctx, rd, rs, (ctx->opcode >> 18) & 0x7,
7721                           (ctx->opcode >> 16) & 1);
7722             } else {
7723                 generate_exception_err(ctx, EXCP_CpU, 1);
7724             }
7725             break;
7726
7727 #if defined(TARGET_MIPS64)
7728        /* MIPS64 specific opcodes */
7729         case OPC_DSLL:
7730         case OPC_DSRA:
7731         case OPC_DSRL:
7732         case OPC_DSLL32:
7733         case OPC_DSRA32:
7734         case OPC_DSRL32:
7735             check_insn(env, ctx, ISA_MIPS3);
7736             check_mips_64(ctx);
7737             gen_shift_imm(env, ctx, op1, rd, rt, sa);
7738             break;
7739         case OPC_DADD ... OPC_DSUBU:
7740             check_insn(env, ctx, ISA_MIPS3);
7741             check_mips_64(ctx);
7742             gen_arith(env, ctx, op1, rd, rs, rt);
7743             break;
7744         case OPC_DSLLV:
7745         case OPC_DSRAV:
7746         case OPC_DSRLV:
7747             check_insn(env, ctx, ISA_MIPS3);
7748             check_mips_64(ctx);
7749             gen_shift(env, ctx, op1, rd, rs, rt);
7750             break;
7751         case OPC_DMULT ... OPC_DDIVU:
7752             check_insn(env, ctx, ISA_MIPS3);
7753             check_mips_64(ctx);
7754             gen_muldiv(ctx, op1, rs, rt);
7755             break;
7756 #endif
7757         default:            /* Invalid */
7758             MIPS_INVAL("special");
7759             generate_exception(ctx, EXCP_RI);
7760             break;
7761         }
7762         break;
7763     case OPC_SPECIAL2:
7764         op1 = MASK_SPECIAL2(ctx->opcode);
7765         switch (op1) {
7766         case OPC_MADD ... OPC_MADDU: /* Multiply and add/sub */
7767         case OPC_MSUB ... OPC_MSUBU:
7768             check_insn(env, ctx, ISA_MIPS32);
7769             gen_muldiv(ctx, op1, rs, rt);
7770             break;
7771         case OPC_MUL:
7772             gen_arith(env, ctx, op1, rd, rs, rt);
7773             break;
7774         case OPC_CLO:
7775         case OPC_CLZ:
7776             check_insn(env, ctx, ISA_MIPS32);
7777             gen_cl(ctx, op1, rd, rs);
7778             break;
7779         case OPC_SDBBP:
7780             /* XXX: not clear which exception should be raised
7781              *      when in debug mode...
7782              */
7783             check_insn(env, ctx, ISA_MIPS32);
7784             if (!(ctx->hflags & MIPS_HFLAG_DM)) {
7785                 generate_exception(ctx, EXCP_DBp);
7786             } else {
7787                 generate_exception(ctx, EXCP_DBp);
7788             }
7789             /* Treat as NOP. */
7790             break;
7791 #if defined(TARGET_MIPS64)
7792         case OPC_DCLO:
7793         case OPC_DCLZ:
7794             check_insn(env, ctx, ISA_MIPS64);
7795             check_mips_64(ctx);
7796             gen_cl(ctx, op1, rd, rs);
7797             break;
7798 #endif
7799         default:            /* Invalid */
7800             MIPS_INVAL("special2");
7801             generate_exception(ctx, EXCP_RI);
7802             break;
7803         }
7804         break;
7805     case OPC_SPECIAL3:
7806         op1 = MASK_SPECIAL3(ctx->opcode);
7807         switch (op1) {
7808         case OPC_EXT:
7809         case OPC_INS:
7810             check_insn(env, ctx, ISA_MIPS32R2);
7811             gen_bitops(ctx, op1, rt, rs, sa, rd);
7812             break;
7813         case OPC_BSHFL:
7814             check_insn(env, ctx, ISA_MIPS32R2);
7815             op2 = MASK_BSHFL(ctx->opcode);
7816             gen_bshfl(ctx, op2, rt, rd);
7817             break;
7818         case OPC_RDHWR:
7819             check_insn(env, ctx, ISA_MIPS32R2);
7820             {
7821                 TCGv t0 = tcg_temp_new();
7822
7823                 switch (rd) {
7824                 case 0:
7825                     save_cpu_state(ctx, 1);
7826                     gen_helper_rdhwr_cpunum(t0);
7827                     gen_store_gpr(t0, rt);
7828                     break;
7829                 case 1:
7830                     save_cpu_state(ctx, 1);
7831                     gen_helper_rdhwr_synci_step(t0);
7832                     gen_store_gpr(t0, rt);
7833                     break;
7834                 case 2:
7835                     save_cpu_state(ctx, 1);
7836                     gen_helper_rdhwr_cc(t0);
7837                     gen_store_gpr(t0, rt);
7838                     break;
7839                 case 3:
7840                     save_cpu_state(ctx, 1);
7841                     gen_helper_rdhwr_ccres(t0);
7842                     gen_store_gpr(t0, rt);
7843                     break;
7844                 case 29:
7845 #if defined(CONFIG_USER_ONLY)
7846                     tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUState, tls_value));
7847                     gen_store_gpr(t0, rt);
7848                     break;
7849 #else
7850                     /* XXX: Some CPUs implement this in hardware.
7851                        Not supported yet. */
7852 #endif
7853                 default:            /* Invalid */
7854                     MIPS_INVAL("rdhwr");
7855                     generate_exception(ctx, EXCP_RI);
7856                     break;
7857                 }
7858                 tcg_temp_free(t0);
7859             }
7860             break;
7861         case OPC_FORK:
7862             check_insn(env, ctx, ASE_MT);
7863             {
7864                 TCGv t0 = tcg_temp_new();
7865                 TCGv t1 = tcg_temp_new();
7866
7867                 gen_load_gpr(t0, rt);
7868                 gen_load_gpr(t1, rs);
7869                 gen_helper_fork(t0, t1);
7870                 tcg_temp_free(t0);
7871                 tcg_temp_free(t1);
7872             }
7873             break;
7874         case OPC_YIELD:
7875             check_insn(env, ctx, ASE_MT);
7876             {
7877                 TCGv t0 = tcg_temp_new();
7878
7879                 save_cpu_state(ctx, 1);
7880                 gen_load_gpr(t0, rs);
7881                 gen_helper_yield(t0, t0);
7882                 gen_store_gpr(t0, rd);
7883                 tcg_temp_free(t0);
7884             }
7885             break;
7886 #if defined(TARGET_MIPS64)
7887         case OPC_DEXTM ... OPC_DEXT:
7888         case OPC_DINSM ... OPC_DINS:
7889             check_insn(env, ctx, ISA_MIPS64R2);
7890             check_mips_64(ctx);
7891             gen_bitops(ctx, op1, rt, rs, sa, rd);
7892             break;
7893         case OPC_DBSHFL:
7894             check_insn(env, ctx, ISA_MIPS64R2);
7895             check_mips_64(ctx);
7896             op2 = MASK_DBSHFL(ctx->opcode);
7897             gen_bshfl(ctx, op2, rt, rd);
7898             break;
7899 #endif
7900         default:            /* Invalid */
7901             MIPS_INVAL("special3");
7902             generate_exception(ctx, EXCP_RI);
7903             break;
7904         }
7905         break;
7906     case OPC_REGIMM:
7907         op1 = MASK_REGIMM(ctx->opcode);
7908         switch (op1) {
7909         case OPC_BLTZ ... OPC_BGEZL: /* REGIMM branches */
7910         case OPC_BLTZAL ... OPC_BGEZALL:
7911             gen_compute_branch(ctx, op1, rs, -1, imm << 2);
7912             return;
7913         case OPC_TGEI ... OPC_TEQI: /* REGIMM traps */
7914         case OPC_TNEI:
7915             gen_trap(ctx, op1, rs, -1, imm);
7916             break;
7917         case OPC_SYNCI:
7918             check_insn(env, ctx, ISA_MIPS32R2);
7919             /* Treat as NOP. */
7920             break;
7921         default:            /* Invalid */
7922             MIPS_INVAL("regimm");
7923             generate_exception(ctx, EXCP_RI);
7924             break;
7925         }
7926         break;
7927     case OPC_CP0:
7928         check_cp0_enabled(ctx);
7929         op1 = MASK_CP0(ctx->opcode);
7930         switch (op1) {
7931         case OPC_MFC0:
7932         case OPC_MTC0:
7933         case OPC_MFTR:
7934         case OPC_MTTR:
7935 #if defined(TARGET_MIPS64)
7936         case OPC_DMFC0:
7937         case OPC_DMTC0:
7938 #endif
7939 #ifndef CONFIG_USER_ONLY
7940             gen_cp0(env, ctx, op1, rt, rd);
7941 #endif /* !CONFIG_USER_ONLY */
7942             break;
7943         case OPC_C0_FIRST ... OPC_C0_LAST:
7944 #ifndef CONFIG_USER_ONLY
7945             gen_cp0(env, ctx, MASK_C0(ctx->opcode), rt, rd);
7946 #endif /* !CONFIG_USER_ONLY */
7947             break;
7948         case OPC_MFMC0:
7949 #ifndef CONFIG_USER_ONLY
7950             {
7951                 TCGv t0 = tcg_temp_new();
7952
7953                 op2 = MASK_MFMC0(ctx->opcode);
7954                 switch (op2) {
7955                 case OPC_DMT:
7956                     check_insn(env, ctx, ASE_MT);
7957                     gen_helper_dmt(t0, t0);
7958                     gen_store_gpr(t0, rt);
7959                     break;
7960                 case OPC_EMT:
7961                     check_insn(env, ctx, ASE_MT);
7962                     gen_helper_emt(t0, t0);
7963                     gen_store_gpr(t0, rt);
7964                     break;
7965                 case OPC_DVPE:
7966                     check_insn(env, ctx, ASE_MT);
7967                     gen_helper_dvpe(t0, t0);
7968                     gen_store_gpr(t0, rt);
7969                     break;
7970                 case OPC_EVPE:
7971                     check_insn(env, ctx, ASE_MT);
7972                     gen_helper_evpe(t0, t0);
7973                     gen_store_gpr(t0, rt);
7974                     break;
7975                 case OPC_DI:
7976                     check_insn(env, ctx, ISA_MIPS32R2);
7977                     save_cpu_state(ctx, 1);
7978                     gen_helper_di(t0);
7979                     gen_store_gpr(t0, rt);
7980                     /* Stop translation as we may have switched the execution mode */
7981                     ctx->bstate = BS_STOP;
7982                     break;
7983                 case OPC_EI:
7984                     check_insn(env, ctx, ISA_MIPS32R2);
7985                     save_cpu_state(ctx, 1);
7986                     gen_helper_ei(t0);
7987                     gen_store_gpr(t0, rt);
7988                     /* Stop translation as we may have switched the execution mode */
7989                     ctx->bstate = BS_STOP;
7990                     break;
7991                 default:            /* Invalid */
7992                     MIPS_INVAL("mfmc0");
7993                     generate_exception(ctx, EXCP_RI);
7994                     break;
7995                 }
7996                 tcg_temp_free(t0);
7997             }
7998 #endif /* !CONFIG_USER_ONLY */
7999             break;
8000         case OPC_RDPGPR:
8001             check_insn(env, ctx, ISA_MIPS32R2);
8002             gen_load_srsgpr(rt, rd);
8003             break;
8004         case OPC_WRPGPR:
8005             check_insn(env, ctx, ISA_MIPS32R2);
8006             gen_store_srsgpr(rt, rd);
8007             break;
8008         default:
8009             MIPS_INVAL("cp0");
8010             generate_exception(ctx, EXCP_RI);
8011             break;
8012         }
8013         break;
8014     case OPC_ADDI: /* Arithmetic with immediate opcode */
8015     case OPC_ADDIU:
8016          gen_arith_imm(env, ctx, op, rt, rs, imm);
8017          break;
8018     case OPC_SLTI: /* Set on less than with immediate opcode */
8019     case OPC_SLTIU:
8020          gen_slt_imm(env, op, rt, rs, imm);
8021          break;
8022     case OPC_ANDI: /* Arithmetic with immediate opcode */
8023     case OPC_LUI:
8024     case OPC_ORI:
8025     case OPC_XORI:
8026          gen_logic_imm(env, op, rt, rs, imm);
8027          break;
8028     case OPC_J ... OPC_JAL: /* Jump */
8029          offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
8030          gen_compute_branch(ctx, op, rs, rt, offset);
8031          return;
8032     case OPC_BEQ ... OPC_BGTZ: /* Branch */
8033     case OPC_BEQL ... OPC_BGTZL:
8034          gen_compute_branch(ctx, op, rs, rt, imm << 2);
8035          return;
8036     case OPC_LB ... OPC_LWR: /* Load and stores */
8037     case OPC_SB ... OPC_SW:
8038     case OPC_SWR:
8039     case OPC_LL:
8040          gen_ldst(ctx, op, rt, rs, imm);
8041          break;
8042     case OPC_SC:
8043          gen_st_cond(ctx, op, rt, rs, imm);
8044          break;
8045     case OPC_CACHE:
8046         check_insn(env, ctx, ISA_MIPS3 | ISA_MIPS32);
8047         /* Treat as NOP. */
8048         break;
8049     case OPC_PREF:
8050         check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
8051         /* Treat as NOP. */
8052         break;
8053
8054     /* Floating point (COP1). */
8055     case OPC_LWC1:
8056     case OPC_LDC1:
8057     case OPC_SWC1:
8058     case OPC_SDC1:
8059         if (env->CP0_Config1 & (1 << CP0C1_FP)) {
8060             check_cp1_enabled(ctx);
8061             gen_flt_ldst(ctx, op, rt, rs, imm);
8062         } else {
8063             generate_exception_err(ctx, EXCP_CpU, 1);
8064         }
8065         break;
8066
8067     case OPC_CP1:
8068         if (env->CP0_Config1 & (1 << CP0C1_FP)) {
8069             check_cp1_enabled(ctx);
8070             op1 = MASK_CP1(ctx->opcode);
8071             switch (op1) {
8072             case OPC_MFHC1:
8073             case OPC_MTHC1:
8074                 check_insn(env, ctx, ISA_MIPS32R2);
8075             case OPC_MFC1:
8076             case OPC_CFC1:
8077             case OPC_MTC1:
8078             case OPC_CTC1:
8079                 gen_cp1(ctx, op1, rt, rd);
8080                 break;
8081 #if defined(TARGET_MIPS64)
8082             case OPC_DMFC1:
8083             case OPC_DMTC1:
8084                 check_insn(env, ctx, ISA_MIPS3);
8085                 gen_cp1(ctx, op1, rt, rd);
8086                 break;
8087 #endif
8088             case OPC_BC1ANY2:
8089             case OPC_BC1ANY4:
8090                 check_cop1x(ctx);
8091                 check_insn(env, ctx, ASE_MIPS3D);
8092                 /* fall through */
8093             case OPC_BC1:
8094                 gen_compute_branch1(env, ctx, MASK_BC1(ctx->opcode),
8095                                     (rt >> 2) & 0x7, imm << 2);
8096                 return;
8097             case OPC_S_FMT:
8098             case OPC_D_FMT:
8099             case OPC_W_FMT:
8100             case OPC_L_FMT:
8101             case OPC_PS_FMT:
8102                 gen_farith(ctx, MASK_CP1_FUNC(ctx->opcode), rt, rd, sa,
8103                            (imm >> 8) & 0x7);
8104                 break;
8105             default:
8106                 MIPS_INVAL("cp1");
8107                 generate_exception (ctx, EXCP_RI);
8108                 break;
8109             }
8110         } else {
8111             generate_exception_err(ctx, EXCP_CpU, 1);
8112         }
8113         break;
8114
8115     /* COP2.  */
8116     case OPC_LWC2:
8117     case OPC_LDC2:
8118     case OPC_SWC2:
8119     case OPC_SDC2:
8120     case OPC_CP2:
8121         /* COP2: Not implemented. */
8122         generate_exception_err(ctx, EXCP_CpU, 2);
8123         break;
8124
8125     case OPC_CP3:
8126         if (env->CP0_Config1 & (1 << CP0C1_FP)) {
8127             check_cp1_enabled(ctx);
8128             op1 = MASK_CP3(ctx->opcode);
8129             switch (op1) {
8130             case OPC_LWXC1:
8131             case OPC_LDXC1:
8132             case OPC_LUXC1:
8133             case OPC_SWXC1:
8134             case OPC_SDXC1:
8135             case OPC_SUXC1:
8136                 gen_flt3_ldst(ctx, op1, sa, rd, rs, rt);
8137                 break;
8138             case OPC_PREFX:
8139                 /* Treat as NOP. */
8140                 break;
8141             case OPC_ALNV_PS:
8142             case OPC_MADD_S:
8143             case OPC_MADD_D:
8144             case OPC_MADD_PS:
8145             case OPC_MSUB_S:
8146             case OPC_MSUB_D:
8147             case OPC_MSUB_PS:
8148             case OPC_NMADD_S:
8149             case OPC_NMADD_D:
8150             case OPC_NMADD_PS:
8151             case OPC_NMSUB_S:
8152             case OPC_NMSUB_D:
8153             case OPC_NMSUB_PS:
8154                 gen_flt3_arith(ctx, op1, sa, rs, rd, rt);
8155                 break;
8156             default:
8157                 MIPS_INVAL("cp3");
8158                 generate_exception (ctx, EXCP_RI);
8159                 break;
8160             }
8161         } else {
8162             generate_exception_err(ctx, EXCP_CpU, 1);
8163         }
8164         break;
8165
8166 #if defined(TARGET_MIPS64)
8167     /* MIPS64 opcodes */
8168     case OPC_LWU:
8169     case OPC_LDL ... OPC_LDR:
8170     case OPC_SDL ... OPC_SDR:
8171     case OPC_LLD:
8172     case OPC_LD:
8173     case OPC_SD:
8174         check_insn(env, ctx, ISA_MIPS3);
8175         check_mips_64(ctx);
8176         gen_ldst(ctx, op, rt, rs, imm);
8177         break;
8178     case OPC_SCD:
8179         check_insn(env, ctx, ISA_MIPS3);
8180         check_mips_64(ctx);
8181         gen_st_cond(ctx, op, rt, rs, imm);
8182         break;
8183     case OPC_DADDI:
8184     case OPC_DADDIU:
8185         check_insn(env, ctx, ISA_MIPS3);
8186         check_mips_64(ctx);
8187         gen_arith_imm(env, ctx, op, rt, rs, imm);
8188         break;
8189 #endif
8190     case OPC_JALX:
8191         check_insn(env, ctx, ASE_MIPS16);
8192         /* MIPS16: Not implemented. */
8193     case OPC_MDMX:
8194         check_insn(env, ctx, ASE_MDMX);
8195         /* MDMX: Not implemented. */
8196     default:            /* Invalid */
8197         MIPS_INVAL("major opcode");
8198         generate_exception(ctx, EXCP_RI);
8199         break;
8200     }
8201     if (ctx->hflags & MIPS_HFLAG_BMASK) {
8202         int hflags = ctx->hflags & MIPS_HFLAG_BMASK;
8203         /* Branches completion */
8204         ctx->hflags &= ~MIPS_HFLAG_BMASK;
8205         ctx->bstate = BS_BRANCH;
8206         save_cpu_state(ctx, 0);
8207         /* FIXME: Need to clear can_do_io.  */
8208         switch (hflags) {
8209         case MIPS_HFLAG_B:
8210             /* unconditional branch */
8211             MIPS_DEBUG("unconditional branch");
8212             gen_goto_tb(ctx, 0, ctx->btarget);
8213             break;
8214         case MIPS_HFLAG_BL:
8215             /* blikely taken case */
8216             MIPS_DEBUG("blikely branch taken");
8217             gen_goto_tb(ctx, 0, ctx->btarget);
8218             break;
8219         case MIPS_HFLAG_BC:
8220             /* Conditional branch */
8221             MIPS_DEBUG("conditional branch");
8222             {
8223                 int l1 = gen_new_label();
8224
8225                 tcg_gen_brcondi_tl(TCG_COND_NE, bcond, 0, l1);
8226                 gen_goto_tb(ctx, 1, ctx->pc + 4);
8227                 gen_set_label(l1);
8228                 gen_goto_tb(ctx, 0, ctx->btarget);
8229             }
8230             break;
8231         case MIPS_HFLAG_BR:
8232             /* unconditional branch to register */
8233             MIPS_DEBUG("branch to register");
8234             tcg_gen_mov_tl(cpu_PC, btarget);
8235             tcg_gen_exit_tb(0);
8236             break;
8237         default:
8238             MIPS_DEBUG("unknown branch");
8239             break;
8240         }
8241     }
8242 }
8243
8244 static inline void
8245 gen_intermediate_code_internal (CPUState *env, TranslationBlock *tb,
8246                                 int search_pc)
8247 {
8248     DisasContext ctx;
8249     target_ulong pc_start;
8250     uint16_t *gen_opc_end;
8251     CPUBreakpoint *bp;
8252     int j, lj = -1;
8253     int num_insns;
8254     int max_insns;
8255
8256     if (search_pc)
8257         qemu_log("search pc %d\n", search_pc);
8258
8259     pc_start = tb->pc;
8260     /* Leave some spare opc slots for branch handling. */
8261     gen_opc_end = gen_opc_buf + OPC_MAX_SIZE - 16;
8262     ctx.pc = pc_start;
8263     ctx.saved_pc = -1;
8264     ctx.tb = tb;
8265     ctx.bstate = BS_NONE;
8266     /* Restore delay slot state from the tb context.  */
8267     ctx.hflags = (uint32_t)tb->flags; /* FIXME: maybe use 64 bits here? */
8268     restore_cpu_state(env, &ctx);
8269 #ifdef CONFIG_USER_ONLY
8270         ctx.mem_idx = MIPS_HFLAG_UM;
8271 #else
8272         ctx.mem_idx = ctx.hflags & MIPS_HFLAG_KSU;
8273 #endif
8274     num_insns = 0;
8275     max_insns = tb->cflags & CF_COUNT_MASK;
8276     if (max_insns == 0)
8277         max_insns = CF_COUNT_MASK;
8278 #ifdef DEBUG_DISAS
8279     qemu_log_mask(CPU_LOG_TB_CPU, "------------------------------------------------\n");
8280     /* FIXME: This may print out stale hflags from env... */
8281     log_cpu_state_mask(CPU_LOG_TB_CPU, env, 0);
8282 #endif
8283     LOG_DISAS("\ntb %p idx %d hflags %04x\n", tb, ctx.mem_idx, ctx.hflags);
8284     gen_icount_start();
8285     while (ctx.bstate == BS_NONE) {
8286         if (unlikely(!TAILQ_EMPTY(&env->breakpoints))) {
8287             TAILQ_FOREACH(bp, &env->breakpoints, entry) {
8288                 if (bp->pc == ctx.pc) {
8289                     save_cpu_state(&ctx, 1);
8290                     ctx.bstate = BS_BRANCH;
8291                     gen_helper_0i(raise_exception, EXCP_DEBUG);
8292                     /* Include the breakpoint location or the tb won't
8293                      * be flushed when it must be.  */
8294                     ctx.pc += 4;
8295                     goto done_generating;
8296                 }
8297             }
8298         }
8299
8300         if (search_pc) {
8301             j = gen_opc_ptr - gen_opc_buf;
8302             if (lj < j) {
8303                 lj++;
8304                 while (lj < j)
8305                     gen_opc_instr_start[lj++] = 0;
8306             }
8307             gen_opc_pc[lj] = ctx.pc;
8308             gen_opc_hflags[lj] = ctx.hflags & MIPS_HFLAG_BMASK;
8309             gen_opc_instr_start[lj] = 1;
8310             gen_opc_icount[lj] = num_insns;
8311         }
8312         if (num_insns + 1 == max_insns && (tb->cflags & CF_LAST_IO))
8313             gen_io_start();
8314         ctx.opcode = ldl_code(ctx.pc);
8315         decode_opc(env, &ctx);
8316         ctx.pc += 4;
8317         num_insns++;
8318
8319         if (env->singlestep_enabled)
8320             break;
8321
8322         if ((ctx.pc & (TARGET_PAGE_SIZE - 1)) == 0)
8323             break;
8324
8325         if (gen_opc_ptr >= gen_opc_end)
8326             break;
8327
8328         if (num_insns >= max_insns)
8329             break;
8330
8331         if (singlestep)
8332             break;
8333     }
8334     if (tb->cflags & CF_LAST_IO)
8335         gen_io_end();
8336     if (env->singlestep_enabled) {
8337         save_cpu_state(&ctx, ctx.bstate == BS_NONE);
8338         gen_helper_0i(raise_exception, EXCP_DEBUG);
8339     } else {
8340         switch (ctx.bstate) {
8341         case BS_STOP:
8342             gen_helper_interrupt_restart();
8343             gen_goto_tb(&ctx, 0, ctx.pc);
8344             break;
8345         case BS_NONE:
8346             save_cpu_state(&ctx, 0);
8347             gen_goto_tb(&ctx, 0, ctx.pc);
8348             break;
8349         case BS_EXCP:
8350             gen_helper_interrupt_restart();
8351             tcg_gen_exit_tb(0);
8352             break;
8353         case BS_BRANCH:
8354         default:
8355             break;
8356         }
8357     }
8358 done_generating:
8359     gen_icount_end(tb, num_insns);
8360     *gen_opc_ptr = INDEX_op_end;
8361     if (search_pc) {
8362         j = gen_opc_ptr - gen_opc_buf;
8363         lj++;
8364         while (lj <= j)
8365             gen_opc_instr_start[lj++] = 0;
8366     } else {
8367         tb->size = ctx.pc - pc_start;
8368         tb->icount = num_insns;
8369     }
8370 #ifdef DEBUG_DISAS
8371     LOG_DISAS("\n");
8372     if (qemu_loglevel_mask(CPU_LOG_TB_IN_ASM)) {
8373         qemu_log("IN: %s\n", lookup_symbol(pc_start));
8374         log_target_disas(pc_start, ctx.pc - pc_start, 0);
8375         qemu_log("\n");
8376     }
8377     qemu_log_mask(CPU_LOG_TB_CPU, "---------------- %d %08x\n", ctx.bstate, ctx.hflags);
8378 #endif
8379 }
8380
8381 void gen_intermediate_code (CPUState *env, struct TranslationBlock *tb)
8382 {
8383     gen_intermediate_code_internal(env, tb, 0);
8384 }
8385
8386 void gen_intermediate_code_pc (CPUState *env, struct TranslationBlock *tb)
8387 {
8388     gen_intermediate_code_internal(env, tb, 1);
8389 }
8390
8391 static void fpu_dump_state(CPUState *env, FILE *f,
8392                            int (*fpu_fprintf)(FILE *f, const char *fmt, ...),
8393                            int flags)
8394 {
8395     int i;
8396     int is_fpu64 = !!(env->hflags & MIPS_HFLAG_F64);
8397
8398 #define printfpr(fp)                                                        \
8399     do {                                                                    \
8400         if (is_fpu64)                                                       \
8401             fpu_fprintf(f, "w:%08x d:%016lx fd:%13g fs:%13g psu: %13g\n",   \
8402                         (fp)->w[FP_ENDIAN_IDX], (fp)->d, (fp)->fd,          \
8403                         (fp)->fs[FP_ENDIAN_IDX], (fp)->fs[!FP_ENDIAN_IDX]); \
8404         else {                                                              \
8405             fpr_t tmp;                                                      \
8406             tmp.w[FP_ENDIAN_IDX] = (fp)->w[FP_ENDIAN_IDX];                  \
8407             tmp.w[!FP_ENDIAN_IDX] = ((fp) + 1)->w[FP_ENDIAN_IDX];           \
8408             fpu_fprintf(f, "w:%08x d:%016lx fd:%13g fs:%13g psu:%13g\n",    \
8409                         tmp.w[FP_ENDIAN_IDX], tmp.d, tmp.fd,                \
8410                         tmp.fs[FP_ENDIAN_IDX], tmp.fs[!FP_ENDIAN_IDX]);     \
8411         }                                                                   \
8412     } while(0)
8413
8414
8415     fpu_fprintf(f, "CP1 FCR0 0x%08x  FCR31 0x%08x  SR.FR %d  fp_status 0x%08x(0x%02x)\n",
8416                 env->active_fpu.fcr0, env->active_fpu.fcr31, is_fpu64, env->active_fpu.fp_status,
8417                 get_float_exception_flags(&env->active_fpu.fp_status));
8418     for (i = 0; i < 32; (is_fpu64) ? i++ : (i += 2)) {
8419         fpu_fprintf(f, "%3s: ", fregnames[i]);
8420         printfpr(&env->active_fpu.fpr[i]);
8421     }
8422
8423 #undef printfpr
8424 }
8425
8426 #if defined(TARGET_MIPS64) && defined(MIPS_DEBUG_SIGN_EXTENSIONS)
8427 /* Debug help: The architecture requires 32bit code to maintain proper
8428    sign-extended values on 64bit machines.  */
8429
8430 #define SIGN_EXT_P(val) ((((val) & ~0x7fffffff) == 0) || (((val) & ~0x7fffffff) == ~0x7fffffff))
8431
8432 static void
8433 cpu_mips_check_sign_extensions (CPUState *env, FILE *f,
8434                                 int (*cpu_fprintf)(FILE *f, const char *fmt, ...),
8435                                 int flags)
8436 {
8437     int i;
8438
8439     if (!SIGN_EXT_P(env->active_tc.PC))
8440         cpu_fprintf(f, "BROKEN: pc=0x" TARGET_FMT_lx "\n", env->active_tc.PC);
8441     if (!SIGN_EXT_P(env->active_tc.HI[0]))
8442         cpu_fprintf(f, "BROKEN: HI=0x" TARGET_FMT_lx "\n", env->active_tc.HI[0]);
8443     if (!SIGN_EXT_P(env->active_tc.LO[0]))
8444         cpu_fprintf(f, "BROKEN: LO=0x" TARGET_FMT_lx "\n", env->active_tc.LO[0]);
8445     if (!SIGN_EXT_P(env->btarget))
8446         cpu_fprintf(f, "BROKEN: btarget=0x" TARGET_FMT_lx "\n", env->btarget);
8447
8448     for (i = 0; i < 32; i++) {
8449         if (!SIGN_EXT_P(env->active_tc.gpr[i]))
8450             cpu_fprintf(f, "BROKEN: %s=0x" TARGET_FMT_lx "\n", regnames[i], env->active_tc.gpr[i]);
8451     }
8452
8453     if (!SIGN_EXT_P(env->CP0_EPC))
8454         cpu_fprintf(f, "BROKEN: EPC=0x" TARGET_FMT_lx "\n", env->CP0_EPC);
8455     if (!SIGN_EXT_P(env->CP0_LLAddr))
8456         cpu_fprintf(f, "BROKEN: LLAddr=0x" TARGET_FMT_lx "\n", env->CP0_LLAddr);
8457 }
8458 #endif
8459
8460 void cpu_dump_state (CPUState *env, FILE *f,
8461                      int (*cpu_fprintf)(FILE *f, const char *fmt, ...),
8462                      int flags)
8463 {
8464     int i;
8465
8466     cpu_fprintf(f, "pc=0x" TARGET_FMT_lx " HI=0x" TARGET_FMT_lx " LO=0x" TARGET_FMT_lx " ds %04x " TARGET_FMT_lx " %d\n",
8467                 env->active_tc.PC, env->active_tc.HI[0], env->active_tc.LO[0],
8468                 env->hflags, env->btarget, env->bcond);
8469     for (i = 0; i < 32; i++) {
8470         if ((i & 3) == 0)
8471             cpu_fprintf(f, "GPR%02d:", i);
8472         cpu_fprintf(f, " %s " TARGET_FMT_lx, regnames[i], env->active_tc.gpr[i]);
8473         if ((i & 3) == 3)
8474             cpu_fprintf(f, "\n");
8475     }
8476
8477     cpu_fprintf(f, "CP0 Status  0x%08x Cause   0x%08x EPC    0x" TARGET_FMT_lx "\n",
8478                 env->CP0_Status, env->CP0_Cause, env->CP0_EPC);
8479     cpu_fprintf(f, "    Config0 0x%08x Config1 0x%08x LLAddr 0x" TARGET_FMT_lx "\n",
8480                 env->CP0_Config0, env->CP0_Config1, env->CP0_LLAddr);
8481     if (env->hflags & MIPS_HFLAG_FPU)
8482         fpu_dump_state(env, f, cpu_fprintf, flags);
8483 #if defined(TARGET_MIPS64) && defined(MIPS_DEBUG_SIGN_EXTENSIONS)
8484     cpu_mips_check_sign_extensions(env, f, cpu_fprintf, flags);
8485 #endif
8486 }
8487
8488 static void mips_tcg_init(void)
8489 {
8490     int i;
8491     static int inited;
8492
8493     /* Initialize various static tables. */
8494     if (inited)
8495         return;
8496
8497     cpu_env = tcg_global_reg_new_ptr(TCG_AREG0, "env");
8498     for (i = 1; i < 32; i++)
8499         cpu_gpr[i] = tcg_global_mem_new(TCG_AREG0,
8500                                         offsetof(CPUState, active_tc.gpr[i]),
8501                                         regnames[i]);
8502     cpu_PC = tcg_global_mem_new(TCG_AREG0,
8503                                 offsetof(CPUState, active_tc.PC), "PC");
8504     for (i = 0; i < MIPS_DSP_ACC; i++) {
8505         cpu_HI[i] = tcg_global_mem_new(TCG_AREG0,
8506                                        offsetof(CPUState, active_tc.HI[i]),
8507                                        regnames_HI[i]);
8508         cpu_LO[i] = tcg_global_mem_new(TCG_AREG0,
8509                                        offsetof(CPUState, active_tc.LO[i]),
8510                                        regnames_LO[i]);
8511         cpu_ACX[i] = tcg_global_mem_new(TCG_AREG0,
8512                                         offsetof(CPUState, active_tc.ACX[i]),
8513                                         regnames_ACX[i]);
8514     }
8515     cpu_dspctrl = tcg_global_mem_new(TCG_AREG0,
8516                                      offsetof(CPUState, active_tc.DSPControl),
8517                                      "DSPControl");
8518     bcond = tcg_global_mem_new(TCG_AREG0,
8519                                offsetof(CPUState, bcond), "bcond");
8520     btarget = tcg_global_mem_new(TCG_AREG0,
8521                                  offsetof(CPUState, btarget), "btarget");
8522     hflags = tcg_global_mem_new_i32(TCG_AREG0,
8523                                     offsetof(CPUState, hflags), "hflags");
8524
8525     fpu_fcr0 = tcg_global_mem_new_i32(TCG_AREG0,
8526                                       offsetof(CPUState, active_fpu.fcr0),
8527                                       "fcr0");
8528     fpu_fcr31 = tcg_global_mem_new_i32(TCG_AREG0,
8529                                        offsetof(CPUState, active_fpu.fcr31),
8530                                        "fcr31");
8531
8532     /* register helpers */
8533 #define GEN_HELPER 2
8534 #include "helper.h"
8535
8536     inited = 1;
8537 }
8538
8539 #include "translate_init.c"
8540
8541 CPUMIPSState *cpu_mips_init (const char *cpu_model)
8542 {
8543     CPUMIPSState *env;
8544     const mips_def_t *def;
8545
8546     def = cpu_mips_find_by_name(cpu_model);
8547     if (!def)
8548         return NULL;
8549     env = qemu_mallocz(sizeof(CPUMIPSState));
8550     env->cpu_model = def;
8551
8552     cpu_exec_init(env);
8553     env->cpu_model_str = cpu_model;
8554     mips_tcg_init();
8555     cpu_reset(env);
8556     return env;
8557 }
8558
8559 void cpu_reset (CPUMIPSState *env)
8560 {
8561     if (qemu_loglevel_mask(CPU_LOG_RESET)) {
8562         qemu_log("CPU Reset (CPU %d)\n", env->cpu_index);
8563         log_cpu_state(env, 0);
8564     }
8565
8566     memset(env, 0, offsetof(CPUMIPSState, breakpoints));
8567
8568     tlb_flush(env, 1);
8569
8570     /* Minimal init */
8571 #if defined(CONFIG_USER_ONLY)
8572     env->hflags = MIPS_HFLAG_UM;
8573 #else
8574     if (env->hflags & MIPS_HFLAG_BMASK) {
8575         /* If the exception was raised from a delay slot,
8576            come back to the jump.  */
8577         env->CP0_ErrorEPC = env->active_tc.PC - 4;
8578     } else {
8579         env->CP0_ErrorEPC = env->active_tc.PC;
8580     }
8581     env->active_tc.PC = (int32_t)0xBFC00000;
8582     env->CP0_Wired = 0;
8583     /* SMP not implemented */
8584     env->CP0_EBase = 0x80000000;
8585     env->CP0_Status = (1 << CP0St_BEV) | (1 << CP0St_ERL);
8586     /* vectored interrupts not implemented, timer on int 7,
8587        no performance counters. */
8588     env->CP0_IntCtl = 0xe0000000;
8589     {
8590         int i;
8591
8592         for (i = 0; i < 7; i++) {
8593             env->CP0_WatchLo[i] = 0;
8594             env->CP0_WatchHi[i] = 0x80000000;
8595         }
8596         env->CP0_WatchLo[7] = 0;
8597         env->CP0_WatchHi[7] = 0;
8598     }
8599     /* Count register increments in debug mode, EJTAG version 1 */
8600     env->CP0_Debug = (1 << CP0DB_CNT) | (0x1 << CP0DB_VER);
8601     env->hflags = MIPS_HFLAG_CP0;
8602 #endif
8603     env->exception_index = EXCP_NONE;
8604     cpu_mips_register(env, env->cpu_model);
8605 }
8606
8607 void gen_pc_load(CPUState *env, TranslationBlock *tb,
8608                 unsigned long searched_pc, int pc_pos, void *puc)
8609 {
8610     env->active_tc.PC = gen_opc_pc[pc_pos];
8611     env->hflags &= ~MIPS_HFLAG_BMASK;
8612     env->hflags |= gen_opc_hflags[pc_pos];
8613 }