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