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