sync
[sdk/emulator/qemu.git] / 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  *  Copyright (c) 2009 CodeSourcery (MIPS16 and microMIPS support)
8  *
9  * This library is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU Lesser General Public
11  * License as published by the Free Software Foundation; either
12  * version 2 of the License, or (at your option) any later version.
13  *
14  * This library is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17  * Lesser General Public License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with this library; if not, see <http://www.gnu.org/licenses/>.
21  */
22
23 #include "cpu.h"
24 #include "disas.h"
25 #include "tcg-op.h"
26
27 #include "helper.h"
28 #define GEN_HELPER 1
29 #include "helper.h"
30
31 //#define MIPS_DEBUG_DISAS
32 //#define MIPS_DEBUG_SIGN_EXTENSIONS
33
34 /* MIPS major opcodes */
35 #define MASK_OP_MAJOR(op)  (op & (0x3F << 26))
36
37 enum {
38     /* indirect opcode tables */
39     OPC_SPECIAL  = (0x00 << 26),
40     OPC_REGIMM   = (0x01 << 26),
41     OPC_CP0      = (0x10 << 26),
42     OPC_CP1      = (0x11 << 26),
43     OPC_CP2      = (0x12 << 26),
44     OPC_CP3      = (0x13 << 26),
45     OPC_SPECIAL2 = (0x1C << 26),
46     OPC_SPECIAL3 = (0x1F << 26),
47     /* arithmetic with immediate */
48     OPC_ADDI     = (0x08 << 26),
49     OPC_ADDIU    = (0x09 << 26),
50     OPC_SLTI     = (0x0A << 26),
51     OPC_SLTIU    = (0x0B << 26),
52     /* logic with immediate */
53     OPC_ANDI     = (0x0C << 26),
54     OPC_ORI      = (0x0D << 26),
55     OPC_XORI     = (0x0E << 26),
56     OPC_LUI      = (0x0F << 26),
57     /* arithmetic with immediate */
58     OPC_DADDI    = (0x18 << 26),
59     OPC_DADDIU   = (0x19 << 26),
60     /* Jump and branches */
61     OPC_J        = (0x02 << 26),
62     OPC_JAL      = (0x03 << 26),
63     OPC_JALS     = OPC_JAL | 0x5,
64     OPC_BEQ      = (0x04 << 26),  /* Unconditional if rs = rt = 0 (B) */
65     OPC_BEQL     = (0x14 << 26),
66     OPC_BNE      = (0x05 << 26),
67     OPC_BNEL     = (0x15 << 26),
68     OPC_BLEZ     = (0x06 << 26),
69     OPC_BLEZL    = (0x16 << 26),
70     OPC_BGTZ     = (0x07 << 26),
71     OPC_BGTZL    = (0x17 << 26),
72     OPC_JALX     = (0x1D << 26),  /* MIPS 16 only */
73     OPC_JALXS    = OPC_JALX | 0x5,
74     /* Load and stores */
75     OPC_LDL      = (0x1A << 26),
76     OPC_LDR      = (0x1B << 26),
77     OPC_LB       = (0x20 << 26),
78     OPC_LH       = (0x21 << 26),
79     OPC_LWL      = (0x22 << 26),
80     OPC_LW       = (0x23 << 26),
81     OPC_LWPC     = OPC_LW | 0x5,
82     OPC_LBU      = (0x24 << 26),
83     OPC_LHU      = (0x25 << 26),
84     OPC_LWR      = (0x26 << 26),
85     OPC_LWU      = (0x27 << 26),
86     OPC_SB       = (0x28 << 26),
87     OPC_SH       = (0x29 << 26),
88     OPC_SWL      = (0x2A << 26),
89     OPC_SW       = (0x2B << 26),
90     OPC_SDL      = (0x2C << 26),
91     OPC_SDR      = (0x2D << 26),
92     OPC_SWR      = (0x2E << 26),
93     OPC_LL       = (0x30 << 26),
94     OPC_LLD      = (0x34 << 26),
95     OPC_LD       = (0x37 << 26),
96     OPC_LDPC     = OPC_LD | 0x5,
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_ROTR     = OPC_SRL | (1 << 21),
129     OPC_SRA      = 0x03 | OPC_SPECIAL,
130     OPC_SLLV     = 0x04 | OPC_SPECIAL,
131     OPC_SRLV     = 0x06 | OPC_SPECIAL, /* also ROTRV */
132     OPC_ROTRV    = OPC_SRLV | (1 << 6),
133     OPC_SRAV     = 0x07 | OPC_SPECIAL,
134     OPC_DSLLV    = 0x14 | OPC_SPECIAL,
135     OPC_DSRLV    = 0x16 | OPC_SPECIAL, /* also DROTRV */
136     OPC_DROTRV   = OPC_DSRLV | (1 << 6),
137     OPC_DSRAV    = 0x17 | OPC_SPECIAL,
138     OPC_DSLL     = 0x38 | OPC_SPECIAL,
139     OPC_DSRL     = 0x3A | OPC_SPECIAL, /* also DROTR */
140     OPC_DROTR    = OPC_DSRL | (1 << 21),
141     OPC_DSRA     = 0x3B | OPC_SPECIAL,
142     OPC_DSLL32   = 0x3C | OPC_SPECIAL,
143     OPC_DSRL32   = 0x3E | OPC_SPECIAL, /* also DROTR32 */
144     OPC_DROTR32  = OPC_DSRL32 | (1 << 21),
145     OPC_DSRA32   = 0x3F | OPC_SPECIAL,
146     /* Multiplication / division */
147     OPC_MULT     = 0x18 | OPC_SPECIAL,
148     OPC_MULTU    = 0x19 | OPC_SPECIAL,
149     OPC_DIV      = 0x1A | OPC_SPECIAL,
150     OPC_DIVU     = 0x1B | OPC_SPECIAL,
151     OPC_DMULT    = 0x1C | OPC_SPECIAL,
152     OPC_DMULTU   = 0x1D | OPC_SPECIAL,
153     OPC_DDIV     = 0x1E | OPC_SPECIAL,
154     OPC_DDIVU    = 0x1F | OPC_SPECIAL,
155     /* 2 registers arithmetic / logic */
156     OPC_ADD      = 0x20 | OPC_SPECIAL,
157     OPC_ADDU     = 0x21 | OPC_SPECIAL,
158     OPC_SUB      = 0x22 | OPC_SPECIAL,
159     OPC_SUBU     = 0x23 | OPC_SPECIAL,
160     OPC_AND      = 0x24 | OPC_SPECIAL,
161     OPC_OR       = 0x25 | OPC_SPECIAL,
162     OPC_XOR      = 0x26 | OPC_SPECIAL,
163     OPC_NOR      = 0x27 | OPC_SPECIAL,
164     OPC_SLT      = 0x2A | OPC_SPECIAL,
165     OPC_SLTU     = 0x2B | OPC_SPECIAL,
166     OPC_DADD     = 0x2C | OPC_SPECIAL,
167     OPC_DADDU    = 0x2D | OPC_SPECIAL,
168     OPC_DSUB     = 0x2E | OPC_SPECIAL,
169     OPC_DSUBU    = 0x2F | OPC_SPECIAL,
170     /* Jumps */
171     OPC_JR       = 0x08 | OPC_SPECIAL, /* Also JR.HB */
172     OPC_JALR     = 0x09 | OPC_SPECIAL, /* Also JALR.HB */
173     OPC_JALRC    = OPC_JALR | (0x5 << 6),
174     OPC_JALRS    = 0x10 | OPC_SPECIAL | (0x5 << 6),
175     /* Traps */
176     OPC_TGE      = 0x30 | OPC_SPECIAL,
177     OPC_TGEU     = 0x31 | OPC_SPECIAL,
178     OPC_TLT      = 0x32 | OPC_SPECIAL,
179     OPC_TLTU     = 0x33 | OPC_SPECIAL,
180     OPC_TEQ      = 0x34 | OPC_SPECIAL,
181     OPC_TNE      = 0x36 | OPC_SPECIAL,
182     /* HI / LO registers load & stores */
183     OPC_MFHI     = 0x10 | OPC_SPECIAL,
184     OPC_MTHI     = 0x11 | OPC_SPECIAL,
185     OPC_MFLO     = 0x12 | OPC_SPECIAL,
186     OPC_MTLO     = 0x13 | OPC_SPECIAL,
187     /* Conditional moves */
188     OPC_MOVZ     = 0x0A | OPC_SPECIAL,
189     OPC_MOVN     = 0x0B | OPC_SPECIAL,
190
191     OPC_MOVCI    = 0x01 | OPC_SPECIAL,
192
193     /* Special */
194     OPC_PMON     = 0x05 | OPC_SPECIAL, /* unofficial */
195     OPC_SYSCALL  = 0x0C | OPC_SPECIAL,
196     OPC_BREAK    = 0x0D | OPC_SPECIAL,
197     OPC_SPIM     = 0x0E | OPC_SPECIAL, /* unofficial */
198     OPC_SYNC     = 0x0F | OPC_SPECIAL,
199
200     OPC_SPECIAL15_RESERVED = 0x15 | OPC_SPECIAL,
201     OPC_SPECIAL28_RESERVED = 0x28 | OPC_SPECIAL,
202     OPC_SPECIAL29_RESERVED = 0x29 | OPC_SPECIAL,
203     OPC_SPECIAL35_RESERVED = 0x35 | OPC_SPECIAL,
204     OPC_SPECIAL37_RESERVED = 0x37 | OPC_SPECIAL,
205     OPC_SPECIAL39_RESERVED = 0x39 | OPC_SPECIAL,
206     OPC_SPECIAL3D_RESERVED = 0x3D | OPC_SPECIAL,
207 };
208
209 /* Multiplication variants of the vr54xx. */
210 #define MASK_MUL_VR54XX(op)   MASK_SPECIAL(op) | (op & (0x1F << 6))
211
212 enum {
213     OPC_VR54XX_MULS    = (0x03 << 6) | OPC_MULT,
214     OPC_VR54XX_MULSU   = (0x03 << 6) | OPC_MULTU,
215     OPC_VR54XX_MACC    = (0x05 << 6) | OPC_MULT,
216     OPC_VR54XX_MACCU   = (0x05 << 6) | OPC_MULTU,
217     OPC_VR54XX_MSAC    = (0x07 << 6) | OPC_MULT,
218     OPC_VR54XX_MSACU   = (0x07 << 6) | OPC_MULTU,
219     OPC_VR54XX_MULHI   = (0x09 << 6) | OPC_MULT,
220     OPC_VR54XX_MULHIU  = (0x09 << 6) | OPC_MULTU,
221     OPC_VR54XX_MULSHI  = (0x0B << 6) | OPC_MULT,
222     OPC_VR54XX_MULSHIU = (0x0B << 6) | OPC_MULTU,
223     OPC_VR54XX_MACCHI  = (0x0D << 6) | OPC_MULT,
224     OPC_VR54XX_MACCHIU = (0x0D << 6) | OPC_MULTU,
225     OPC_VR54XX_MSACHI  = (0x0F << 6) | OPC_MULT,
226     OPC_VR54XX_MSACHIU = (0x0F << 6) | OPC_MULTU,
227 };
228
229 /* REGIMM (rt field) opcodes */
230 #define MASK_REGIMM(op)    MASK_OP_MAJOR(op) | (op & (0x1F << 16))
231
232 enum {
233     OPC_BLTZ     = (0x00 << 16) | OPC_REGIMM,
234     OPC_BLTZL    = (0x02 << 16) | OPC_REGIMM,
235     OPC_BGEZ     = (0x01 << 16) | OPC_REGIMM,
236     OPC_BGEZL    = (0x03 << 16) | OPC_REGIMM,
237     OPC_BLTZAL   = (0x10 << 16) | OPC_REGIMM,
238     OPC_BLTZALS  = OPC_BLTZAL | 0x5, /* microMIPS */
239     OPC_BLTZALL  = (0x12 << 16) | OPC_REGIMM,
240     OPC_BGEZAL   = (0x11 << 16) | OPC_REGIMM,
241     OPC_BGEZALS  = OPC_BGEZAL | 0x5, /* microMIPS */
242     OPC_BGEZALL  = (0x13 << 16) | OPC_REGIMM,
243     OPC_TGEI     = (0x08 << 16) | OPC_REGIMM,
244     OPC_TGEIU    = (0x09 << 16) | OPC_REGIMM,
245     OPC_TLTI     = (0x0A << 16) | OPC_REGIMM,
246     OPC_TLTIU    = (0x0B << 16) | OPC_REGIMM,
247     OPC_TEQI     = (0x0C << 16) | OPC_REGIMM,
248     OPC_TNEI     = (0x0E << 16) | OPC_REGIMM,
249     OPC_SYNCI    = (0x1F << 16) | OPC_REGIMM,
250 };
251
252 /* Special2 opcodes */
253 #define MASK_SPECIAL2(op)  MASK_OP_MAJOR(op) | (op & 0x3F)
254
255 enum {
256     /* Multiply & xxx operations */
257     OPC_MADD     = 0x00 | OPC_SPECIAL2,
258     OPC_MADDU    = 0x01 | OPC_SPECIAL2,
259     OPC_MUL      = 0x02 | OPC_SPECIAL2,
260     OPC_MSUB     = 0x04 | OPC_SPECIAL2,
261     OPC_MSUBU    = 0x05 | OPC_SPECIAL2,
262     /* Loongson 2F */
263     OPC_MULT_G_2F   = 0x10 | OPC_SPECIAL2,
264     OPC_DMULT_G_2F  = 0x11 | OPC_SPECIAL2,
265     OPC_MULTU_G_2F  = 0x12 | OPC_SPECIAL2,
266     OPC_DMULTU_G_2F = 0x13 | OPC_SPECIAL2,
267     OPC_DIV_G_2F    = 0x14 | OPC_SPECIAL2,
268     OPC_DDIV_G_2F   = 0x15 | OPC_SPECIAL2,
269     OPC_DIVU_G_2F   = 0x16 | OPC_SPECIAL2,
270     OPC_DDIVU_G_2F  = 0x17 | OPC_SPECIAL2,
271     OPC_MOD_G_2F    = 0x1c | OPC_SPECIAL2,
272     OPC_DMOD_G_2F   = 0x1d | OPC_SPECIAL2,
273     OPC_MODU_G_2F   = 0x1e | OPC_SPECIAL2,
274     OPC_DMODU_G_2F  = 0x1f | OPC_SPECIAL2,
275     /* Misc */
276     OPC_CLZ      = 0x20 | OPC_SPECIAL2,
277     OPC_CLO      = 0x21 | OPC_SPECIAL2,
278     OPC_DCLZ     = 0x24 | OPC_SPECIAL2,
279     OPC_DCLO     = 0x25 | OPC_SPECIAL2,
280     /* Special */
281     OPC_SDBBP    = 0x3F | OPC_SPECIAL2,
282 };
283
284 /* Special3 opcodes */
285 #define MASK_SPECIAL3(op)  MASK_OP_MAJOR(op) | (op & 0x3F)
286
287 enum {
288     OPC_EXT      = 0x00 | OPC_SPECIAL3,
289     OPC_DEXTM    = 0x01 | OPC_SPECIAL3,
290     OPC_DEXTU    = 0x02 | OPC_SPECIAL3,
291     OPC_DEXT     = 0x03 | OPC_SPECIAL3,
292     OPC_INS      = 0x04 | OPC_SPECIAL3,
293     OPC_DINSM    = 0x05 | OPC_SPECIAL3,
294     OPC_DINSU    = 0x06 | OPC_SPECIAL3,
295     OPC_DINS     = 0x07 | OPC_SPECIAL3,
296     OPC_FORK     = 0x08 | OPC_SPECIAL3,
297     OPC_YIELD    = 0x09 | OPC_SPECIAL3,
298     OPC_BSHFL    = 0x20 | OPC_SPECIAL3,
299     OPC_DBSHFL   = 0x24 | OPC_SPECIAL3,
300     OPC_RDHWR    = 0x3B | OPC_SPECIAL3,
301
302     /* Loongson 2E */
303     OPC_MULT_G_2E   = 0x18 | OPC_SPECIAL3,
304     OPC_MULTU_G_2E  = 0x19 | OPC_SPECIAL3,
305     OPC_DIV_G_2E    = 0x1A | OPC_SPECIAL3,
306     OPC_DIVU_G_2E   = 0x1B | OPC_SPECIAL3,
307     OPC_DMULT_G_2E  = 0x1C | OPC_SPECIAL3,
308     OPC_DMULTU_G_2E = 0x1D | OPC_SPECIAL3,
309     OPC_DDIV_G_2E   = 0x1E | OPC_SPECIAL3,
310     OPC_DDIVU_G_2E  = 0x1F | OPC_SPECIAL3,
311     OPC_MOD_G_2E    = 0x22 | OPC_SPECIAL3,
312     OPC_MODU_G_2E   = 0x23 | OPC_SPECIAL3,
313     OPC_DMOD_G_2E   = 0x26 | OPC_SPECIAL3,
314     OPC_DMODU_G_2E  = 0x27 | OPC_SPECIAL3,
315 };
316
317 /* BSHFL opcodes */
318 #define MASK_BSHFL(op)     MASK_SPECIAL3(op) | (op & (0x1F << 6))
319
320 enum {
321     OPC_WSBH     = (0x02 << 6) | OPC_BSHFL,
322     OPC_SEB      = (0x10 << 6) | OPC_BSHFL,
323     OPC_SEH      = (0x18 << 6) | OPC_BSHFL,
324 };
325
326 /* DBSHFL opcodes */
327 #define MASK_DBSHFL(op)    MASK_SPECIAL3(op) | (op & (0x1F << 6))
328
329 enum {
330     OPC_DSBH     = (0x02 << 6) | OPC_DBSHFL,
331     OPC_DSHD     = (0x05 << 6) | OPC_DBSHFL,
332 };
333
334 /* Coprocessor 0 (rs field) */
335 #define MASK_CP0(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
336
337 enum {
338     OPC_MFC0     = (0x00 << 21) | OPC_CP0,
339     OPC_DMFC0    = (0x01 << 21) | OPC_CP0,
340     OPC_MTC0     = (0x04 << 21) | OPC_CP0,
341     OPC_DMTC0    = (0x05 << 21) | OPC_CP0,
342     OPC_MFTR     = (0x08 << 21) | OPC_CP0,
343     OPC_RDPGPR   = (0x0A << 21) | OPC_CP0,
344     OPC_MFMC0    = (0x0B << 21) | OPC_CP0,
345     OPC_MTTR     = (0x0C << 21) | OPC_CP0,
346     OPC_WRPGPR   = (0x0E << 21) | OPC_CP0,
347     OPC_C0       = (0x10 << 21) | OPC_CP0,
348     OPC_C0_FIRST = (0x10 << 21) | OPC_CP0,
349     OPC_C0_LAST  = (0x1F << 21) | OPC_CP0,
350 };
351
352 /* MFMC0 opcodes */
353 #define MASK_MFMC0(op)     MASK_CP0(op) | (op & 0xFFFF)
354
355 enum {
356     OPC_DMT      = 0x01 | (0 << 5) | (0x0F << 6) | (0x01 << 11) | OPC_MFMC0,
357     OPC_EMT      = 0x01 | (1 << 5) | (0x0F << 6) | (0x01 << 11) | OPC_MFMC0,
358     OPC_DVPE     = 0x01 | (0 << 5) | OPC_MFMC0,
359     OPC_EVPE     = 0x01 | (1 << 5) | OPC_MFMC0,
360     OPC_DI       = (0 << 5) | (0x0C << 11) | OPC_MFMC0,
361     OPC_EI       = (1 << 5) | (0x0C << 11) | OPC_MFMC0,
362 };
363
364 /* Coprocessor 0 (with rs == C0) */
365 #define MASK_C0(op)        MASK_CP0(op) | (op & 0x3F)
366
367 enum {
368     OPC_TLBR     = 0x01 | OPC_C0,
369     OPC_TLBWI    = 0x02 | OPC_C0,
370     OPC_TLBWR    = 0x06 | OPC_C0,
371     OPC_TLBP     = 0x08 | OPC_C0,
372     OPC_RFE      = 0x10 | OPC_C0,
373     OPC_ERET     = 0x18 | OPC_C0,
374     OPC_DERET    = 0x1F | OPC_C0,
375     OPC_WAIT     = 0x20 | OPC_C0,
376 };
377
378 /* Coprocessor 1 (rs field) */
379 #define MASK_CP1(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
380
381 /* Values for the fmt field in FP instructions */
382 enum {
383     /* 0 - 15 are reserved */
384     FMT_S = 16,          /* single fp */
385     FMT_D = 17,          /* double fp */
386     FMT_E = 18,          /* extended fp */
387     FMT_Q = 19,          /* quad fp */
388     FMT_W = 20,          /* 32-bit fixed */
389     FMT_L = 21,          /* 64-bit fixed */
390     FMT_PS = 22,         /* paired single fp */
391     /* 23 - 31 are reserved */
392 };
393
394 enum {
395     OPC_MFC1     = (0x00 << 21) | OPC_CP1,
396     OPC_DMFC1    = (0x01 << 21) | OPC_CP1,
397     OPC_CFC1     = (0x02 << 21) | OPC_CP1,
398     OPC_MFHC1    = (0x03 << 21) | OPC_CP1,
399     OPC_MTC1     = (0x04 << 21) | OPC_CP1,
400     OPC_DMTC1    = (0x05 << 21) | OPC_CP1,
401     OPC_CTC1     = (0x06 << 21) | OPC_CP1,
402     OPC_MTHC1    = (0x07 << 21) | OPC_CP1,
403     OPC_BC1      = (0x08 << 21) | OPC_CP1, /* bc */
404     OPC_BC1ANY2  = (0x09 << 21) | OPC_CP1,
405     OPC_BC1ANY4  = (0x0A << 21) | OPC_CP1,
406     OPC_S_FMT    = (FMT_S << 21) | OPC_CP1,
407     OPC_D_FMT    = (FMT_D << 21) | OPC_CP1,
408     OPC_E_FMT    = (FMT_E << 21) | OPC_CP1,
409     OPC_Q_FMT    = (FMT_Q << 21) | OPC_CP1,
410     OPC_W_FMT    = (FMT_W << 21) | OPC_CP1,
411     OPC_L_FMT    = (FMT_L << 21) | OPC_CP1,
412     OPC_PS_FMT   = (FMT_PS << 21) | OPC_CP1,
413 };
414
415 #define MASK_CP1_FUNC(op)       MASK_CP1(op) | (op & 0x3F)
416 #define MASK_BC1(op)            MASK_CP1(op) | (op & (0x3 << 16))
417
418 enum {
419     OPC_BC1F     = (0x00 << 16) | OPC_BC1,
420     OPC_BC1T     = (0x01 << 16) | OPC_BC1,
421     OPC_BC1FL    = (0x02 << 16) | OPC_BC1,
422     OPC_BC1TL    = (0x03 << 16) | OPC_BC1,
423 };
424
425 enum {
426     OPC_BC1FANY2     = (0x00 << 16) | OPC_BC1ANY2,
427     OPC_BC1TANY2     = (0x01 << 16) | OPC_BC1ANY2,
428 };
429
430 enum {
431     OPC_BC1FANY4     = (0x00 << 16) | OPC_BC1ANY4,
432     OPC_BC1TANY4     = (0x01 << 16) | OPC_BC1ANY4,
433 };
434
435 #define MASK_CP2(op)       MASK_OP_MAJOR(op) | (op & (0x1F << 21))
436
437 enum {
438     OPC_MFC2    = (0x00 << 21) | OPC_CP2,
439     OPC_DMFC2   = (0x01 << 21) | OPC_CP2,
440     OPC_CFC2    = (0x02 << 21) | OPC_CP2,
441     OPC_MFHC2   = (0x03 << 21) | OPC_CP2,
442     OPC_MTC2    = (0x04 << 21) | OPC_CP2,
443     OPC_DMTC2   = (0x05 << 21) | OPC_CP2,
444     OPC_CTC2    = (0x06 << 21) | OPC_CP2,
445     OPC_MTHC2   = (0x07 << 21) | OPC_CP2,
446     OPC_BC2     = (0x08 << 21) | OPC_CP2,
447 };
448
449 #define MASK_CP3(op)       MASK_OP_MAJOR(op) | (op & 0x3F)
450
451 enum {
452     OPC_LWXC1   = 0x00 | OPC_CP3,
453     OPC_LDXC1   = 0x01 | OPC_CP3,
454     OPC_LUXC1   = 0x05 | OPC_CP3,
455     OPC_SWXC1   = 0x08 | OPC_CP3,
456     OPC_SDXC1   = 0x09 | OPC_CP3,
457     OPC_SUXC1   = 0x0D | OPC_CP3,
458     OPC_PREFX   = 0x0F | OPC_CP3,
459     OPC_ALNV_PS = 0x1E | OPC_CP3,
460     OPC_MADD_S  = 0x20 | OPC_CP3,
461     OPC_MADD_D  = 0x21 | OPC_CP3,
462     OPC_MADD_PS = 0x26 | OPC_CP3,
463     OPC_MSUB_S  = 0x28 | OPC_CP3,
464     OPC_MSUB_D  = 0x29 | OPC_CP3,
465     OPC_MSUB_PS = 0x2E | OPC_CP3,
466     OPC_NMADD_S = 0x30 | OPC_CP3,
467     OPC_NMADD_D = 0x31 | OPC_CP3,
468     OPC_NMADD_PS= 0x36 | OPC_CP3,
469     OPC_NMSUB_S = 0x38 | OPC_CP3,
470     OPC_NMSUB_D = 0x39 | OPC_CP3,
471     OPC_NMSUB_PS= 0x3E | OPC_CP3,
472 };
473
474 /* global register indices */
475 static TCGv_ptr cpu_env;
476 static TCGv cpu_gpr[32], cpu_PC;
477 static TCGv cpu_HI[MIPS_DSP_ACC], cpu_LO[MIPS_DSP_ACC], cpu_ACX[MIPS_DSP_ACC];
478 static TCGv cpu_dspctrl, btarget, bcond;
479 static TCGv_i32 hflags;
480 static TCGv_i32 fpu_fcr0, fpu_fcr31;
481
482 static uint32_t gen_opc_hflags[OPC_BUF_SIZE];
483
484 #include "gen-icount.h"
485
486 #define gen_helper_0i(name, arg) do {                             \
487     TCGv_i32 helper_tmp = tcg_const_i32(arg);                     \
488     gen_helper_##name(helper_tmp);                                \
489     tcg_temp_free_i32(helper_tmp);                                \
490     } while(0)
491
492 #define gen_helper_1i(name, arg1, arg2) do {                      \
493     TCGv_i32 helper_tmp = tcg_const_i32(arg2);                    \
494     gen_helper_##name(arg1, helper_tmp);                          \
495     tcg_temp_free_i32(helper_tmp);                                \
496     } while(0)
497
498 #define gen_helper_2i(name, arg1, arg2, arg3) do {                \
499     TCGv_i32 helper_tmp = tcg_const_i32(arg3);                    \
500     gen_helper_##name(arg1, arg2, helper_tmp);                    \
501     tcg_temp_free_i32(helper_tmp);                                \
502     } while(0)
503
504 #define gen_helper_3i(name, arg1, arg2, arg3, arg4) do {          \
505     TCGv_i32 helper_tmp = tcg_const_i32(arg4);                    \
506     gen_helper_##name(arg1, arg2, arg3, helper_tmp);              \
507     tcg_temp_free_i32(helper_tmp);                                \
508     } while(0)
509
510 typedef struct DisasContext {
511     struct TranslationBlock *tb;
512     target_ulong pc, saved_pc;
513     uint32_t opcode;
514     int singlestep_enabled;
515     /* Routine used to access memory */
516     int mem_idx;
517     uint32_t hflags, saved_hflags;
518     int bstate;
519     target_ulong btarget;
520 } DisasContext;
521
522 enum {
523     BS_NONE     = 0, /* We go out of the TB without reaching a branch or an
524                       * exception condition */
525     BS_STOP     = 1, /* We want to stop translation for any reason */
526     BS_BRANCH   = 2, /* We reached a branch condition     */
527     BS_EXCP     = 3, /* We reached an exception condition */
528 };
529
530 static const char *regnames[] =
531     { "r0", "at", "v0", "v1", "a0", "a1", "a2", "a3",
532       "t0", "t1", "t2", "t3", "t4", "t5", "t6", "t7",
533       "s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7",
534       "t8", "t9", "k0", "k1", "gp", "sp", "s8", "ra", };
535
536 static const char *regnames_HI[] =
537     { "HI0", "HI1", "HI2", "HI3", };
538
539 static const char *regnames_LO[] =
540     { "LO0", "LO1", "LO2", "LO3", };
541
542 static const char *regnames_ACX[] =
543     { "ACX0", "ACX1", "ACX2", "ACX3", };
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 #ifdef MIPS_DEBUG_DISAS
552 #define MIPS_DEBUG(fmt, ...)                         \
553         qemu_log_mask(CPU_LOG_TB_IN_ASM,                \
554                        TARGET_FMT_lx ": %08x " fmt "\n", \
555                        ctx->pc, ctx->opcode , ## __VA_ARGS__)
556 #define LOG_DISAS(...) qemu_log_mask(CPU_LOG_TB_IN_ASM, ## __VA_ARGS__)
557 #else
558 #define MIPS_DEBUG(fmt, ...) do { } while(0)
559 #define LOG_DISAS(...) do { } while (0)
560 #endif
561
562 #define MIPS_INVAL(op)                                                        \
563 do {                                                                          \
564     MIPS_DEBUG("Invalid %s %03x %03x %03x", op, ctx->opcode >> 26,            \
565                ctx->opcode & 0x3F, ((ctx->opcode >> 16) & 0x1F));             \
566 } while (0)
567
568 /* General purpose registers moves. */
569 static inline void gen_load_gpr (TCGv t, int reg)
570 {
571     if (reg == 0)
572         tcg_gen_movi_tl(t, 0);
573     else
574         tcg_gen_mov_tl(t, cpu_gpr[reg]);
575 }
576
577 static inline void gen_store_gpr (TCGv t, int reg)
578 {
579     if (reg != 0)
580         tcg_gen_mov_tl(cpu_gpr[reg], t);
581 }
582
583 /* Moves to/from ACX register.  */
584 static inline void gen_load_ACX (TCGv t, int reg)
585 {
586     tcg_gen_mov_tl(t, cpu_ACX[reg]);
587 }
588
589 static inline void gen_store_ACX (TCGv t, int reg)
590 {
591     tcg_gen_mov_tl(cpu_ACX[reg], t);
592 }
593
594 /* Moves to/from shadow registers. */
595 static inline void gen_load_srsgpr (int from, int to)
596 {
597     TCGv t0 = tcg_temp_new();
598
599     if (from == 0)
600         tcg_gen_movi_tl(t0, 0);
601     else {
602         TCGv_i32 t2 = tcg_temp_new_i32();
603         TCGv_ptr addr = tcg_temp_new_ptr();
604
605         tcg_gen_ld_i32(t2, cpu_env, offsetof(CPUMIPSState, CP0_SRSCtl));
606         tcg_gen_shri_i32(t2, t2, CP0SRSCtl_PSS);
607         tcg_gen_andi_i32(t2, t2, 0xf);
608         tcg_gen_muli_i32(t2, t2, sizeof(target_ulong) * 32);
609         tcg_gen_ext_i32_ptr(addr, t2);
610         tcg_gen_add_ptr(addr, cpu_env, addr);
611
612         tcg_gen_ld_tl(t0, addr, sizeof(target_ulong) * from);
613         tcg_temp_free_ptr(addr);
614         tcg_temp_free_i32(t2);
615     }
616     gen_store_gpr(t0, to);
617     tcg_temp_free(t0);
618 }
619
620 static inline void gen_store_srsgpr (int from, int to)
621 {
622     if (to != 0) {
623         TCGv t0 = tcg_temp_new();
624         TCGv_i32 t2 = tcg_temp_new_i32();
625         TCGv_ptr addr = tcg_temp_new_ptr();
626
627         gen_load_gpr(t0, from);
628         tcg_gen_ld_i32(t2, cpu_env, offsetof(CPUMIPSState, CP0_SRSCtl));
629         tcg_gen_shri_i32(t2, t2, CP0SRSCtl_PSS);
630         tcg_gen_andi_i32(t2, t2, 0xf);
631         tcg_gen_muli_i32(t2, t2, sizeof(target_ulong) * 32);
632         tcg_gen_ext_i32_ptr(addr, t2);
633         tcg_gen_add_ptr(addr, cpu_env, addr);
634
635         tcg_gen_st_tl(t0, addr, sizeof(target_ulong) * to);
636         tcg_temp_free_ptr(addr);
637         tcg_temp_free_i32(t2);
638         tcg_temp_free(t0);
639     }
640 }
641
642 /* Floating point register moves. */
643 static inline void gen_load_fpr32 (TCGv_i32 t, int reg)
644 {
645     tcg_gen_ld_i32(t, cpu_env, offsetof(CPUMIPSState, active_fpu.fpr[reg].w[FP_ENDIAN_IDX]));
646 }
647
648 static inline void gen_store_fpr32 (TCGv_i32 t, int reg)
649 {
650     tcg_gen_st_i32(t, cpu_env, offsetof(CPUMIPSState, active_fpu.fpr[reg].w[FP_ENDIAN_IDX]));
651 }
652
653 static inline void gen_load_fpr32h (TCGv_i32 t, int reg)
654 {
655     tcg_gen_ld_i32(t, cpu_env, offsetof(CPUMIPSState, active_fpu.fpr[reg].w[!FP_ENDIAN_IDX]));
656 }
657
658 static inline void gen_store_fpr32h (TCGv_i32 t, int reg)
659 {
660     tcg_gen_st_i32(t, cpu_env, offsetof(CPUMIPSState, active_fpu.fpr[reg].w[!FP_ENDIAN_IDX]));
661 }
662
663 static inline void gen_load_fpr64 (DisasContext *ctx, TCGv_i64 t, int reg)
664 {
665     if (ctx->hflags & MIPS_HFLAG_F64) {
666         tcg_gen_ld_i64(t, cpu_env, offsetof(CPUMIPSState, active_fpu.fpr[reg].d));
667     } else {
668         TCGv_i32 t0 = tcg_temp_new_i32();
669         TCGv_i32 t1 = tcg_temp_new_i32();
670         gen_load_fpr32(t0, reg & ~1);
671         gen_load_fpr32(t1, reg | 1);
672         tcg_gen_concat_i32_i64(t, t0, t1);
673         tcg_temp_free_i32(t0);
674         tcg_temp_free_i32(t1);
675     }
676 }
677
678 static inline void gen_store_fpr64 (DisasContext *ctx, TCGv_i64 t, int reg)
679 {
680     if (ctx->hflags & MIPS_HFLAG_F64) {
681         tcg_gen_st_i64(t, cpu_env, offsetof(CPUMIPSState, active_fpu.fpr[reg].d));
682     } else {
683         TCGv_i64 t0 = tcg_temp_new_i64();
684         TCGv_i32 t1 = tcg_temp_new_i32();
685         tcg_gen_trunc_i64_i32(t1, t);
686         gen_store_fpr32(t1, reg & ~1);
687         tcg_gen_shri_i64(t0, t, 32);
688         tcg_gen_trunc_i64_i32(t1, t0);
689         gen_store_fpr32(t1, reg | 1);
690         tcg_temp_free_i32(t1);
691         tcg_temp_free_i64(t0);
692     }
693 }
694
695 static inline int get_fp_bit (int cc)
696 {
697     if (cc)
698         return 24 + cc;
699     else
700         return 23;
701 }
702
703 /* Tests */
704 static inline void gen_save_pc(target_ulong pc)
705 {
706     tcg_gen_movi_tl(cpu_PC, pc);
707 }
708
709 static inline void save_cpu_state (DisasContext *ctx, int do_save_pc)
710 {
711     LOG_DISAS("hflags %08x saved %08x\n", ctx->hflags, ctx->saved_hflags);
712     if (do_save_pc && ctx->pc != ctx->saved_pc) {
713         gen_save_pc(ctx->pc);
714         ctx->saved_pc = ctx->pc;
715     }
716     if (ctx->hflags != ctx->saved_hflags) {
717         tcg_gen_movi_i32(hflags, ctx->hflags);
718         ctx->saved_hflags = ctx->hflags;
719         switch (ctx->hflags & MIPS_HFLAG_BMASK_BASE) {
720         case MIPS_HFLAG_BR:
721             break;
722         case MIPS_HFLAG_BC:
723         case MIPS_HFLAG_BL:
724         case MIPS_HFLAG_B:
725             tcg_gen_movi_tl(btarget, ctx->btarget);
726             break;
727         }
728     }
729 }
730
731 static inline void restore_cpu_state (CPUMIPSState *env, DisasContext *ctx)
732 {
733     ctx->saved_hflags = ctx->hflags;
734     switch (ctx->hflags & MIPS_HFLAG_BMASK_BASE) {
735     case MIPS_HFLAG_BR:
736         break;
737     case MIPS_HFLAG_BC:
738     case MIPS_HFLAG_BL:
739     case MIPS_HFLAG_B:
740         ctx->btarget = env->btarget;
741         break;
742     }
743 }
744
745 static inline void
746 generate_exception_err (DisasContext *ctx, int excp, int err)
747 {
748     TCGv_i32 texcp = tcg_const_i32(excp);
749     TCGv_i32 terr = tcg_const_i32(err);
750     save_cpu_state(ctx, 1);
751     gen_helper_raise_exception_err(texcp, terr);
752     tcg_temp_free_i32(terr);
753     tcg_temp_free_i32(texcp);
754 }
755
756 static inline void
757 generate_exception (DisasContext *ctx, int excp)
758 {
759     save_cpu_state(ctx, 1);
760     gen_helper_0i(raise_exception, excp);
761 }
762
763 /* Addresses computation */
764 static inline void gen_op_addr_add (DisasContext *ctx, TCGv ret, TCGv arg0, TCGv arg1)
765 {
766     tcg_gen_add_tl(ret, arg0, arg1);
767
768 #if defined(TARGET_MIPS64)
769     /* For compatibility with 32-bit code, data reference in user mode
770        with Status_UX = 0 should be casted to 32-bit and sign extended.
771        See the MIPS64 PRA manual, section 4.10. */
772     if (((ctx->hflags & MIPS_HFLAG_KSU) == MIPS_HFLAG_UM) &&
773         !(ctx->hflags & MIPS_HFLAG_UX)) {
774         tcg_gen_ext32s_i64(ret, ret);
775     }
776 #endif
777 }
778
779 static inline void check_cp0_enabled(DisasContext *ctx)
780 {
781     if (unlikely(!(ctx->hflags & MIPS_HFLAG_CP0)))
782         generate_exception_err(ctx, EXCP_CpU, 0);
783 }
784
785 static inline void check_cp1_enabled(DisasContext *ctx)
786 {
787     if (unlikely(!(ctx->hflags & MIPS_HFLAG_FPU)))
788         generate_exception_err(ctx, EXCP_CpU, 1);
789 }
790
791 /* Verify that the processor is running with COP1X instructions enabled.
792    This is associated with the nabla symbol in the MIPS32 and MIPS64
793    opcode tables.  */
794
795 static inline void check_cop1x(DisasContext *ctx)
796 {
797     if (unlikely(!(ctx->hflags & MIPS_HFLAG_COP1X)))
798         generate_exception(ctx, EXCP_RI);
799 }
800
801 /* Verify that the processor is running with 64-bit floating-point
802    operations enabled.  */
803
804 static inline void check_cp1_64bitmode(DisasContext *ctx)
805 {
806     if (unlikely(~ctx->hflags & (MIPS_HFLAG_F64 | MIPS_HFLAG_COP1X)))
807         generate_exception(ctx, EXCP_RI);
808 }
809
810 /*
811  * Verify if floating point register is valid; an operation is not defined
812  * if bit 0 of any register specification is set and the FR bit in the
813  * Status register equals zero, since the register numbers specify an
814  * even-odd pair of adjacent coprocessor general registers. When the FR bit
815  * in the Status register equals one, both even and odd register numbers
816  * are valid. This limitation exists only for 64 bit wide (d,l,ps) registers.
817  *
818  * Multiple 64 bit wide registers can be checked by calling
819  * gen_op_cp1_registers(freg1 | freg2 | ... | fregN);
820  */
821 static inline void check_cp1_registers(DisasContext *ctx, int regs)
822 {
823     if (unlikely(!(ctx->hflags & MIPS_HFLAG_F64) && (regs & 1)))
824         generate_exception(ctx, EXCP_RI);
825 }
826
827 /* This code generates a "reserved instruction" exception if the
828    CPU does not support the instruction set corresponding to flags. */
829 static inline void check_insn(CPUMIPSState *env, DisasContext *ctx, int flags)
830 {
831     if (unlikely(!(env->insn_flags & flags)))
832         generate_exception(ctx, EXCP_RI);
833 }
834
835 /* This code generates a "reserved instruction" exception if 64-bit
836    instructions are not enabled. */
837 static inline void check_mips_64(DisasContext *ctx)
838 {
839     if (unlikely(!(ctx->hflags & MIPS_HFLAG_64)))
840         generate_exception(ctx, EXCP_RI);
841 }
842
843 /* Define small wrappers for gen_load_fpr* so that we have a uniform
844    calling interface for 32 and 64-bit FPRs.  No sense in changing
845    all callers for gen_load_fpr32 when we need the CTX parameter for
846    this one use.  */
847 #define gen_ldcmp_fpr32(ctx, x, y) gen_load_fpr32(x, y)
848 #define gen_ldcmp_fpr64(ctx, x, y) gen_load_fpr64(ctx, x, y)
849 #define FOP_CONDS(type, abs, fmt, ifmt, bits)                                 \
850 static inline void gen_cmp ## type ## _ ## fmt(DisasContext *ctx, int n,      \
851                                                int ft, int fs, int cc)        \
852 {                                                                             \
853     TCGv_i##bits fp0 = tcg_temp_new_i##bits ();                               \
854     TCGv_i##bits fp1 = tcg_temp_new_i##bits ();                               \
855     switch (ifmt) {                                                           \
856     case FMT_PS:                                                              \
857         check_cp1_64bitmode(ctx);                                             \
858         break;                                                                \
859     case FMT_D:                                                               \
860         if (abs) {                                                            \
861             check_cop1x(ctx);                                                 \
862         }                                                                     \
863         check_cp1_registers(ctx, fs | ft);                                    \
864         break;                                                                \
865     case FMT_S:                                                               \
866         if (abs) {                                                            \
867             check_cop1x(ctx);                                                 \
868         }                                                                     \
869         break;                                                                \
870     }                                                                         \
871     gen_ldcmp_fpr##bits (ctx, fp0, fs);                                       \
872     gen_ldcmp_fpr##bits (ctx, fp1, ft);                                       \
873     switch (n) {                                                              \
874     case  0: gen_helper_2i(cmp ## type ## _ ## fmt ## _f, fp0, fp1, cc);    break;\
875     case  1: gen_helper_2i(cmp ## type ## _ ## fmt ## _un, fp0, fp1, cc);   break;\
876     case  2: gen_helper_2i(cmp ## type ## _ ## fmt ## _eq, fp0, fp1, cc);   break;\
877     case  3: gen_helper_2i(cmp ## type ## _ ## fmt ## _ueq, fp0, fp1, cc);  break;\
878     case  4: gen_helper_2i(cmp ## type ## _ ## fmt ## _olt, fp0, fp1, cc);  break;\
879     case  5: gen_helper_2i(cmp ## type ## _ ## fmt ## _ult, fp0, fp1, cc);  break;\
880     case  6: gen_helper_2i(cmp ## type ## _ ## fmt ## _ole, fp0, fp1, cc);  break;\
881     case  7: gen_helper_2i(cmp ## type ## _ ## fmt ## _ule, fp0, fp1, cc);  break;\
882     case  8: gen_helper_2i(cmp ## type ## _ ## fmt ## _sf, fp0, fp1, cc);   break;\
883     case  9: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngle, fp0, fp1, cc); break;\
884     case 10: gen_helper_2i(cmp ## type ## _ ## fmt ## _seq, fp0, fp1, cc);  break;\
885     case 11: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngl, fp0, fp1, cc);  break;\
886     case 12: gen_helper_2i(cmp ## type ## _ ## fmt ## _lt, fp0, fp1, cc);   break;\
887     case 13: gen_helper_2i(cmp ## type ## _ ## fmt ## _nge, fp0, fp1, cc);  break;\
888     case 14: gen_helper_2i(cmp ## type ## _ ## fmt ## _le, fp0, fp1, cc);   break;\
889     case 15: gen_helper_2i(cmp ## type ## _ ## fmt ## _ngt, fp0, fp1, cc);  break;\
890     default: abort();                                                         \
891     }                                                                         \
892     tcg_temp_free_i##bits (fp0);                                              \
893     tcg_temp_free_i##bits (fp1);                                              \
894 }
895
896 FOP_CONDS(, 0, d, FMT_D, 64)
897 FOP_CONDS(abs, 1, d, FMT_D, 64)
898 FOP_CONDS(, 0, s, FMT_S, 32)
899 FOP_CONDS(abs, 1, s, FMT_S, 32)
900 FOP_CONDS(, 0, ps, FMT_PS, 64)
901 FOP_CONDS(abs, 1, ps, FMT_PS, 64)
902 #undef FOP_CONDS
903 #undef gen_ldcmp_fpr32
904 #undef gen_ldcmp_fpr64
905
906 /* load/store instructions. */
907 #define OP_LD(insn,fname)                                                 \
908 static inline void op_ld_##insn(TCGv ret, TCGv arg1, DisasContext *ctx)   \
909 {                                                                         \
910     tcg_gen_qemu_##fname(ret, arg1, ctx->mem_idx);                        \
911 }
912 OP_LD(lb,ld8s);
913 OP_LD(lbu,ld8u);
914 OP_LD(lh,ld16s);
915 OP_LD(lhu,ld16u);
916 OP_LD(lw,ld32s);
917 #if defined(TARGET_MIPS64)
918 OP_LD(lwu,ld32u);
919 OP_LD(ld,ld64);
920 #endif
921 #undef OP_LD
922
923 #define OP_ST(insn,fname)                                                  \
924 static inline void op_st_##insn(TCGv arg1, TCGv arg2, DisasContext *ctx)   \
925 {                                                                          \
926     tcg_gen_qemu_##fname(arg1, arg2, ctx->mem_idx);                        \
927 }
928 OP_ST(sb,st8);
929 OP_ST(sh,st16);
930 OP_ST(sw,st32);
931 #if defined(TARGET_MIPS64)
932 OP_ST(sd,st64);
933 #endif
934 #undef OP_ST
935
936 #ifdef CONFIG_USER_ONLY
937 #define OP_LD_ATOMIC(insn,fname)                                           \
938 static inline void op_ld_##insn(TCGv ret, TCGv arg1, DisasContext *ctx)    \
939 {                                                                          \
940     TCGv t0 = tcg_temp_new();                                              \
941     tcg_gen_mov_tl(t0, arg1);                                              \
942     tcg_gen_qemu_##fname(ret, arg1, ctx->mem_idx);                         \
943     tcg_gen_st_tl(t0, cpu_env, offsetof(CPUMIPSState, lladdr));                \
944     tcg_gen_st_tl(ret, cpu_env, offsetof(CPUMIPSState, llval));                \
945     tcg_temp_free(t0);                                                     \
946 }
947 #else
948 #define OP_LD_ATOMIC(insn,fname)                                           \
949 static inline void op_ld_##insn(TCGv ret, TCGv arg1, DisasContext *ctx)    \
950 {                                                                          \
951     gen_helper_2i(insn, ret, arg1, ctx->mem_idx);                          \
952 }
953 #endif
954 OP_LD_ATOMIC(ll,ld32s);
955 #if defined(TARGET_MIPS64)
956 OP_LD_ATOMIC(lld,ld64);
957 #endif
958 #undef OP_LD_ATOMIC
959
960 #ifdef CONFIG_USER_ONLY
961 #define OP_ST_ATOMIC(insn,fname,ldname,almask)                               \
962 static inline void op_st_##insn(TCGv arg1, TCGv arg2, int rt, DisasContext *ctx) \
963 {                                                                            \
964     TCGv t0 = tcg_temp_new();                                                \
965     int l1 = gen_new_label();                                                \
966     int l2 = gen_new_label();                                                \
967                                                                              \
968     tcg_gen_andi_tl(t0, arg2, almask);                                       \
969     tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);                              \
970     tcg_gen_st_tl(arg2, cpu_env, offsetof(CPUMIPSState, CP0_BadVAddr));          \
971     generate_exception(ctx, EXCP_AdES);                                      \
972     gen_set_label(l1);                                                       \
973     tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUMIPSState, lladdr));                  \
974     tcg_gen_brcond_tl(TCG_COND_NE, arg2, t0, l2);                            \
975     tcg_gen_movi_tl(t0, rt | ((almask << 3) & 0x20));                        \
976     tcg_gen_st_tl(t0, cpu_env, offsetof(CPUMIPSState, llreg));                   \
977     tcg_gen_st_tl(arg1, cpu_env, offsetof(CPUMIPSState, llnewval));              \
978     gen_helper_0i(raise_exception, EXCP_SC);                                 \
979     gen_set_label(l2);                                                       \
980     tcg_gen_movi_tl(t0, 0);                                                  \
981     gen_store_gpr(t0, rt);                                                   \
982     tcg_temp_free(t0);                                                       \
983 }
984 #else
985 #define OP_ST_ATOMIC(insn,fname,ldname,almask)                               \
986 static inline void op_st_##insn(TCGv arg1, TCGv arg2, int rt, DisasContext *ctx) \
987 {                                                                            \
988     TCGv t0 = tcg_temp_new();                                                \
989     gen_helper_3i(insn, t0, arg1, arg2, ctx->mem_idx);                       \
990     gen_store_gpr(t0, rt);                                                   \
991     tcg_temp_free(t0);                                                       \
992 }
993 #endif
994 OP_ST_ATOMIC(sc,st32,ld32s,0x3);
995 #if defined(TARGET_MIPS64)
996 OP_ST_ATOMIC(scd,st64,ld64,0x7);
997 #endif
998 #undef OP_ST_ATOMIC
999
1000 static void gen_base_offset_addr (DisasContext *ctx, TCGv addr,
1001                                   int base, int16_t offset)
1002 {
1003     if (base == 0) {
1004         tcg_gen_movi_tl(addr, offset);
1005     } else if (offset == 0) {
1006         gen_load_gpr(addr, base);
1007     } else {
1008         tcg_gen_movi_tl(addr, offset);
1009         gen_op_addr_add(ctx, addr, cpu_gpr[base], addr);
1010     }
1011 }
1012
1013 static target_ulong pc_relative_pc (DisasContext *ctx)
1014 {
1015     target_ulong pc = ctx->pc;
1016
1017     if (ctx->hflags & MIPS_HFLAG_BMASK) {
1018         int branch_bytes = ctx->hflags & MIPS_HFLAG_BDS16 ? 2 : 4;
1019
1020         pc -= branch_bytes;
1021     }
1022
1023     pc &= ~(target_ulong)3;
1024     return pc;
1025 }
1026
1027 /* Load */
1028 static void gen_ld (CPUMIPSState *env, DisasContext *ctx, uint32_t opc,
1029                     int rt, int base, int16_t offset)
1030 {
1031     const char *opn = "ld";
1032     TCGv t0, t1;
1033
1034     if (rt == 0 && env->insn_flags & (INSN_LOONGSON2E | INSN_LOONGSON2F)) {
1035         /* Loongson CPU uses a load to zero register for prefetch.
1036            We emulate it as a NOP. On other CPU we must perform the
1037            actual memory access. */
1038         MIPS_DEBUG("NOP");
1039         return;
1040     }
1041
1042     t0 = tcg_temp_new();
1043     t1 = tcg_temp_new();
1044     gen_base_offset_addr(ctx, t0, base, offset);
1045
1046     switch (opc) {
1047 #if defined(TARGET_MIPS64)
1048     case OPC_LWU:
1049         save_cpu_state(ctx, 0);
1050         op_ld_lwu(t0, t0, ctx);
1051         gen_store_gpr(t0, rt);
1052         opn = "lwu";
1053         break;
1054     case OPC_LD:
1055         save_cpu_state(ctx, 0);
1056         op_ld_ld(t0, t0, ctx);
1057         gen_store_gpr(t0, rt);
1058         opn = "ld";
1059         break;
1060     case OPC_LLD:
1061         save_cpu_state(ctx, 1);
1062         op_ld_lld(t0, t0, ctx);
1063         gen_store_gpr(t0, rt);
1064         opn = "lld";
1065         break;
1066     case OPC_LDL:
1067         save_cpu_state(ctx, 1);
1068         gen_load_gpr(t1, rt);
1069         gen_helper_3i(ldl, t1, t1, t0, ctx->mem_idx);
1070         gen_store_gpr(t1, rt);
1071         opn = "ldl";
1072         break;
1073     case OPC_LDR:
1074         save_cpu_state(ctx, 1);
1075         gen_load_gpr(t1, rt);
1076         gen_helper_3i(ldr, t1, t1, t0, ctx->mem_idx);
1077         gen_store_gpr(t1, rt);
1078         opn = "ldr";
1079         break;
1080     case OPC_LDPC:
1081         save_cpu_state(ctx, 0);
1082         tcg_gen_movi_tl(t1, pc_relative_pc(ctx));
1083         gen_op_addr_add(ctx, t0, t0, t1);
1084         op_ld_ld(t0, t0, ctx);
1085         gen_store_gpr(t0, rt);
1086         opn = "ldpc";
1087         break;
1088 #endif
1089     case OPC_LWPC:
1090         save_cpu_state(ctx, 0);
1091         tcg_gen_movi_tl(t1, pc_relative_pc(ctx));
1092         gen_op_addr_add(ctx, t0, t0, t1);
1093         op_ld_lw(t0, t0, ctx);
1094         gen_store_gpr(t0, rt);
1095         opn = "lwpc";
1096         break;
1097     case OPC_LW:
1098         save_cpu_state(ctx, 0);
1099         op_ld_lw(t0, t0, ctx);
1100         gen_store_gpr(t0, rt);
1101         opn = "lw";
1102         break;
1103     case OPC_LH:
1104         save_cpu_state(ctx, 0);
1105         op_ld_lh(t0, t0, ctx);
1106         gen_store_gpr(t0, rt);
1107         opn = "lh";
1108         break;
1109     case OPC_LHU:
1110         save_cpu_state(ctx, 0);
1111         op_ld_lhu(t0, t0, ctx);
1112         gen_store_gpr(t0, rt);
1113         opn = "lhu";
1114         break;
1115     case OPC_LB:
1116         save_cpu_state(ctx, 0);
1117         op_ld_lb(t0, t0, ctx);
1118         gen_store_gpr(t0, rt);
1119         opn = "lb";
1120         break;
1121     case OPC_LBU:
1122         save_cpu_state(ctx, 0);
1123         op_ld_lbu(t0, t0, ctx);
1124         gen_store_gpr(t0, rt);
1125         opn = "lbu";
1126         break;
1127     case OPC_LWL:
1128         save_cpu_state(ctx, 1);
1129         gen_load_gpr(t1, rt);
1130         gen_helper_3i(lwl, t1, t1, t0, ctx->mem_idx);
1131         gen_store_gpr(t1, rt);
1132         opn = "lwl";
1133         break;
1134     case OPC_LWR:
1135         save_cpu_state(ctx, 1);
1136         gen_load_gpr(t1, rt);
1137         gen_helper_3i(lwr, t1, t1, t0, ctx->mem_idx);
1138         gen_store_gpr(t1, rt);
1139         opn = "lwr";
1140         break;
1141     case OPC_LL:
1142         save_cpu_state(ctx, 1);
1143         op_ld_ll(t0, t0, ctx);
1144         gen_store_gpr(t0, rt);
1145         opn = "ll";
1146         break;
1147     }
1148     (void)opn; /* avoid a compiler warning */
1149     MIPS_DEBUG("%s %s, %d(%s)", opn, regnames[rt], offset, regnames[base]);
1150     tcg_temp_free(t0);
1151     tcg_temp_free(t1);
1152 }
1153
1154 /* Store */
1155 static void gen_st (DisasContext *ctx, uint32_t opc, int rt,
1156                     int base, int16_t offset)
1157 {
1158     const char *opn = "st";
1159     TCGv t0 = tcg_temp_new();
1160     TCGv t1 = tcg_temp_new();
1161
1162     gen_base_offset_addr(ctx, t0, base, offset);
1163     gen_load_gpr(t1, rt);
1164     switch (opc) {
1165 #if defined(TARGET_MIPS64)
1166     case OPC_SD:
1167         save_cpu_state(ctx, 0);
1168         op_st_sd(t1, t0, ctx);
1169         opn = "sd";
1170         break;
1171     case OPC_SDL:
1172         save_cpu_state(ctx, 1);
1173         gen_helper_2i(sdl, t1, t0, ctx->mem_idx);
1174         opn = "sdl";
1175         break;
1176     case OPC_SDR:
1177         save_cpu_state(ctx, 1);
1178         gen_helper_2i(sdr, t1, t0, ctx->mem_idx);
1179         opn = "sdr";
1180         break;
1181 #endif
1182     case OPC_SW:
1183         save_cpu_state(ctx, 0);
1184         op_st_sw(t1, t0, ctx);
1185         opn = "sw";
1186         break;
1187     case OPC_SH:
1188         save_cpu_state(ctx, 0);
1189         op_st_sh(t1, t0, ctx);
1190         opn = "sh";
1191         break;
1192     case OPC_SB:
1193         save_cpu_state(ctx, 0);
1194         op_st_sb(t1, t0, ctx);
1195         opn = "sb";
1196         break;
1197     case OPC_SWL:
1198         save_cpu_state(ctx, 1);
1199         gen_helper_2i(swl, t1, t0, ctx->mem_idx);
1200         opn = "swl";
1201         break;
1202     case OPC_SWR:
1203         save_cpu_state(ctx, 1);
1204         gen_helper_2i(swr, t1, t0, ctx->mem_idx);
1205         opn = "swr";
1206         break;
1207     }
1208     (void)opn; /* avoid a compiler warning */
1209     MIPS_DEBUG("%s %s, %d(%s)", opn, regnames[rt], offset, regnames[base]);
1210     tcg_temp_free(t0);
1211     tcg_temp_free(t1);
1212 }
1213
1214
1215 /* Store conditional */
1216 static void gen_st_cond (DisasContext *ctx, uint32_t opc, int rt,
1217                          int base, int16_t offset)
1218 {
1219     const char *opn = "st_cond";
1220     TCGv t0, t1;
1221
1222     t0 = tcg_temp_local_new();
1223
1224     gen_base_offset_addr(ctx, t0, base, offset);
1225     /* Don't do NOP if destination is zero: we must perform the actual
1226        memory access. */
1227
1228     t1 = tcg_temp_local_new();
1229     gen_load_gpr(t1, rt);
1230     switch (opc) {
1231 #if defined(TARGET_MIPS64)
1232     case OPC_SCD:
1233         save_cpu_state(ctx, 1);
1234         op_st_scd(t1, t0, rt, ctx);
1235         opn = "scd";
1236         break;
1237 #endif
1238     case OPC_SC:
1239         save_cpu_state(ctx, 1);
1240         op_st_sc(t1, t0, rt, ctx);
1241         opn = "sc";
1242         break;
1243     }
1244     (void)opn; /* avoid a compiler warning */
1245     MIPS_DEBUG("%s %s, %d(%s)", opn, regnames[rt], offset, regnames[base]);
1246     tcg_temp_free(t1);
1247     tcg_temp_free(t0);
1248 }
1249
1250 /* Load and store */
1251 static void gen_flt_ldst (DisasContext *ctx, uint32_t opc, int ft,
1252                           int base, int16_t offset)
1253 {
1254     const char *opn = "flt_ldst";
1255     TCGv t0 = tcg_temp_new();
1256
1257     gen_base_offset_addr(ctx, t0, base, offset);
1258     /* Don't do NOP if destination is zero: we must perform the actual
1259        memory access. */
1260     switch (opc) {
1261     case OPC_LWC1:
1262         {
1263             TCGv_i32 fp0 = tcg_temp_new_i32();
1264
1265             tcg_gen_qemu_ld32s(t0, t0, ctx->mem_idx);
1266             tcg_gen_trunc_tl_i32(fp0, t0);
1267             gen_store_fpr32(fp0, ft);
1268             tcg_temp_free_i32(fp0);
1269         }
1270         opn = "lwc1";
1271         break;
1272     case OPC_SWC1:
1273         {
1274             TCGv_i32 fp0 = tcg_temp_new_i32();
1275             TCGv t1 = tcg_temp_new();
1276
1277             gen_load_fpr32(fp0, ft);
1278             tcg_gen_extu_i32_tl(t1, fp0);
1279             tcg_gen_qemu_st32(t1, t0, ctx->mem_idx);
1280             tcg_temp_free(t1);
1281             tcg_temp_free_i32(fp0);
1282         }
1283         opn = "swc1";
1284         break;
1285     case OPC_LDC1:
1286         {
1287             TCGv_i64 fp0 = tcg_temp_new_i64();
1288
1289             tcg_gen_qemu_ld64(fp0, t0, ctx->mem_idx);
1290             gen_store_fpr64(ctx, fp0, ft);
1291             tcg_temp_free_i64(fp0);
1292         }
1293         opn = "ldc1";
1294         break;
1295     case OPC_SDC1:
1296         {
1297             TCGv_i64 fp0 = tcg_temp_new_i64();
1298
1299             gen_load_fpr64(ctx, fp0, ft);
1300             tcg_gen_qemu_st64(fp0, t0, ctx->mem_idx);
1301             tcg_temp_free_i64(fp0);
1302         }
1303         opn = "sdc1";
1304         break;
1305     default:
1306         MIPS_INVAL(opn);
1307         generate_exception(ctx, EXCP_RI);
1308         goto out;
1309     }
1310     (void)opn; /* avoid a compiler warning */
1311     MIPS_DEBUG("%s %s, %d(%s)", opn, fregnames[ft], offset, regnames[base]);
1312  out:
1313     tcg_temp_free(t0);
1314 }
1315
1316 static void gen_cop1_ldst(CPUMIPSState *env, DisasContext *ctx,
1317                           uint32_t op, int rt, int rs, int16_t imm)
1318 {
1319     if (env->CP0_Config1 & (1 << CP0C1_FP)) {
1320         check_cp1_enabled(ctx);
1321         gen_flt_ldst(ctx, op, rt, rs, imm);
1322     } else {
1323         generate_exception_err(ctx, EXCP_CpU, 1);
1324     }
1325 }
1326
1327 /* Arithmetic with immediate operand */
1328 static void gen_arith_imm (CPUMIPSState *env, DisasContext *ctx, uint32_t opc,
1329                            int rt, int rs, int16_t imm)
1330 {
1331     target_ulong uimm = (target_long)imm; /* Sign extend to 32/64 bits */
1332     const char *opn = "imm arith";
1333
1334     if (rt == 0 && opc != OPC_ADDI && opc != OPC_DADDI) {
1335         /* If no destination, treat it as a NOP.
1336            For addi, we must generate the overflow exception when needed. */
1337         MIPS_DEBUG("NOP");
1338         return;
1339     }
1340     switch (opc) {
1341     case OPC_ADDI:
1342         {
1343             TCGv t0 = tcg_temp_local_new();
1344             TCGv t1 = tcg_temp_new();
1345             TCGv t2 = tcg_temp_new();
1346             int l1 = gen_new_label();
1347
1348             gen_load_gpr(t1, rs);
1349             tcg_gen_addi_tl(t0, t1, uimm);
1350             tcg_gen_ext32s_tl(t0, t0);
1351
1352             tcg_gen_xori_tl(t1, t1, ~uimm);
1353             tcg_gen_xori_tl(t2, t0, uimm);
1354             tcg_gen_and_tl(t1, t1, t2);
1355             tcg_temp_free(t2);
1356             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1357             tcg_temp_free(t1);
1358             /* operands of same sign, result different sign */
1359             generate_exception(ctx, EXCP_OVERFLOW);
1360             gen_set_label(l1);
1361             tcg_gen_ext32s_tl(t0, t0);
1362             gen_store_gpr(t0, rt);
1363             tcg_temp_free(t0);
1364         }
1365         opn = "addi";
1366         break;
1367     case OPC_ADDIU:
1368         if (rs != 0) {
1369             tcg_gen_addi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1370             tcg_gen_ext32s_tl(cpu_gpr[rt], cpu_gpr[rt]);
1371         } else {
1372             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1373         }
1374         opn = "addiu";
1375         break;
1376 #if defined(TARGET_MIPS64)
1377     case OPC_DADDI:
1378         {
1379             TCGv t0 = tcg_temp_local_new();
1380             TCGv t1 = tcg_temp_new();
1381             TCGv t2 = tcg_temp_new();
1382             int l1 = gen_new_label();
1383
1384             gen_load_gpr(t1, rs);
1385             tcg_gen_addi_tl(t0, t1, uimm);
1386
1387             tcg_gen_xori_tl(t1, t1, ~uimm);
1388             tcg_gen_xori_tl(t2, t0, uimm);
1389             tcg_gen_and_tl(t1, t1, t2);
1390             tcg_temp_free(t2);
1391             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1392             tcg_temp_free(t1);
1393             /* operands of same sign, result different sign */
1394             generate_exception(ctx, EXCP_OVERFLOW);
1395             gen_set_label(l1);
1396             gen_store_gpr(t0, rt);
1397             tcg_temp_free(t0);
1398         }
1399         opn = "daddi";
1400         break;
1401     case OPC_DADDIU:
1402         if (rs != 0) {
1403             tcg_gen_addi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1404         } else {
1405             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1406         }
1407         opn = "daddiu";
1408         break;
1409 #endif
1410     }
1411     (void)opn; /* avoid a compiler warning */
1412     MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1413 }
1414
1415 /* Logic with immediate operand */
1416 static void gen_logic_imm (CPUMIPSState *env, uint32_t opc, int rt, int rs, int16_t imm)
1417 {
1418     target_ulong uimm;
1419     const char *opn = "imm logic";
1420
1421     if (rt == 0) {
1422         /* If no destination, treat it as a NOP. */
1423         MIPS_DEBUG("NOP");
1424         return;
1425     }
1426     uimm = (uint16_t)imm;
1427     switch (opc) {
1428     case OPC_ANDI:
1429         if (likely(rs != 0))
1430             tcg_gen_andi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1431         else
1432             tcg_gen_movi_tl(cpu_gpr[rt], 0);
1433         opn = "andi";
1434         break;
1435     case OPC_ORI:
1436         if (rs != 0)
1437             tcg_gen_ori_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1438         else
1439             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1440         opn = "ori";
1441         break;
1442     case OPC_XORI:
1443         if (likely(rs != 0))
1444             tcg_gen_xori_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
1445         else
1446             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
1447         opn = "xori";
1448         break;
1449     case OPC_LUI:
1450         tcg_gen_movi_tl(cpu_gpr[rt], imm << 16);
1451         opn = "lui";
1452         break;
1453     }
1454     (void)opn; /* avoid a compiler warning */
1455     MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1456 }
1457
1458 /* Set on less than with immediate operand */
1459 static void gen_slt_imm (CPUMIPSState *env, uint32_t opc, int rt, int rs, int16_t imm)
1460 {
1461     target_ulong uimm = (target_long)imm; /* Sign extend to 32/64 bits */
1462     const char *opn = "imm arith";
1463     TCGv t0;
1464
1465     if (rt == 0) {
1466         /* If no destination, treat it as a NOP. */
1467         MIPS_DEBUG("NOP");
1468         return;
1469     }
1470     t0 = tcg_temp_new();
1471     gen_load_gpr(t0, rs);
1472     switch (opc) {
1473     case OPC_SLTI:
1474         tcg_gen_setcondi_tl(TCG_COND_LT, cpu_gpr[rt], t0, uimm);
1475         opn = "slti";
1476         break;
1477     case OPC_SLTIU:
1478         tcg_gen_setcondi_tl(TCG_COND_LTU, cpu_gpr[rt], t0, uimm);
1479         opn = "sltiu";
1480         break;
1481     }
1482     (void)opn; /* avoid a compiler warning */
1483     MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1484     tcg_temp_free(t0);
1485 }
1486
1487 /* Shifts with immediate operand */
1488 static void gen_shift_imm(CPUMIPSState *env, DisasContext *ctx, uint32_t opc,
1489                           int rt, int rs, int16_t imm)
1490 {
1491     target_ulong uimm = ((uint16_t)imm) & 0x1f;
1492     const char *opn = "imm shift";
1493     TCGv t0;
1494
1495     if (rt == 0) {
1496         /* If no destination, treat it as a NOP. */
1497         MIPS_DEBUG("NOP");
1498         return;
1499     }
1500
1501     t0 = tcg_temp_new();
1502     gen_load_gpr(t0, rs);
1503     switch (opc) {
1504     case OPC_SLL:
1505         tcg_gen_shli_tl(t0, t0, uimm);
1506         tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
1507         opn = "sll";
1508         break;
1509     case OPC_SRA:
1510         tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm);
1511         opn = "sra";
1512         break;
1513     case OPC_SRL:
1514         if (uimm != 0) {
1515             tcg_gen_ext32u_tl(t0, t0);
1516             tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm);
1517         } else {
1518             tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
1519         }
1520         opn = "srl";
1521         break;
1522     case OPC_ROTR:
1523         if (uimm != 0) {
1524             TCGv_i32 t1 = tcg_temp_new_i32();
1525
1526             tcg_gen_trunc_tl_i32(t1, t0);
1527             tcg_gen_rotri_i32(t1, t1, uimm);
1528             tcg_gen_ext_i32_tl(cpu_gpr[rt], t1);
1529             tcg_temp_free_i32(t1);
1530         } else {
1531             tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
1532         }
1533         opn = "rotr";
1534         break;
1535 #if defined(TARGET_MIPS64)
1536     case OPC_DSLL:
1537         tcg_gen_shli_tl(cpu_gpr[rt], t0, uimm);
1538         opn = "dsll";
1539         break;
1540     case OPC_DSRA:
1541         tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm);
1542         opn = "dsra";
1543         break;
1544     case OPC_DSRL:
1545         tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm);
1546         opn = "dsrl";
1547         break;
1548     case OPC_DROTR:
1549         if (uimm != 0) {
1550             tcg_gen_rotri_tl(cpu_gpr[rt], t0, uimm);
1551         } else {
1552             tcg_gen_mov_tl(cpu_gpr[rt], t0);
1553         }
1554         opn = "drotr";
1555         break;
1556     case OPC_DSLL32:
1557         tcg_gen_shli_tl(cpu_gpr[rt], t0, uimm + 32);
1558         opn = "dsll32";
1559         break;
1560     case OPC_DSRA32:
1561         tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm + 32);
1562         opn = "dsra32";
1563         break;
1564     case OPC_DSRL32:
1565         tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm + 32);
1566         opn = "dsrl32";
1567         break;
1568     case OPC_DROTR32:
1569         tcg_gen_rotri_tl(cpu_gpr[rt], t0, uimm + 32);
1570         opn = "drotr32";
1571         break;
1572 #endif
1573     }
1574     (void)opn; /* avoid a compiler warning */
1575     MIPS_DEBUG("%s %s, %s, " TARGET_FMT_lx, opn, regnames[rt], regnames[rs], uimm);
1576     tcg_temp_free(t0);
1577 }
1578
1579 /* Arithmetic */
1580 static void gen_arith (CPUMIPSState *env, DisasContext *ctx, uint32_t opc,
1581                        int rd, int rs, int rt)
1582 {
1583     const char *opn = "arith";
1584
1585     if (rd == 0 && opc != OPC_ADD && opc != OPC_SUB
1586        && opc != OPC_DADD && opc != OPC_DSUB) {
1587         /* If no destination, treat it as a NOP.
1588            For add & sub, we must generate the overflow exception when needed. */
1589         MIPS_DEBUG("NOP");
1590         return;
1591     }
1592
1593     switch (opc) {
1594     case OPC_ADD:
1595         {
1596             TCGv t0 = tcg_temp_local_new();
1597             TCGv t1 = tcg_temp_new();
1598             TCGv t2 = tcg_temp_new();
1599             int l1 = gen_new_label();
1600
1601             gen_load_gpr(t1, rs);
1602             gen_load_gpr(t2, rt);
1603             tcg_gen_add_tl(t0, t1, t2);
1604             tcg_gen_ext32s_tl(t0, t0);
1605             tcg_gen_xor_tl(t1, t1, t2);
1606             tcg_gen_xor_tl(t2, t0, t2);
1607             tcg_gen_andc_tl(t1, t2, t1);
1608             tcg_temp_free(t2);
1609             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1610             tcg_temp_free(t1);
1611             /* operands of same sign, result different sign */
1612             generate_exception(ctx, EXCP_OVERFLOW);
1613             gen_set_label(l1);
1614             gen_store_gpr(t0, rd);
1615             tcg_temp_free(t0);
1616         }
1617         opn = "add";
1618         break;
1619     case OPC_ADDU:
1620         if (rs != 0 && rt != 0) {
1621             tcg_gen_add_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1622             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1623         } else if (rs == 0 && rt != 0) {
1624             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1625         } else if (rs != 0 && rt == 0) {
1626             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1627         } else {
1628             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1629         }
1630         opn = "addu";
1631         break;
1632     case OPC_SUB:
1633         {
1634             TCGv t0 = tcg_temp_local_new();
1635             TCGv t1 = tcg_temp_new();
1636             TCGv t2 = tcg_temp_new();
1637             int l1 = gen_new_label();
1638
1639             gen_load_gpr(t1, rs);
1640             gen_load_gpr(t2, rt);
1641             tcg_gen_sub_tl(t0, t1, t2);
1642             tcg_gen_ext32s_tl(t0, t0);
1643             tcg_gen_xor_tl(t2, t1, t2);
1644             tcg_gen_xor_tl(t1, t0, t1);
1645             tcg_gen_and_tl(t1, t1, t2);
1646             tcg_temp_free(t2);
1647             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1648             tcg_temp_free(t1);
1649             /* operands of different sign, first operand and result different sign */
1650             generate_exception(ctx, EXCP_OVERFLOW);
1651             gen_set_label(l1);
1652             gen_store_gpr(t0, rd);
1653             tcg_temp_free(t0);
1654         }
1655         opn = "sub";
1656         break;
1657     case OPC_SUBU:
1658         if (rs != 0 && rt != 0) {
1659             tcg_gen_sub_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1660             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1661         } else if (rs == 0 && rt != 0) {
1662             tcg_gen_neg_tl(cpu_gpr[rd], cpu_gpr[rt]);
1663             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1664         } else if (rs != 0 && rt == 0) {
1665             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1666         } else {
1667             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1668         }
1669         opn = "subu";
1670         break;
1671 #if defined(TARGET_MIPS64)
1672     case OPC_DADD:
1673         {
1674             TCGv t0 = tcg_temp_local_new();
1675             TCGv t1 = tcg_temp_new();
1676             TCGv t2 = tcg_temp_new();
1677             int l1 = gen_new_label();
1678
1679             gen_load_gpr(t1, rs);
1680             gen_load_gpr(t2, rt);
1681             tcg_gen_add_tl(t0, t1, t2);
1682             tcg_gen_xor_tl(t1, t1, t2);
1683             tcg_gen_xor_tl(t2, t0, t2);
1684             tcg_gen_andc_tl(t1, t2, t1);
1685             tcg_temp_free(t2);
1686             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1687             tcg_temp_free(t1);
1688             /* operands of same sign, result different sign */
1689             generate_exception(ctx, EXCP_OVERFLOW);
1690             gen_set_label(l1);
1691             gen_store_gpr(t0, rd);
1692             tcg_temp_free(t0);
1693         }
1694         opn = "dadd";
1695         break;
1696     case OPC_DADDU:
1697         if (rs != 0 && rt != 0) {
1698             tcg_gen_add_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1699         } else if (rs == 0 && rt != 0) {
1700             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1701         } else if (rs != 0 && rt == 0) {
1702             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1703         } else {
1704             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1705         }
1706         opn = "daddu";
1707         break;
1708     case OPC_DSUB:
1709         {
1710             TCGv t0 = tcg_temp_local_new();
1711             TCGv t1 = tcg_temp_new();
1712             TCGv t2 = tcg_temp_new();
1713             int l1 = gen_new_label();
1714
1715             gen_load_gpr(t1, rs);
1716             gen_load_gpr(t2, rt);
1717             tcg_gen_sub_tl(t0, t1, t2);
1718             tcg_gen_xor_tl(t2, t1, t2);
1719             tcg_gen_xor_tl(t1, t0, t1);
1720             tcg_gen_and_tl(t1, t1, t2);
1721             tcg_temp_free(t2);
1722             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
1723             tcg_temp_free(t1);
1724             /* operands of different sign, first operand and result different sign */
1725             generate_exception(ctx, EXCP_OVERFLOW);
1726             gen_set_label(l1);
1727             gen_store_gpr(t0, rd);
1728             tcg_temp_free(t0);
1729         }
1730         opn = "dsub";
1731         break;
1732     case OPC_DSUBU:
1733         if (rs != 0 && rt != 0) {
1734             tcg_gen_sub_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1735         } else if (rs == 0 && rt != 0) {
1736             tcg_gen_neg_tl(cpu_gpr[rd], cpu_gpr[rt]);
1737         } else if (rs != 0 && rt == 0) {
1738             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1739         } else {
1740             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1741         }
1742         opn = "dsubu";
1743         break;
1744 #endif
1745     case OPC_MUL:
1746         if (likely(rs != 0 && rt != 0)) {
1747             tcg_gen_mul_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1748             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
1749         } else {
1750             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1751         }
1752         opn = "mul";
1753         break;
1754     }
1755     (void)opn; /* avoid a compiler warning */
1756     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1757 }
1758
1759 /* Conditional move */
1760 static void gen_cond_move (CPUMIPSState *env, uint32_t opc, int rd, int rs, int rt)
1761 {
1762     const char *opn = "cond move";
1763     int l1;
1764
1765     if (rd == 0) {
1766         /* If no destination, treat it as a NOP.
1767            For add & sub, we must generate the overflow exception when needed. */
1768         MIPS_DEBUG("NOP");
1769         return;
1770     }
1771
1772     l1 = gen_new_label();
1773     switch (opc) {
1774     case OPC_MOVN:
1775         if (likely(rt != 0))
1776             tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[rt], 0, l1);
1777         else
1778             tcg_gen_br(l1);
1779         opn = "movn";
1780         break;
1781     case OPC_MOVZ:
1782         if (likely(rt != 0))
1783             tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[rt], 0, l1);
1784         opn = "movz";
1785         break;
1786     }
1787     if (rs != 0)
1788         tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1789     else
1790         tcg_gen_movi_tl(cpu_gpr[rd], 0);
1791     gen_set_label(l1);
1792
1793     (void)opn; /* avoid a compiler warning */
1794     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1795 }
1796
1797 /* Logic */
1798 static void gen_logic (CPUMIPSState *env, uint32_t opc, int rd, int rs, int rt)
1799 {
1800     const char *opn = "logic";
1801
1802     if (rd == 0) {
1803         /* If no destination, treat it as a NOP. */
1804         MIPS_DEBUG("NOP");
1805         return;
1806     }
1807
1808     switch (opc) {
1809     case OPC_AND:
1810         if (likely(rs != 0 && rt != 0)) {
1811             tcg_gen_and_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1812         } else {
1813             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1814         }
1815         opn = "and";
1816         break;
1817     case OPC_NOR:
1818         if (rs != 0 && rt != 0) {
1819             tcg_gen_nor_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1820         } else if (rs == 0 && rt != 0) {
1821             tcg_gen_not_tl(cpu_gpr[rd], cpu_gpr[rt]);
1822         } else if (rs != 0 && rt == 0) {
1823             tcg_gen_not_tl(cpu_gpr[rd], cpu_gpr[rs]);
1824         } else {
1825             tcg_gen_movi_tl(cpu_gpr[rd], ~((target_ulong)0));
1826         }
1827         opn = "nor";
1828         break;
1829     case OPC_OR:
1830         if (likely(rs != 0 && rt != 0)) {
1831             tcg_gen_or_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1832         } else if (rs == 0 && rt != 0) {
1833             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1834         } else if (rs != 0 && rt == 0) {
1835             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1836         } else {
1837             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1838         }
1839         opn = "or";
1840         break;
1841     case OPC_XOR:
1842         if (likely(rs != 0 && rt != 0)) {
1843             tcg_gen_xor_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
1844         } else if (rs == 0 && rt != 0) {
1845             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
1846         } else if (rs != 0 && rt == 0) {
1847             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
1848         } else {
1849             tcg_gen_movi_tl(cpu_gpr[rd], 0);
1850         }
1851         opn = "xor";
1852         break;
1853     }
1854     (void)opn; /* avoid a compiler warning */
1855     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1856 }
1857
1858 /* Set on lower than */
1859 static void gen_slt (CPUMIPSState *env, uint32_t opc, int rd, int rs, int rt)
1860 {
1861     const char *opn = "slt";
1862     TCGv t0, t1;
1863
1864     if (rd == 0) {
1865         /* If no destination, treat it as a NOP. */
1866         MIPS_DEBUG("NOP");
1867         return;
1868     }
1869
1870     t0 = tcg_temp_new();
1871     t1 = tcg_temp_new();
1872     gen_load_gpr(t0, rs);
1873     gen_load_gpr(t1, rt);
1874     switch (opc) {
1875     case OPC_SLT:
1876         tcg_gen_setcond_tl(TCG_COND_LT, cpu_gpr[rd], t0, t1);
1877         opn = "slt";
1878         break;
1879     case OPC_SLTU:
1880         tcg_gen_setcond_tl(TCG_COND_LTU, cpu_gpr[rd], t0, t1);
1881         opn = "sltu";
1882         break;
1883     }
1884     (void)opn; /* avoid a compiler warning */
1885     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1886     tcg_temp_free(t0);
1887     tcg_temp_free(t1);
1888 }
1889
1890 /* Shifts */
1891 static void gen_shift (CPUMIPSState *env, DisasContext *ctx, uint32_t opc,
1892                        int rd, int rs, int rt)
1893 {
1894     const char *opn = "shifts";
1895     TCGv t0, t1;
1896
1897     if (rd == 0) {
1898         /* If no destination, treat it as a NOP.
1899            For add & sub, we must generate the overflow exception when needed. */
1900         MIPS_DEBUG("NOP");
1901         return;
1902     }
1903
1904     t0 = tcg_temp_new();
1905     t1 = tcg_temp_new();
1906     gen_load_gpr(t0, rs);
1907     gen_load_gpr(t1, rt);
1908     switch (opc) {
1909     case OPC_SLLV:
1910         tcg_gen_andi_tl(t0, t0, 0x1f);
1911         tcg_gen_shl_tl(t0, t1, t0);
1912         tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
1913         opn = "sllv";
1914         break;
1915     case OPC_SRAV:
1916         tcg_gen_andi_tl(t0, t0, 0x1f);
1917         tcg_gen_sar_tl(cpu_gpr[rd], t1, t0);
1918         opn = "srav";
1919         break;
1920     case OPC_SRLV:
1921         tcg_gen_ext32u_tl(t1, t1);
1922         tcg_gen_andi_tl(t0, t0, 0x1f);
1923         tcg_gen_shr_tl(t0, t1, t0);
1924         tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
1925         opn = "srlv";
1926         break;
1927     case OPC_ROTRV:
1928         {
1929             TCGv_i32 t2 = tcg_temp_new_i32();
1930             TCGv_i32 t3 = tcg_temp_new_i32();
1931
1932             tcg_gen_trunc_tl_i32(t2, t0);
1933             tcg_gen_trunc_tl_i32(t3, t1);
1934             tcg_gen_andi_i32(t2, t2, 0x1f);
1935             tcg_gen_rotr_i32(t2, t3, t2);
1936             tcg_gen_ext_i32_tl(cpu_gpr[rd], t2);
1937             tcg_temp_free_i32(t2);
1938             tcg_temp_free_i32(t3);
1939             opn = "rotrv";
1940         }
1941         break;
1942 #if defined(TARGET_MIPS64)
1943     case OPC_DSLLV:
1944         tcg_gen_andi_tl(t0, t0, 0x3f);
1945         tcg_gen_shl_tl(cpu_gpr[rd], t1, t0);
1946         opn = "dsllv";
1947         break;
1948     case OPC_DSRAV:
1949         tcg_gen_andi_tl(t0, t0, 0x3f);
1950         tcg_gen_sar_tl(cpu_gpr[rd], t1, t0);
1951         opn = "dsrav";
1952         break;
1953     case OPC_DSRLV:
1954         tcg_gen_andi_tl(t0, t0, 0x3f);
1955         tcg_gen_shr_tl(cpu_gpr[rd], t1, t0);
1956         opn = "dsrlv";
1957         break;
1958     case OPC_DROTRV:
1959         tcg_gen_andi_tl(t0, t0, 0x3f);
1960         tcg_gen_rotr_tl(cpu_gpr[rd], t1, t0);
1961         opn = "drotrv";
1962         break;
1963 #endif
1964     }
1965     (void)opn; /* avoid a compiler warning */
1966     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
1967     tcg_temp_free(t0);
1968     tcg_temp_free(t1);
1969 }
1970
1971 /* Arithmetic on HI/LO registers */
1972 static void gen_HILO (DisasContext *ctx, uint32_t opc, int reg)
1973 {
1974     const char *opn = "hilo";
1975
1976     if (reg == 0 && (opc == OPC_MFHI || opc == OPC_MFLO)) {
1977         /* Treat as NOP. */
1978         MIPS_DEBUG("NOP");
1979         return;
1980     }
1981     switch (opc) {
1982     case OPC_MFHI:
1983         tcg_gen_mov_tl(cpu_gpr[reg], cpu_HI[0]);
1984         opn = "mfhi";
1985         break;
1986     case OPC_MFLO:
1987         tcg_gen_mov_tl(cpu_gpr[reg], cpu_LO[0]);
1988         opn = "mflo";
1989         break;
1990     case OPC_MTHI:
1991         if (reg != 0)
1992             tcg_gen_mov_tl(cpu_HI[0], cpu_gpr[reg]);
1993         else
1994             tcg_gen_movi_tl(cpu_HI[0], 0);
1995         opn = "mthi";
1996         break;
1997     case OPC_MTLO:
1998         if (reg != 0)
1999             tcg_gen_mov_tl(cpu_LO[0], cpu_gpr[reg]);
2000         else
2001             tcg_gen_movi_tl(cpu_LO[0], 0);
2002         opn = "mtlo";
2003         break;
2004     }
2005     (void)opn; /* avoid a compiler warning */
2006     MIPS_DEBUG("%s %s", opn, regnames[reg]);
2007 }
2008
2009 static void gen_muldiv (DisasContext *ctx, uint32_t opc,
2010                         int rs, int rt)
2011 {
2012     const char *opn = "mul/div";
2013     TCGv t0, t1;
2014
2015     switch (opc) {
2016     case OPC_DIV:
2017     case OPC_DIVU:
2018 #if defined(TARGET_MIPS64)
2019     case OPC_DDIV:
2020     case OPC_DDIVU:
2021 #endif
2022         t0 = tcg_temp_local_new();
2023         t1 = tcg_temp_local_new();
2024         break;
2025     default:
2026         t0 = tcg_temp_new();
2027         t1 = tcg_temp_new();
2028         break;
2029     }
2030
2031     gen_load_gpr(t0, rs);
2032     gen_load_gpr(t1, rt);
2033     switch (opc) {
2034     case OPC_DIV:
2035         {
2036             int l1 = gen_new_label();
2037             int l2 = gen_new_label();
2038
2039             tcg_gen_ext32s_tl(t0, t0);
2040             tcg_gen_ext32s_tl(t1, t1);
2041             tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2042             tcg_gen_brcondi_tl(TCG_COND_NE, t0, INT_MIN, l2);
2043             tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1, l2);
2044
2045             tcg_gen_mov_tl(cpu_LO[0], t0);
2046             tcg_gen_movi_tl(cpu_HI[0], 0);
2047             tcg_gen_br(l1);
2048             gen_set_label(l2);
2049             tcg_gen_div_tl(cpu_LO[0], t0, t1);
2050             tcg_gen_rem_tl(cpu_HI[0], t0, t1);
2051             tcg_gen_ext32s_tl(cpu_LO[0], cpu_LO[0]);
2052             tcg_gen_ext32s_tl(cpu_HI[0], cpu_HI[0]);
2053             gen_set_label(l1);
2054         }
2055         opn = "div";
2056         break;
2057     case OPC_DIVU:
2058         {
2059             int l1 = gen_new_label();
2060
2061             tcg_gen_ext32u_tl(t0, t0);
2062             tcg_gen_ext32u_tl(t1, t1);
2063             tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2064             tcg_gen_divu_tl(cpu_LO[0], t0, t1);
2065             tcg_gen_remu_tl(cpu_HI[0], t0, t1);
2066             tcg_gen_ext32s_tl(cpu_LO[0], cpu_LO[0]);
2067             tcg_gen_ext32s_tl(cpu_HI[0], cpu_HI[0]);
2068             gen_set_label(l1);
2069         }
2070         opn = "divu";
2071         break;
2072     case OPC_MULT:
2073         {
2074             TCGv_i64 t2 = tcg_temp_new_i64();
2075             TCGv_i64 t3 = tcg_temp_new_i64();
2076
2077             tcg_gen_ext_tl_i64(t2, t0);
2078             tcg_gen_ext_tl_i64(t3, t1);
2079             tcg_gen_mul_i64(t2, t2, t3);
2080             tcg_temp_free_i64(t3);
2081             tcg_gen_trunc_i64_tl(t0, t2);
2082             tcg_gen_shri_i64(t2, t2, 32);
2083             tcg_gen_trunc_i64_tl(t1, t2);
2084             tcg_temp_free_i64(t2);
2085             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2086             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2087         }
2088         opn = "mult";
2089         break;
2090     case OPC_MULTU:
2091         {
2092             TCGv_i64 t2 = tcg_temp_new_i64();
2093             TCGv_i64 t3 = tcg_temp_new_i64();
2094
2095             tcg_gen_ext32u_tl(t0, t0);
2096             tcg_gen_ext32u_tl(t1, t1);
2097             tcg_gen_extu_tl_i64(t2, t0);
2098             tcg_gen_extu_tl_i64(t3, t1);
2099             tcg_gen_mul_i64(t2, t2, t3);
2100             tcg_temp_free_i64(t3);
2101             tcg_gen_trunc_i64_tl(t0, t2);
2102             tcg_gen_shri_i64(t2, t2, 32);
2103             tcg_gen_trunc_i64_tl(t1, t2);
2104             tcg_temp_free_i64(t2);
2105             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2106             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2107         }
2108         opn = "multu";
2109         break;
2110 #if defined(TARGET_MIPS64)
2111     case OPC_DDIV:
2112         {
2113             int l1 = gen_new_label();
2114             int l2 = gen_new_label();
2115
2116             tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2117             tcg_gen_brcondi_tl(TCG_COND_NE, t0, -1LL << 63, l2);
2118             tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1LL, l2);
2119             tcg_gen_mov_tl(cpu_LO[0], t0);
2120             tcg_gen_movi_tl(cpu_HI[0], 0);
2121             tcg_gen_br(l1);
2122             gen_set_label(l2);
2123             tcg_gen_div_i64(cpu_LO[0], t0, t1);
2124             tcg_gen_rem_i64(cpu_HI[0], t0, t1);
2125             gen_set_label(l1);
2126         }
2127         opn = "ddiv";
2128         break;
2129     case OPC_DDIVU:
2130         {
2131             int l1 = gen_new_label();
2132
2133             tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2134             tcg_gen_divu_i64(cpu_LO[0], t0, t1);
2135             tcg_gen_remu_i64(cpu_HI[0], t0, t1);
2136             gen_set_label(l1);
2137         }
2138         opn = "ddivu";
2139         break;
2140     case OPC_DMULT:
2141         gen_helper_dmult(t0, t1);
2142         opn = "dmult";
2143         break;
2144     case OPC_DMULTU:
2145         gen_helper_dmultu(t0, t1);
2146         opn = "dmultu";
2147         break;
2148 #endif
2149     case OPC_MADD:
2150         {
2151             TCGv_i64 t2 = tcg_temp_new_i64();
2152             TCGv_i64 t3 = tcg_temp_new_i64();
2153
2154             tcg_gen_ext_tl_i64(t2, t0);
2155             tcg_gen_ext_tl_i64(t3, t1);
2156             tcg_gen_mul_i64(t2, t2, t3);
2157             tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2158             tcg_gen_add_i64(t2, t2, t3);
2159             tcg_temp_free_i64(t3);
2160             tcg_gen_trunc_i64_tl(t0, t2);
2161             tcg_gen_shri_i64(t2, t2, 32);
2162             tcg_gen_trunc_i64_tl(t1, t2);
2163             tcg_temp_free_i64(t2);
2164             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2165             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2166         }
2167         opn = "madd";
2168         break;
2169     case OPC_MADDU:
2170        {
2171             TCGv_i64 t2 = tcg_temp_new_i64();
2172             TCGv_i64 t3 = tcg_temp_new_i64();
2173
2174             tcg_gen_ext32u_tl(t0, t0);
2175             tcg_gen_ext32u_tl(t1, t1);
2176             tcg_gen_extu_tl_i64(t2, t0);
2177             tcg_gen_extu_tl_i64(t3, t1);
2178             tcg_gen_mul_i64(t2, t2, t3);
2179             tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2180             tcg_gen_add_i64(t2, t2, t3);
2181             tcg_temp_free_i64(t3);
2182             tcg_gen_trunc_i64_tl(t0, t2);
2183             tcg_gen_shri_i64(t2, t2, 32);
2184             tcg_gen_trunc_i64_tl(t1, t2);
2185             tcg_temp_free_i64(t2);
2186             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2187             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2188         }
2189         opn = "maddu";
2190         break;
2191     case OPC_MSUB:
2192         {
2193             TCGv_i64 t2 = tcg_temp_new_i64();
2194             TCGv_i64 t3 = tcg_temp_new_i64();
2195
2196             tcg_gen_ext_tl_i64(t2, t0);
2197             tcg_gen_ext_tl_i64(t3, t1);
2198             tcg_gen_mul_i64(t2, t2, t3);
2199             tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2200             tcg_gen_sub_i64(t2, t3, t2);
2201             tcg_temp_free_i64(t3);
2202             tcg_gen_trunc_i64_tl(t0, t2);
2203             tcg_gen_shri_i64(t2, t2, 32);
2204             tcg_gen_trunc_i64_tl(t1, t2);
2205             tcg_temp_free_i64(t2);
2206             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2207             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2208         }
2209         opn = "msub";
2210         break;
2211     case OPC_MSUBU:
2212         {
2213             TCGv_i64 t2 = tcg_temp_new_i64();
2214             TCGv_i64 t3 = tcg_temp_new_i64();
2215
2216             tcg_gen_ext32u_tl(t0, t0);
2217             tcg_gen_ext32u_tl(t1, t1);
2218             tcg_gen_extu_tl_i64(t2, t0);
2219             tcg_gen_extu_tl_i64(t3, t1);
2220             tcg_gen_mul_i64(t2, t2, t3);
2221             tcg_gen_concat_tl_i64(t3, cpu_LO[0], cpu_HI[0]);
2222             tcg_gen_sub_i64(t2, t3, t2);
2223             tcg_temp_free_i64(t3);
2224             tcg_gen_trunc_i64_tl(t0, t2);
2225             tcg_gen_shri_i64(t2, t2, 32);
2226             tcg_gen_trunc_i64_tl(t1, t2);
2227             tcg_temp_free_i64(t2);
2228             tcg_gen_ext32s_tl(cpu_LO[0], t0);
2229             tcg_gen_ext32s_tl(cpu_HI[0], t1);
2230         }
2231         opn = "msubu";
2232         break;
2233     default:
2234         MIPS_INVAL(opn);
2235         generate_exception(ctx, EXCP_RI);
2236         goto out;
2237     }
2238     (void)opn; /* avoid a compiler warning */
2239     MIPS_DEBUG("%s %s %s", opn, regnames[rs], regnames[rt]);
2240  out:
2241     tcg_temp_free(t0);
2242     tcg_temp_free(t1);
2243 }
2244
2245 static void gen_mul_vr54xx (DisasContext *ctx, uint32_t opc,
2246                             int rd, int rs, int rt)
2247 {
2248     const char *opn = "mul vr54xx";
2249     TCGv t0 = tcg_temp_new();
2250     TCGv t1 = tcg_temp_new();
2251
2252     gen_load_gpr(t0, rs);
2253     gen_load_gpr(t1, rt);
2254
2255     switch (opc) {
2256     case OPC_VR54XX_MULS:
2257         gen_helper_muls(t0, t0, t1);
2258         opn = "muls";
2259         break;
2260     case OPC_VR54XX_MULSU:
2261         gen_helper_mulsu(t0, t0, t1);
2262         opn = "mulsu";
2263         break;
2264     case OPC_VR54XX_MACC:
2265         gen_helper_macc(t0, t0, t1);
2266         opn = "macc";
2267         break;
2268     case OPC_VR54XX_MACCU:
2269         gen_helper_maccu(t0, t0, t1);
2270         opn = "maccu";
2271         break;
2272     case OPC_VR54XX_MSAC:
2273         gen_helper_msac(t0, t0, t1);
2274         opn = "msac";
2275         break;
2276     case OPC_VR54XX_MSACU:
2277         gen_helper_msacu(t0, t0, t1);
2278         opn = "msacu";
2279         break;
2280     case OPC_VR54XX_MULHI:
2281         gen_helper_mulhi(t0, t0, t1);
2282         opn = "mulhi";
2283         break;
2284     case OPC_VR54XX_MULHIU:
2285         gen_helper_mulhiu(t0, t0, t1);
2286         opn = "mulhiu";
2287         break;
2288     case OPC_VR54XX_MULSHI:
2289         gen_helper_mulshi(t0, t0, t1);
2290         opn = "mulshi";
2291         break;
2292     case OPC_VR54XX_MULSHIU:
2293         gen_helper_mulshiu(t0, t0, t1);
2294         opn = "mulshiu";
2295         break;
2296     case OPC_VR54XX_MACCHI:
2297         gen_helper_macchi(t0, t0, t1);
2298         opn = "macchi";
2299         break;
2300     case OPC_VR54XX_MACCHIU:
2301         gen_helper_macchiu(t0, t0, t1);
2302         opn = "macchiu";
2303         break;
2304     case OPC_VR54XX_MSACHI:
2305         gen_helper_msachi(t0, t0, t1);
2306         opn = "msachi";
2307         break;
2308     case OPC_VR54XX_MSACHIU:
2309         gen_helper_msachiu(t0, t0, t1);
2310         opn = "msachiu";
2311         break;
2312     default:
2313         MIPS_INVAL("mul vr54xx");
2314         generate_exception(ctx, EXCP_RI);
2315         goto out;
2316     }
2317     gen_store_gpr(t0, rd);
2318     (void)opn; /* avoid a compiler warning */
2319     MIPS_DEBUG("%s %s, %s, %s", opn, regnames[rd], regnames[rs], regnames[rt]);
2320
2321  out:
2322     tcg_temp_free(t0);
2323     tcg_temp_free(t1);
2324 }
2325
2326 static void gen_cl (DisasContext *ctx, uint32_t opc,
2327                     int rd, int rs)
2328 {
2329     const char *opn = "CLx";
2330     TCGv t0;
2331
2332     if (rd == 0) {
2333         /* Treat as NOP. */
2334         MIPS_DEBUG("NOP");
2335         return;
2336     }
2337     t0 = tcg_temp_new();
2338     gen_load_gpr(t0, rs);
2339     switch (opc) {
2340     case OPC_CLO:
2341         gen_helper_clo(cpu_gpr[rd], t0);
2342         opn = "clo";
2343         break;
2344     case OPC_CLZ:
2345         gen_helper_clz(cpu_gpr[rd], t0);
2346         opn = "clz";
2347         break;
2348 #if defined(TARGET_MIPS64)
2349     case OPC_DCLO:
2350         gen_helper_dclo(cpu_gpr[rd], t0);
2351         opn = "dclo";
2352         break;
2353     case OPC_DCLZ:
2354         gen_helper_dclz(cpu_gpr[rd], t0);
2355         opn = "dclz";
2356         break;
2357 #endif
2358     }
2359     (void)opn; /* avoid a compiler warning */
2360     MIPS_DEBUG("%s %s, %s", opn, regnames[rd], regnames[rs]);
2361     tcg_temp_free(t0);
2362 }
2363
2364 /* Godson integer instructions */
2365 static void gen_loongson_integer (DisasContext *ctx, uint32_t opc,
2366                                 int rd, int rs, int rt)
2367 {
2368     const char *opn = "loongson";
2369     TCGv t0, t1;
2370
2371     if (rd == 0) {
2372         /* Treat as NOP. */
2373         MIPS_DEBUG("NOP");
2374         return;
2375     }
2376
2377     switch (opc) {
2378     case OPC_MULT_G_2E:
2379     case OPC_MULT_G_2F:
2380     case OPC_MULTU_G_2E:
2381     case OPC_MULTU_G_2F:
2382 #if defined(TARGET_MIPS64)
2383     case OPC_DMULT_G_2E:
2384     case OPC_DMULT_G_2F:
2385     case OPC_DMULTU_G_2E:
2386     case OPC_DMULTU_G_2F:
2387 #endif
2388         t0 = tcg_temp_new();
2389         t1 = tcg_temp_new();
2390         break;
2391     default:
2392         t0 = tcg_temp_local_new();
2393         t1 = tcg_temp_local_new();
2394         break;
2395     }
2396
2397     gen_load_gpr(t0, rs);
2398     gen_load_gpr(t1, rt);
2399
2400     switch (opc) {
2401     case OPC_MULT_G_2E:
2402     case OPC_MULT_G_2F:
2403         tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
2404         tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2405         opn = "mult.g";
2406         break;
2407     case OPC_MULTU_G_2E:
2408     case OPC_MULTU_G_2F:
2409         tcg_gen_ext32u_tl(t0, t0);
2410         tcg_gen_ext32u_tl(t1, t1);
2411         tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
2412         tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2413         opn = "multu.g";
2414         break;
2415     case OPC_DIV_G_2E:
2416     case OPC_DIV_G_2F:
2417         {
2418             int l1 = gen_new_label();
2419             int l2 = gen_new_label();
2420             int l3 = gen_new_label();
2421             tcg_gen_ext32s_tl(t0, t0);
2422             tcg_gen_ext32s_tl(t1, t1);
2423             tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2424             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2425             tcg_gen_br(l3);
2426             gen_set_label(l1);
2427             tcg_gen_brcondi_tl(TCG_COND_NE, t0, INT_MIN, l2);
2428             tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1, l2);
2429             tcg_gen_mov_tl(cpu_gpr[rd], t0);
2430             tcg_gen_br(l3);
2431             gen_set_label(l2);
2432             tcg_gen_div_tl(cpu_gpr[rd], t0, t1);
2433             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2434             gen_set_label(l3);
2435         }
2436         opn = "div.g";
2437         break;
2438     case OPC_DIVU_G_2E:
2439     case OPC_DIVU_G_2F:
2440         {
2441             int l1 = gen_new_label();
2442             int l2 = gen_new_label();
2443             tcg_gen_ext32u_tl(t0, t0);
2444             tcg_gen_ext32u_tl(t1, t1);
2445             tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2446             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2447             tcg_gen_br(l2);
2448             gen_set_label(l1);
2449             tcg_gen_divu_tl(cpu_gpr[rd], t0, t1);
2450             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2451             gen_set_label(l2);
2452         }
2453         opn = "divu.g";
2454         break;
2455     case OPC_MOD_G_2E:
2456     case OPC_MOD_G_2F:
2457         {
2458             int l1 = gen_new_label();
2459             int l2 = gen_new_label();
2460             int l3 = gen_new_label();
2461             tcg_gen_ext32u_tl(t0, t0);
2462             tcg_gen_ext32u_tl(t1, t1);
2463             tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2464             tcg_gen_brcondi_tl(TCG_COND_NE, t0, INT_MIN, l2);
2465             tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1, l2);
2466             gen_set_label(l1);
2467             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2468             tcg_gen_br(l3);
2469             gen_set_label(l2);
2470             tcg_gen_rem_tl(cpu_gpr[rd], t0, t1);
2471             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2472             gen_set_label(l3);
2473         }
2474         opn = "mod.g";
2475         break;
2476     case OPC_MODU_G_2E:
2477     case OPC_MODU_G_2F:
2478         {
2479             int l1 = gen_new_label();
2480             int l2 = gen_new_label();
2481             tcg_gen_ext32u_tl(t0, t0);
2482             tcg_gen_ext32u_tl(t1, t1);
2483             tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2484             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2485             tcg_gen_br(l2);
2486             gen_set_label(l1);
2487             tcg_gen_remu_tl(cpu_gpr[rd], t0, t1);
2488             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2489             gen_set_label(l2);
2490         }
2491         opn = "modu.g";
2492         break;
2493 #if defined(TARGET_MIPS64)
2494     case OPC_DMULT_G_2E:
2495     case OPC_DMULT_G_2F:
2496         tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
2497         opn = "dmult.g";
2498         break;
2499     case OPC_DMULTU_G_2E:
2500     case OPC_DMULTU_G_2F:
2501         tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
2502         opn = "dmultu.g";
2503         break;
2504     case OPC_DDIV_G_2E:
2505     case OPC_DDIV_G_2F:
2506         {
2507             int l1 = gen_new_label();
2508             int l2 = gen_new_label();
2509             int l3 = gen_new_label();
2510             tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2511             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2512             tcg_gen_br(l3);
2513             gen_set_label(l1);
2514             tcg_gen_brcondi_tl(TCG_COND_NE, t0, -1LL << 63, l2);
2515             tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1LL, l2);
2516             tcg_gen_mov_tl(cpu_gpr[rd], t0);
2517             tcg_gen_br(l3);
2518             gen_set_label(l2);
2519             tcg_gen_div_tl(cpu_gpr[rd], t0, t1);
2520             gen_set_label(l3);
2521         }
2522         opn = "ddiv.g";
2523         break;
2524     case OPC_DDIVU_G_2E:
2525     case OPC_DDIVU_G_2F:
2526         {
2527             int l1 = gen_new_label();
2528             int l2 = gen_new_label();
2529             tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2530             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2531             tcg_gen_br(l2);
2532             gen_set_label(l1);
2533             tcg_gen_divu_tl(cpu_gpr[rd], t0, t1);
2534             gen_set_label(l2);
2535         }
2536         opn = "ddivu.g";
2537         break;
2538     case OPC_DMOD_G_2E:
2539     case OPC_DMOD_G_2F:
2540         {
2541             int l1 = gen_new_label();
2542             int l2 = gen_new_label();
2543             int l3 = gen_new_label();
2544             tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
2545             tcg_gen_brcondi_tl(TCG_COND_NE, t0, -1LL << 63, l2);
2546             tcg_gen_brcondi_tl(TCG_COND_NE, t1, -1LL, l2);
2547             gen_set_label(l1);
2548             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2549             tcg_gen_br(l3);
2550             gen_set_label(l2);
2551             tcg_gen_rem_tl(cpu_gpr[rd], t0, t1);
2552             gen_set_label(l3);
2553         }
2554         opn = "dmod.g";
2555         break;
2556     case OPC_DMODU_G_2E:
2557     case OPC_DMODU_G_2F:
2558         {
2559             int l1 = gen_new_label();
2560             int l2 = gen_new_label();
2561             tcg_gen_brcondi_tl(TCG_COND_NE, t1, 0, l1);
2562             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2563             tcg_gen_br(l2);
2564             gen_set_label(l1);
2565             tcg_gen_remu_tl(cpu_gpr[rd], t0, t1);
2566             gen_set_label(l2);
2567         }
2568         opn = "dmodu.g";
2569         break;
2570 #endif
2571     }
2572
2573     (void)opn; /* avoid a compiler warning */
2574     MIPS_DEBUG("%s %s, %s", opn, regnames[rd], regnames[rs]);
2575     tcg_temp_free(t0);
2576     tcg_temp_free(t1);
2577 }
2578
2579 /* Traps */
2580 static void gen_trap (DisasContext *ctx, uint32_t opc,
2581                       int rs, int rt, int16_t imm)
2582 {
2583     int cond;
2584     TCGv t0 = tcg_temp_new();
2585     TCGv t1 = tcg_temp_new();
2586
2587     cond = 0;
2588     /* Load needed operands */
2589     switch (opc) {
2590     case OPC_TEQ:
2591     case OPC_TGE:
2592     case OPC_TGEU:
2593     case OPC_TLT:
2594     case OPC_TLTU:
2595     case OPC_TNE:
2596         /* Compare two registers */
2597         if (rs != rt) {
2598             gen_load_gpr(t0, rs);
2599             gen_load_gpr(t1, rt);
2600             cond = 1;
2601         }
2602         break;
2603     case OPC_TEQI:
2604     case OPC_TGEI:
2605     case OPC_TGEIU:
2606     case OPC_TLTI:
2607     case OPC_TLTIU:
2608     case OPC_TNEI:
2609         /* Compare register to immediate */
2610         if (rs != 0 || imm != 0) {
2611             gen_load_gpr(t0, rs);
2612             tcg_gen_movi_tl(t1, (int32_t)imm);
2613             cond = 1;
2614         }
2615         break;
2616     }
2617     if (cond == 0) {
2618         switch (opc) {
2619         case OPC_TEQ:   /* rs == rs */
2620         case OPC_TEQI:  /* r0 == 0  */
2621         case OPC_TGE:   /* rs >= rs */
2622         case OPC_TGEI:  /* r0 >= 0  */
2623         case OPC_TGEU:  /* rs >= rs unsigned */
2624         case OPC_TGEIU: /* r0 >= 0  unsigned */
2625             /* Always trap */
2626             generate_exception(ctx, EXCP_TRAP);
2627             break;
2628         case OPC_TLT:   /* rs < rs           */
2629         case OPC_TLTI:  /* r0 < 0            */
2630         case OPC_TLTU:  /* rs < rs unsigned  */
2631         case OPC_TLTIU: /* r0 < 0  unsigned  */
2632         case OPC_TNE:   /* rs != rs          */
2633         case OPC_TNEI:  /* r0 != 0           */
2634             /* Never trap: treat as NOP. */
2635             break;
2636         }
2637     } else {
2638         int l1 = gen_new_label();
2639
2640         switch (opc) {
2641         case OPC_TEQ:
2642         case OPC_TEQI:
2643             tcg_gen_brcond_tl(TCG_COND_NE, t0, t1, l1);
2644             break;
2645         case OPC_TGE:
2646         case OPC_TGEI:
2647             tcg_gen_brcond_tl(TCG_COND_LT, t0, t1, l1);
2648             break;
2649         case OPC_TGEU:
2650         case OPC_TGEIU:
2651             tcg_gen_brcond_tl(TCG_COND_LTU, t0, t1, l1);
2652             break;
2653         case OPC_TLT:
2654         case OPC_TLTI:
2655             tcg_gen_brcond_tl(TCG_COND_GE, t0, t1, l1);
2656             break;
2657         case OPC_TLTU:
2658         case OPC_TLTIU:
2659             tcg_gen_brcond_tl(TCG_COND_GEU, t0, t1, l1);
2660             break;
2661         case OPC_TNE:
2662         case OPC_TNEI:
2663             tcg_gen_brcond_tl(TCG_COND_EQ, t0, t1, l1);
2664             break;
2665         }
2666         generate_exception(ctx, EXCP_TRAP);
2667         gen_set_label(l1);
2668     }
2669     tcg_temp_free(t0);
2670     tcg_temp_free(t1);
2671 }
2672
2673 static inline void gen_goto_tb(DisasContext *ctx, int n, target_ulong dest)
2674 {
2675     TranslationBlock *tb;
2676     tb = ctx->tb;
2677     if ((tb->pc & TARGET_PAGE_MASK) == (dest & TARGET_PAGE_MASK) &&
2678         likely(!ctx->singlestep_enabled)) {
2679         tcg_gen_goto_tb(n);
2680         gen_save_pc(dest);
2681         tcg_gen_exit_tb((tcg_target_long)tb + n);
2682     } else {
2683         gen_save_pc(dest);
2684         if (ctx->singlestep_enabled) {
2685             save_cpu_state(ctx, 0);
2686             gen_helper_0i(raise_exception, EXCP_DEBUG);
2687         }
2688         tcg_gen_exit_tb(0);
2689     }
2690 }
2691
2692 /* Branches (before delay slot) */
2693 static void gen_compute_branch (DisasContext *ctx, uint32_t opc,
2694                                 int insn_bytes,
2695                                 int rs, int rt, int32_t offset)
2696 {
2697     target_ulong btgt = -1;
2698     int blink = 0;
2699     int bcond_compute = 0;
2700     TCGv t0 = tcg_temp_new();
2701     TCGv t1 = tcg_temp_new();
2702
2703     if (ctx->hflags & MIPS_HFLAG_BMASK) {
2704 #ifdef MIPS_DEBUG_DISAS
2705         LOG_DISAS("Branch in delay slot at PC 0x" TARGET_FMT_lx "\n", ctx->pc);
2706 #endif
2707         generate_exception(ctx, EXCP_RI);
2708         goto out;
2709     }
2710
2711     /* Load needed operands */
2712     switch (opc) {
2713     case OPC_BEQ:
2714     case OPC_BEQL:
2715     case OPC_BNE:
2716     case OPC_BNEL:
2717         /* Compare two registers */
2718         if (rs != rt) {
2719             gen_load_gpr(t0, rs);
2720             gen_load_gpr(t1, rt);
2721             bcond_compute = 1;
2722         }
2723         btgt = ctx->pc + insn_bytes + offset;
2724         break;
2725     case OPC_BGEZ:
2726     case OPC_BGEZAL:
2727     case OPC_BGEZALS:
2728     case OPC_BGEZALL:
2729     case OPC_BGEZL:
2730     case OPC_BGTZ:
2731     case OPC_BGTZL:
2732     case OPC_BLEZ:
2733     case OPC_BLEZL:
2734     case OPC_BLTZ:
2735     case OPC_BLTZAL:
2736     case OPC_BLTZALS:
2737     case OPC_BLTZALL:
2738     case OPC_BLTZL:
2739         /* Compare to zero */
2740         if (rs != 0) {
2741             gen_load_gpr(t0, rs);
2742             bcond_compute = 1;
2743         }
2744         btgt = ctx->pc + insn_bytes + offset;
2745         break;
2746     case OPC_J:
2747     case OPC_JAL:
2748     case OPC_JALX:
2749     case OPC_JALS:
2750     case OPC_JALXS:
2751         /* Jump to immediate */
2752         btgt = ((ctx->pc + insn_bytes) & (int32_t)0xF0000000) | (uint32_t)offset;
2753         break;
2754     case OPC_JR:
2755     case OPC_JALR:
2756     case OPC_JALRC:
2757     case OPC_JALRS:
2758         /* Jump to register */
2759         if (offset != 0 && offset != 16) {
2760             /* Hint = 0 is JR/JALR, hint 16 is JR.HB/JALR.HB, the
2761                others are reserved. */
2762             MIPS_INVAL("jump hint");
2763             generate_exception(ctx, EXCP_RI);
2764             goto out;
2765         }
2766         gen_load_gpr(btarget, rs);
2767         break;
2768     default:
2769         MIPS_INVAL("branch/jump");
2770         generate_exception(ctx, EXCP_RI);
2771         goto out;
2772     }
2773     if (bcond_compute == 0) {
2774         /* No condition to be computed */
2775         switch (opc) {
2776         case OPC_BEQ:     /* rx == rx        */
2777         case OPC_BEQL:    /* rx == rx likely */
2778         case OPC_BGEZ:    /* 0 >= 0          */
2779         case OPC_BGEZL:   /* 0 >= 0 likely   */
2780         case OPC_BLEZ:    /* 0 <= 0          */
2781         case OPC_BLEZL:   /* 0 <= 0 likely   */
2782             /* Always take */
2783             ctx->hflags |= MIPS_HFLAG_B;
2784             MIPS_DEBUG("balways");
2785             break;
2786         case OPC_BGEZALS:
2787         case OPC_BGEZAL:  /* 0 >= 0          */
2788         case OPC_BGEZALL: /* 0 >= 0 likely   */
2789             ctx->hflags |= (opc == OPC_BGEZALS
2790                             ? MIPS_HFLAG_BDS16
2791                             : MIPS_HFLAG_BDS32);
2792             /* Always take and link */
2793             blink = 31;
2794             ctx->hflags |= MIPS_HFLAG_B;
2795             MIPS_DEBUG("balways and link");
2796             break;
2797         case OPC_BNE:     /* rx != rx        */
2798         case OPC_BGTZ:    /* 0 > 0           */
2799         case OPC_BLTZ:    /* 0 < 0           */
2800             /* Treat as NOP. */
2801             MIPS_DEBUG("bnever (NOP)");
2802             goto out;
2803         case OPC_BLTZALS:
2804         case OPC_BLTZAL:  /* 0 < 0           */
2805             ctx->hflags |= (opc == OPC_BLTZALS
2806                             ? MIPS_HFLAG_BDS16
2807                             : MIPS_HFLAG_BDS32);
2808             /* Handle as an unconditional branch to get correct delay
2809                slot checking.  */
2810             blink = 31;
2811             btgt = ctx->pc + (opc == OPC_BLTZALS ? 6 : 8);
2812             ctx->hflags |= MIPS_HFLAG_B;
2813             MIPS_DEBUG("bnever and link");
2814             break;
2815         case OPC_BLTZALL: /* 0 < 0 likely */
2816             tcg_gen_movi_tl(cpu_gpr[31], ctx->pc + 8);
2817             /* Skip the instruction in the delay slot */
2818             MIPS_DEBUG("bnever, link and skip");
2819             ctx->pc += 4;
2820             goto out;
2821         case OPC_BNEL:    /* rx != rx likely */
2822         case OPC_BGTZL:   /* 0 > 0 likely */
2823         case OPC_BLTZL:   /* 0 < 0 likely */
2824             /* Skip the instruction in the delay slot */
2825             MIPS_DEBUG("bnever and skip");
2826             ctx->pc += 4;
2827             goto out;
2828         case OPC_J:
2829             ctx->hflags |= MIPS_HFLAG_B;
2830             MIPS_DEBUG("j " TARGET_FMT_lx, btgt);
2831             break;
2832         case OPC_JALXS:
2833         case OPC_JALX:
2834             ctx->hflags |= MIPS_HFLAG_BX;
2835             /* Fallthrough */
2836         case OPC_JALS:
2837         case OPC_JAL:
2838             blink = 31;
2839             ctx->hflags |= MIPS_HFLAG_B;
2840             ctx->hflags |= ((opc == OPC_JALS || opc == OPC_JALXS)
2841                             ? MIPS_HFLAG_BDS16
2842                             : MIPS_HFLAG_BDS32);
2843             MIPS_DEBUG("jal " TARGET_FMT_lx, btgt);
2844             break;
2845         case OPC_JR:
2846             ctx->hflags |= MIPS_HFLAG_BR;
2847             if (insn_bytes == 4)
2848                 ctx->hflags |= MIPS_HFLAG_BDS32;
2849             MIPS_DEBUG("jr %s", regnames[rs]);
2850             break;
2851         case OPC_JALRS:
2852         case OPC_JALR:
2853         case OPC_JALRC:
2854             blink = rt;
2855             ctx->hflags |= MIPS_HFLAG_BR;
2856             ctx->hflags |= (opc == OPC_JALRS
2857                             ? MIPS_HFLAG_BDS16
2858                             : MIPS_HFLAG_BDS32);
2859             MIPS_DEBUG("jalr %s, %s", regnames[rt], regnames[rs]);
2860             break;
2861         default:
2862             MIPS_INVAL("branch/jump");
2863             generate_exception(ctx, EXCP_RI);
2864             goto out;
2865         }
2866     } else {
2867         switch (opc) {
2868         case OPC_BEQ:
2869             tcg_gen_setcond_tl(TCG_COND_EQ, bcond, t0, t1);
2870             MIPS_DEBUG("beq %s, %s, " TARGET_FMT_lx,
2871                        regnames[rs], regnames[rt], btgt);
2872             goto not_likely;
2873         case OPC_BEQL:
2874             tcg_gen_setcond_tl(TCG_COND_EQ, bcond, t0, t1);
2875             MIPS_DEBUG("beql %s, %s, " TARGET_FMT_lx,
2876                        regnames[rs], regnames[rt], btgt);
2877             goto likely;
2878         case OPC_BNE:
2879             tcg_gen_setcond_tl(TCG_COND_NE, bcond, t0, t1);
2880             MIPS_DEBUG("bne %s, %s, " TARGET_FMT_lx,
2881                        regnames[rs], regnames[rt], btgt);
2882             goto not_likely;
2883         case OPC_BNEL:
2884             tcg_gen_setcond_tl(TCG_COND_NE, bcond, t0, t1);
2885             MIPS_DEBUG("bnel %s, %s, " TARGET_FMT_lx,
2886                        regnames[rs], regnames[rt], btgt);
2887             goto likely;
2888         case OPC_BGEZ:
2889             tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
2890             MIPS_DEBUG("bgez %s, " TARGET_FMT_lx, regnames[rs], btgt);
2891             goto not_likely;
2892         case OPC_BGEZL:
2893             tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
2894             MIPS_DEBUG("bgezl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2895             goto likely;
2896         case OPC_BGEZALS:
2897         case OPC_BGEZAL:
2898             ctx->hflags |= (opc == OPC_BGEZALS
2899                             ? MIPS_HFLAG_BDS16
2900                             : MIPS_HFLAG_BDS32);
2901             tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
2902             MIPS_DEBUG("bgezal %s, " TARGET_FMT_lx, regnames[rs], btgt);
2903             blink = 31;
2904             goto not_likely;
2905         case OPC_BGEZALL:
2906             tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
2907             blink = 31;
2908             MIPS_DEBUG("bgezall %s, " TARGET_FMT_lx, regnames[rs], btgt);
2909             goto likely;
2910         case OPC_BGTZ:
2911             tcg_gen_setcondi_tl(TCG_COND_GT, bcond, t0, 0);
2912             MIPS_DEBUG("bgtz %s, " TARGET_FMT_lx, regnames[rs], btgt);
2913             goto not_likely;
2914         case OPC_BGTZL:
2915             tcg_gen_setcondi_tl(TCG_COND_GT, bcond, t0, 0);
2916             MIPS_DEBUG("bgtzl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2917             goto likely;
2918         case OPC_BLEZ:
2919             tcg_gen_setcondi_tl(TCG_COND_LE, bcond, t0, 0);
2920             MIPS_DEBUG("blez %s, " TARGET_FMT_lx, regnames[rs], btgt);
2921             goto not_likely;
2922         case OPC_BLEZL:
2923             tcg_gen_setcondi_tl(TCG_COND_LE, bcond, t0, 0);
2924             MIPS_DEBUG("blezl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2925             goto likely;
2926         case OPC_BLTZ:
2927             tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
2928             MIPS_DEBUG("bltz %s, " TARGET_FMT_lx, regnames[rs], btgt);
2929             goto not_likely;
2930         case OPC_BLTZL:
2931             tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
2932             MIPS_DEBUG("bltzl %s, " TARGET_FMT_lx, regnames[rs], btgt);
2933             goto likely;
2934         case OPC_BLTZALS:
2935         case OPC_BLTZAL:
2936             ctx->hflags |= (opc == OPC_BLTZALS
2937                             ? MIPS_HFLAG_BDS16
2938                             : MIPS_HFLAG_BDS32);
2939             tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
2940             blink = 31;
2941             MIPS_DEBUG("bltzal %s, " TARGET_FMT_lx, regnames[rs], btgt);
2942         not_likely:
2943             ctx->hflags |= MIPS_HFLAG_BC;
2944             break;
2945         case OPC_BLTZALL:
2946             tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
2947             blink = 31;
2948             MIPS_DEBUG("bltzall %s, " TARGET_FMT_lx, regnames[rs], btgt);
2949         likely:
2950             ctx->hflags |= MIPS_HFLAG_BL;
2951             break;
2952         default:
2953             MIPS_INVAL("conditional branch/jump");
2954             generate_exception(ctx, EXCP_RI);
2955             goto out;
2956         }
2957     }
2958     MIPS_DEBUG("enter ds: link %d cond %02x target " TARGET_FMT_lx,
2959                blink, ctx->hflags, btgt);
2960
2961     ctx->btarget = btgt;
2962     if (blink > 0) {
2963         int post_delay = insn_bytes;
2964         int lowbit = !!(ctx->hflags & MIPS_HFLAG_M16);
2965
2966         if (opc != OPC_JALRC)
2967             post_delay += ((ctx->hflags & MIPS_HFLAG_BDS16) ? 2 : 4);
2968
2969         tcg_gen_movi_tl(cpu_gpr[blink], ctx->pc + post_delay + lowbit);
2970     }
2971
2972  out:
2973     if (insn_bytes == 2)
2974         ctx->hflags |= MIPS_HFLAG_B16;
2975     tcg_temp_free(t0);
2976     tcg_temp_free(t1);
2977 }
2978
2979 /* special3 bitfield operations */
2980 static void gen_bitops (DisasContext *ctx, uint32_t opc, int rt,
2981                         int rs, int lsb, int msb)
2982 {
2983     TCGv t0 = tcg_temp_new();
2984     TCGv t1 = tcg_temp_new();
2985     target_ulong mask;
2986
2987     gen_load_gpr(t1, rs);
2988     switch (opc) {
2989     case OPC_EXT:
2990         if (lsb + msb > 31)
2991             goto fail;
2992         tcg_gen_shri_tl(t0, t1, lsb);
2993         if (msb != 31) {
2994             tcg_gen_andi_tl(t0, t0, (1 << (msb + 1)) - 1);
2995         } else {
2996             tcg_gen_ext32s_tl(t0, t0);
2997         }
2998         break;
2999 #if defined(TARGET_MIPS64)
3000     case OPC_DEXTM:
3001         tcg_gen_shri_tl(t0, t1, lsb);
3002         if (msb != 31) {
3003             tcg_gen_andi_tl(t0, t0, (1ULL << (msb + 1 + 32)) - 1);
3004         }
3005         break;
3006     case OPC_DEXTU:
3007         tcg_gen_shri_tl(t0, t1, lsb + 32);
3008         tcg_gen_andi_tl(t0, t0, (1ULL << (msb + 1)) - 1);
3009         break;
3010     case OPC_DEXT:
3011         tcg_gen_shri_tl(t0, t1, lsb);
3012         tcg_gen_andi_tl(t0, t0, (1ULL << (msb + 1)) - 1);
3013         break;
3014 #endif
3015     case OPC_INS:
3016         if (lsb > msb)
3017             goto fail;
3018         mask = ((msb - lsb + 1 < 32) ? ((1 << (msb - lsb + 1)) - 1) : ~0) << lsb;
3019         gen_load_gpr(t0, rt);
3020         tcg_gen_andi_tl(t0, t0, ~mask);
3021         tcg_gen_shli_tl(t1, t1, lsb);
3022         tcg_gen_andi_tl(t1, t1, mask);
3023         tcg_gen_or_tl(t0, t0, t1);
3024         tcg_gen_ext32s_tl(t0, t0);
3025         break;
3026 #if defined(TARGET_MIPS64)
3027     case OPC_DINSM:
3028         if (lsb > msb)
3029             goto fail;
3030         mask = ((msb - lsb + 1 + 32 < 64) ? ((1ULL << (msb - lsb + 1 + 32)) - 1) : ~0ULL) << lsb;
3031         gen_load_gpr(t0, rt);
3032         tcg_gen_andi_tl(t0, t0, ~mask);
3033         tcg_gen_shli_tl(t1, t1, lsb);
3034         tcg_gen_andi_tl(t1, t1, mask);
3035         tcg_gen_or_tl(t0, t0, t1);
3036         break;
3037     case OPC_DINSU:
3038         if (lsb > msb)
3039             goto fail;
3040         mask = ((1ULL << (msb - lsb + 1)) - 1) << (lsb + 32);
3041         gen_load_gpr(t0, rt);
3042         tcg_gen_andi_tl(t0, t0, ~mask);
3043         tcg_gen_shli_tl(t1, t1, lsb + 32);
3044         tcg_gen_andi_tl(t1, t1, mask);
3045         tcg_gen_or_tl(t0, t0, t1);
3046         break;
3047     case OPC_DINS:
3048         if (lsb > msb)
3049             goto fail;
3050         gen_load_gpr(t0, rt);
3051         mask = ((1ULL << (msb - lsb + 1)) - 1) << lsb;
3052         gen_load_gpr(t0, rt);
3053         tcg_gen_andi_tl(t0, t0, ~mask);
3054         tcg_gen_shli_tl(t1, t1, lsb);
3055         tcg_gen_andi_tl(t1, t1, mask);
3056         tcg_gen_or_tl(t0, t0, t1);
3057         break;
3058 #endif
3059     default:
3060 fail:
3061         MIPS_INVAL("bitops");
3062         generate_exception(ctx, EXCP_RI);
3063         tcg_temp_free(t0);
3064         tcg_temp_free(t1);
3065         return;
3066     }
3067     gen_store_gpr(t0, rt);
3068     tcg_temp_free(t0);
3069     tcg_temp_free(t1);
3070 }
3071
3072 static void gen_bshfl (DisasContext *ctx, uint32_t op2, int rt, int rd)
3073 {
3074     TCGv t0;
3075
3076     if (rd == 0) {
3077         /* If no destination, treat it as a NOP. */
3078         MIPS_DEBUG("NOP");
3079         return;
3080     }
3081
3082     t0 = tcg_temp_new();
3083     gen_load_gpr(t0, rt);
3084     switch (op2) {
3085     case OPC_WSBH:
3086         {
3087             TCGv t1 = tcg_temp_new();
3088
3089             tcg_gen_shri_tl(t1, t0, 8);
3090             tcg_gen_andi_tl(t1, t1, 0x00FF00FF);
3091             tcg_gen_shli_tl(t0, t0, 8);
3092             tcg_gen_andi_tl(t0, t0, ~0x00FF00FF);
3093             tcg_gen_or_tl(t0, t0, t1);
3094             tcg_temp_free(t1);
3095             tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
3096         }
3097         break;
3098     case OPC_SEB:
3099         tcg_gen_ext8s_tl(cpu_gpr[rd], t0);
3100         break;
3101     case OPC_SEH:
3102         tcg_gen_ext16s_tl(cpu_gpr[rd], t0);
3103         break;
3104 #if defined(TARGET_MIPS64)
3105     case OPC_DSBH:
3106         {
3107             TCGv t1 = tcg_temp_new();
3108
3109             tcg_gen_shri_tl(t1, t0, 8);
3110             tcg_gen_andi_tl(t1, t1, 0x00FF00FF00FF00FFULL);
3111             tcg_gen_shli_tl(t0, t0, 8);
3112             tcg_gen_andi_tl(t0, t0, ~0x00FF00FF00FF00FFULL);
3113             tcg_gen_or_tl(cpu_gpr[rd], t0, t1);
3114             tcg_temp_free(t1);
3115         }
3116         break;
3117     case OPC_DSHD:
3118         {
3119             TCGv t1 = tcg_temp_new();
3120
3121             tcg_gen_shri_tl(t1, t0, 16);
3122             tcg_gen_andi_tl(t1, t1, 0x0000FFFF0000FFFFULL);
3123             tcg_gen_shli_tl(t0, t0, 16);
3124             tcg_gen_andi_tl(t0, t0, ~0x0000FFFF0000FFFFULL);
3125             tcg_gen_or_tl(t0, t0, t1);
3126             tcg_gen_shri_tl(t1, t0, 32);
3127             tcg_gen_shli_tl(t0, t0, 32);
3128             tcg_gen_or_tl(cpu_gpr[rd], t0, t1);
3129             tcg_temp_free(t1);
3130         }
3131         break;
3132 #endif
3133     default:
3134         MIPS_INVAL("bsfhl");
3135         generate_exception(ctx, EXCP_RI);
3136         tcg_temp_free(t0);
3137         return;
3138     }
3139     tcg_temp_free(t0);
3140 }
3141
3142 #ifndef CONFIG_USER_ONLY
3143 /* CP0 (MMU and control) */
3144 static inline void gen_mfc0_load32 (TCGv arg, target_ulong off)
3145 {
3146     TCGv_i32 t0 = tcg_temp_new_i32();
3147
3148     tcg_gen_ld_i32(t0, cpu_env, off);
3149     tcg_gen_ext_i32_tl(arg, t0);
3150     tcg_temp_free_i32(t0);
3151 }
3152
3153 static inline void gen_mfc0_load64 (TCGv arg, target_ulong off)
3154 {
3155     tcg_gen_ld_tl(arg, cpu_env, off);
3156     tcg_gen_ext32s_tl(arg, arg);
3157 }
3158
3159 static inline void gen_mtc0_store32 (TCGv arg, target_ulong off)
3160 {
3161     TCGv_i32 t0 = tcg_temp_new_i32();
3162
3163     tcg_gen_trunc_tl_i32(t0, arg);
3164     tcg_gen_st_i32(t0, cpu_env, off);
3165     tcg_temp_free_i32(t0);
3166 }
3167
3168 static inline void gen_mtc0_store64 (TCGv arg, target_ulong off)
3169 {
3170     tcg_gen_ext32s_tl(arg, arg);
3171     tcg_gen_st_tl(arg, cpu_env, off);
3172 }
3173
3174 static void gen_mfc0 (CPUMIPSState *env, DisasContext *ctx, TCGv arg, int reg, int sel)
3175 {
3176     const char *rn = "invalid";
3177
3178     if (sel != 0)
3179         check_insn(env, ctx, ISA_MIPS32);
3180
3181     switch (reg) {
3182     case 0:
3183         switch (sel) {
3184         case 0:
3185             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Index));
3186             rn = "Index";
3187             break;
3188         case 1:
3189             check_insn(env, ctx, ASE_MT);
3190             gen_helper_mfc0_mvpcontrol(arg);
3191             rn = "MVPControl";
3192             break;
3193         case 2:
3194             check_insn(env, ctx, ASE_MT);
3195             gen_helper_mfc0_mvpconf0(arg);
3196             rn = "MVPConf0";
3197             break;
3198         case 3:
3199             check_insn(env, ctx, ASE_MT);
3200             gen_helper_mfc0_mvpconf1(arg);
3201             rn = "MVPConf1";
3202             break;
3203         default:
3204             goto die;
3205         }
3206         break;
3207     case 1:
3208         switch (sel) {
3209         case 0:
3210             gen_helper_mfc0_random(arg);
3211             rn = "Random";
3212             break;
3213         case 1:
3214             check_insn(env, ctx, ASE_MT);
3215             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEControl));
3216             rn = "VPEControl";
3217             break;
3218         case 2:
3219             check_insn(env, ctx, ASE_MT);
3220             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEConf0));
3221             rn = "VPEConf0";
3222             break;
3223         case 3:
3224             check_insn(env, ctx, ASE_MT);
3225             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEConf1));
3226             rn = "VPEConf1";
3227             break;
3228         case 4:
3229             check_insn(env, ctx, ASE_MT);
3230             gen_mfc0_load64(arg, offsetof(CPUMIPSState, CP0_YQMask));
3231             rn = "YQMask";
3232             break;
3233         case 5:
3234             check_insn(env, ctx, ASE_MT);
3235             gen_mfc0_load64(arg, offsetof(CPUMIPSState, CP0_VPESchedule));
3236             rn = "VPESchedule";
3237             break;
3238         case 6:
3239             check_insn(env, ctx, ASE_MT);
3240             gen_mfc0_load64(arg, offsetof(CPUMIPSState, CP0_VPEScheFBack));
3241             rn = "VPEScheFBack";
3242             break;
3243         case 7:
3244             check_insn(env, ctx, ASE_MT);
3245             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEOpt));
3246             rn = "VPEOpt";
3247             break;
3248         default:
3249             goto die;
3250         }
3251         break;
3252     case 2:
3253         switch (sel) {
3254         case 0:
3255             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_EntryLo0));
3256             tcg_gen_ext32s_tl(arg, arg);
3257             rn = "EntryLo0";
3258             break;
3259         case 1:
3260             check_insn(env, ctx, ASE_MT);
3261             gen_helper_mfc0_tcstatus(arg);
3262             rn = "TCStatus";
3263             break;
3264         case 2:
3265             check_insn(env, ctx, ASE_MT);
3266             gen_helper_mfc0_tcbind(arg);
3267             rn = "TCBind";
3268             break;
3269         case 3:
3270             check_insn(env, ctx, ASE_MT);
3271             gen_helper_mfc0_tcrestart(arg);
3272             rn = "TCRestart";
3273             break;
3274         case 4:
3275             check_insn(env, ctx, ASE_MT);
3276             gen_helper_mfc0_tchalt(arg);
3277             rn = "TCHalt";
3278             break;
3279         case 5:
3280             check_insn(env, ctx, ASE_MT);
3281             gen_helper_mfc0_tccontext(arg);
3282             rn = "TCContext";
3283             break;
3284         case 6:
3285             check_insn(env, ctx, ASE_MT);
3286             gen_helper_mfc0_tcschedule(arg);
3287             rn = "TCSchedule";
3288             break;
3289         case 7:
3290             check_insn(env, ctx, ASE_MT);
3291             gen_helper_mfc0_tcschefback(arg);
3292             rn = "TCScheFBack";
3293             break;
3294         default:
3295             goto die;
3296         }
3297         break;
3298     case 3:
3299         switch (sel) {
3300         case 0:
3301             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_EntryLo1));
3302             tcg_gen_ext32s_tl(arg, arg);
3303             rn = "EntryLo1";
3304             break;
3305         default:
3306             goto die;
3307         }
3308         break;
3309     case 4:
3310         switch (sel) {
3311         case 0:
3312             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_Context));
3313             tcg_gen_ext32s_tl(arg, arg);
3314             rn = "Context";
3315             break;
3316         case 1:
3317 //            gen_helper_mfc0_contextconfig(arg); /* SmartMIPS ASE */
3318             rn = "ContextConfig";
3319 //            break;
3320         default:
3321             goto die;
3322         }
3323         break;
3324     case 5:
3325         switch (sel) {
3326         case 0:
3327             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PageMask));
3328             rn = "PageMask";
3329             break;
3330         case 1:
3331             check_insn(env, ctx, ISA_MIPS32R2);
3332             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PageGrain));
3333             rn = "PageGrain";
3334             break;
3335         default:
3336             goto die;
3337         }
3338         break;
3339     case 6:
3340         switch (sel) {
3341         case 0:
3342             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Wired));
3343             rn = "Wired";
3344             break;
3345         case 1:
3346             check_insn(env, ctx, ISA_MIPS32R2);
3347             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf0));
3348             rn = "SRSConf0";
3349             break;
3350         case 2:
3351             check_insn(env, ctx, ISA_MIPS32R2);
3352             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf1));
3353             rn = "SRSConf1";
3354             break;
3355         case 3:
3356             check_insn(env, ctx, ISA_MIPS32R2);
3357             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf2));
3358             rn = "SRSConf2";
3359             break;
3360         case 4:
3361             check_insn(env, ctx, ISA_MIPS32R2);
3362             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf3));
3363             rn = "SRSConf3";
3364             break;
3365         case 5:
3366             check_insn(env, ctx, ISA_MIPS32R2);
3367             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf4));
3368             rn = "SRSConf4";
3369             break;
3370         default:
3371             goto die;
3372         }
3373         break;
3374     case 7:
3375         switch (sel) {
3376         case 0:
3377             check_insn(env, ctx, ISA_MIPS32R2);
3378             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_HWREna));
3379             rn = "HWREna";
3380             break;
3381         default:
3382             goto die;
3383         }
3384         break;
3385     case 8:
3386         switch (sel) {
3387         case 0:
3388             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_BadVAddr));
3389             tcg_gen_ext32s_tl(arg, arg);
3390             rn = "BadVAddr";
3391             break;
3392         default:
3393             goto die;
3394        }
3395         break;
3396     case 9:
3397         switch (sel) {
3398         case 0:
3399             /* Mark as an IO operation because we read the time.  */
3400             if (use_icount)
3401                 gen_io_start();
3402             gen_helper_mfc0_count(arg);
3403             if (use_icount) {
3404                 gen_io_end();
3405             }
3406             /* Break the TB to be able to take timer interrupts immediately
3407                after reading count.  */
3408             ctx->bstate = BS_STOP;
3409             rn = "Count";
3410             break;
3411         /* 6,7 are implementation dependent */
3412         default:
3413             goto die;
3414         }
3415         break;
3416     case 10:
3417         switch (sel) {
3418         case 0:
3419             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_EntryHi));
3420             tcg_gen_ext32s_tl(arg, arg);
3421             rn = "EntryHi";
3422             break;
3423         default:
3424             goto die;
3425         }
3426         break;
3427     case 11:
3428         switch (sel) {
3429         case 0:
3430             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Compare));
3431             rn = "Compare";
3432             break;
3433         /* 6,7 are implementation dependent */
3434         default:
3435             goto die;
3436         }
3437         break;
3438     case 12:
3439         switch (sel) {
3440         case 0:
3441             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Status));
3442             rn = "Status";
3443             break;
3444         case 1:
3445             check_insn(env, ctx, ISA_MIPS32R2);
3446             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_IntCtl));
3447             rn = "IntCtl";
3448             break;
3449         case 2:
3450             check_insn(env, ctx, ISA_MIPS32R2);
3451             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSCtl));
3452             rn = "SRSCtl";
3453             break;
3454         case 3:
3455             check_insn(env, ctx, ISA_MIPS32R2);
3456             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSMap));
3457             rn = "SRSMap";
3458             break;
3459         default:
3460             goto die;
3461        }
3462         break;
3463     case 13:
3464         switch (sel) {
3465         case 0:
3466             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Cause));
3467             rn = "Cause";
3468             break;
3469         default:
3470             goto die;
3471        }
3472         break;
3473     case 14:
3474         switch (sel) {
3475         case 0:
3476             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_EPC));
3477             tcg_gen_ext32s_tl(arg, arg);
3478             rn = "EPC";
3479             break;
3480         default:
3481             goto die;
3482         }
3483         break;
3484     case 15:
3485         switch (sel) {
3486         case 0:
3487             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PRid));
3488             rn = "PRid";
3489             break;
3490         case 1:
3491             check_insn(env, ctx, ISA_MIPS32R2);
3492             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_EBase));
3493             rn = "EBase";
3494             break;
3495         default:
3496             goto die;
3497        }
3498         break;
3499     case 16:
3500         switch (sel) {
3501         case 0:
3502             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config0));
3503             rn = "Config";
3504             break;
3505         case 1:
3506             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config1));
3507             rn = "Config1";
3508             break;
3509         case 2:
3510             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config2));
3511             rn = "Config2";
3512             break;
3513         case 3:
3514             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config3));
3515             rn = "Config3";
3516             break;
3517         /* 4,5 are reserved */
3518         /* 6,7 are implementation dependent */
3519         case 6:
3520             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config6));
3521             rn = "Config6";
3522             break;
3523         case 7:
3524             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config7));
3525             rn = "Config7";
3526             break;
3527         default:
3528             goto die;
3529         }
3530         break;
3531     case 17:
3532         switch (sel) {
3533         case 0:
3534             gen_helper_mfc0_lladdr(arg);
3535             rn = "LLAddr";
3536             break;
3537         default:
3538             goto die;
3539         }
3540         break;
3541     case 18:
3542         switch (sel) {
3543         case 0 ... 7:
3544             gen_helper_1i(mfc0_watchlo, arg, sel);
3545             rn = "WatchLo";
3546             break;
3547         default:
3548             goto die;
3549         }
3550         break;
3551     case 19:
3552         switch (sel) {
3553         case 0 ...7:
3554             gen_helper_1i(mfc0_watchhi, arg, sel);
3555             rn = "WatchHi";
3556             break;
3557         default:
3558             goto die;
3559         }
3560         break;
3561     case 20:
3562         switch (sel) {
3563         case 0:
3564 #if defined(TARGET_MIPS64)
3565             check_insn(env, ctx, ISA_MIPS3);
3566             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_XContext));
3567             tcg_gen_ext32s_tl(arg, arg);
3568             rn = "XContext";
3569             break;
3570 #endif
3571         default:
3572             goto die;
3573         }
3574         break;
3575     case 21:
3576        /* Officially reserved, but sel 0 is used for R1x000 framemask */
3577         switch (sel) {
3578         case 0:
3579             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Framemask));
3580             rn = "Framemask";
3581             break;
3582         default:
3583             goto die;
3584         }
3585         break;
3586     case 22:
3587         tcg_gen_movi_tl(arg, 0); /* unimplemented */
3588         rn = "'Diagnostic"; /* implementation dependent */
3589         break;
3590     case 23:
3591         switch (sel) {
3592         case 0:
3593             gen_helper_mfc0_debug(arg); /* EJTAG support */
3594             rn = "Debug";
3595             break;
3596         case 1:
3597 //            gen_helper_mfc0_tracecontrol(arg); /* PDtrace support */
3598             rn = "TraceControl";
3599 //            break;
3600         case 2:
3601 //            gen_helper_mfc0_tracecontrol2(arg); /* PDtrace support */
3602             rn = "TraceControl2";
3603 //            break;
3604         case 3:
3605 //            gen_helper_mfc0_usertracedata(arg); /* PDtrace support */
3606             rn = "UserTraceData";
3607 //            break;
3608         case 4:
3609 //            gen_helper_mfc0_tracebpc(arg); /* PDtrace support */
3610             rn = "TraceBPC";
3611 //            break;
3612         default:
3613             goto die;
3614         }
3615         break;
3616     case 24:
3617         switch (sel) {
3618         case 0:
3619             /* EJTAG support */
3620             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_DEPC));
3621             tcg_gen_ext32s_tl(arg, arg);
3622             rn = "DEPC";
3623             break;
3624         default:
3625             goto die;
3626         }
3627         break;
3628     case 25:
3629         switch (sel) {
3630         case 0:
3631             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Performance0));
3632             rn = "Performance0";
3633             break;
3634         case 1:
3635 //            gen_helper_mfc0_performance1(arg);
3636             rn = "Performance1";
3637 //            break;
3638         case 2:
3639 //            gen_helper_mfc0_performance2(arg);
3640             rn = "Performance2";
3641 //            break;
3642         case 3:
3643 //            gen_helper_mfc0_performance3(arg);
3644             rn = "Performance3";
3645 //            break;
3646         case 4:
3647 //            gen_helper_mfc0_performance4(arg);
3648             rn = "Performance4";
3649 //            break;
3650         case 5:
3651 //            gen_helper_mfc0_performance5(arg);
3652             rn = "Performance5";
3653 //            break;
3654         case 6:
3655 //            gen_helper_mfc0_performance6(arg);
3656             rn = "Performance6";
3657 //            break;
3658         case 7:
3659 //            gen_helper_mfc0_performance7(arg);
3660             rn = "Performance7";
3661 //            break;
3662         default:
3663             goto die;
3664         }
3665         break;
3666     case 26:
3667         tcg_gen_movi_tl(arg, 0); /* unimplemented */
3668         rn = "ECC";
3669         break;
3670     case 27:
3671         switch (sel) {
3672         case 0 ... 3:
3673             tcg_gen_movi_tl(arg, 0); /* unimplemented */
3674             rn = "CacheErr";
3675             break;
3676         default:
3677             goto die;
3678         }
3679         break;
3680     case 28:
3681         switch (sel) {
3682         case 0:
3683         case 2:
3684         case 4:
3685         case 6:
3686             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_TagLo));
3687             rn = "TagLo";
3688             break;
3689         case 1:
3690         case 3:
3691         case 5:
3692         case 7:
3693             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DataLo));
3694             rn = "DataLo";
3695             break;
3696         default:
3697             goto die;
3698         }
3699         break;
3700     case 29:
3701         switch (sel) {
3702         case 0:
3703         case 2:
3704         case 4:
3705         case 6:
3706             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_TagHi));
3707             rn = "TagHi";
3708             break;
3709         case 1:
3710         case 3:
3711         case 5:
3712         case 7:
3713             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DataHi));
3714             rn = "DataHi";
3715             break;
3716         default:
3717             goto die;
3718         }
3719         break;
3720     case 30:
3721         switch (sel) {
3722         case 0:
3723             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_ErrorEPC));
3724             tcg_gen_ext32s_tl(arg, arg);
3725             rn = "ErrorEPC";
3726             break;
3727         default:
3728             goto die;
3729         }
3730         break;
3731     case 31:
3732         switch (sel) {
3733         case 0:
3734             /* EJTAG support */
3735             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DESAVE));
3736             rn = "DESAVE";
3737             break;
3738         default:
3739             goto die;
3740         }
3741         break;
3742     default:
3743        goto die;
3744     }
3745     (void)rn; /* avoid a compiler warning */
3746     LOG_DISAS("mfc0 %s (reg %d sel %d)\n", rn, reg, sel);
3747     return;
3748
3749 die:
3750     LOG_DISAS("mfc0 %s (reg %d sel %d)\n", rn, reg, sel);
3751     generate_exception(ctx, EXCP_RI);
3752 }
3753
3754 static void gen_mtc0 (CPUMIPSState *env, DisasContext *ctx, TCGv arg, int reg, int sel)
3755 {
3756     const char *rn = "invalid";
3757
3758     if (sel != 0)
3759         check_insn(env, ctx, ISA_MIPS32);
3760
3761     if (use_icount)
3762         gen_io_start();
3763
3764     switch (reg) {
3765     case 0:
3766         switch (sel) {
3767         case 0:
3768             gen_helper_mtc0_index(arg);
3769             rn = "Index";
3770             break;
3771         case 1:
3772             check_insn(env, ctx, ASE_MT);
3773             gen_helper_mtc0_mvpcontrol(arg);
3774             rn = "MVPControl";
3775             break;
3776         case 2:
3777             check_insn(env, ctx, ASE_MT);
3778             /* ignored */
3779             rn = "MVPConf0";
3780             break;
3781         case 3:
3782             check_insn(env, ctx, ASE_MT);
3783             /* ignored */
3784             rn = "MVPConf1";
3785             break;
3786         default:
3787             goto die;
3788         }
3789         break;
3790     case 1:
3791         switch (sel) {
3792         case 0:
3793             /* ignored */
3794             rn = "Random";
3795             break;
3796         case 1:
3797             check_insn(env, ctx, ASE_MT);
3798             gen_helper_mtc0_vpecontrol(arg);
3799             rn = "VPEControl";
3800             break;
3801         case 2:
3802             check_insn(env, ctx, ASE_MT);
3803             gen_helper_mtc0_vpeconf0(arg);
3804             rn = "VPEConf0";
3805             break;
3806         case 3:
3807             check_insn(env, ctx, ASE_MT);
3808             gen_helper_mtc0_vpeconf1(arg);
3809             rn = "VPEConf1";
3810             break;
3811         case 4:
3812             check_insn(env, ctx, ASE_MT);
3813             gen_helper_mtc0_yqmask(arg);
3814             rn = "YQMask";
3815             break;
3816         case 5:
3817             check_insn(env, ctx, ASE_MT);
3818             gen_mtc0_store64(arg, offsetof(CPUMIPSState, CP0_VPESchedule));
3819             rn = "VPESchedule";
3820             break;
3821         case 6:
3822             check_insn(env, ctx, ASE_MT);
3823             gen_mtc0_store64(arg, offsetof(CPUMIPSState, CP0_VPEScheFBack));
3824             rn = "VPEScheFBack";
3825             break;
3826         case 7:
3827             check_insn(env, ctx, ASE_MT);
3828             gen_helper_mtc0_vpeopt(arg);
3829             rn = "VPEOpt";
3830             break;
3831         default:
3832             goto die;
3833         }
3834         break;
3835     case 2:
3836         switch (sel) {
3837         case 0:
3838             gen_helper_mtc0_entrylo0(arg);
3839             rn = "EntryLo0";
3840             break;
3841         case 1:
3842             check_insn(env, ctx, ASE_MT);
3843             gen_helper_mtc0_tcstatus(arg);
3844             rn = "TCStatus";
3845             break;
3846         case 2:
3847             check_insn(env, ctx, ASE_MT);
3848             gen_helper_mtc0_tcbind(arg);
3849             rn = "TCBind";
3850             break;
3851         case 3:
3852             check_insn(env, ctx, ASE_MT);
3853             gen_helper_mtc0_tcrestart(arg);
3854             rn = "TCRestart";
3855             break;
3856         case 4:
3857             check_insn(env, ctx, ASE_MT);
3858             gen_helper_mtc0_tchalt(arg);
3859             rn = "TCHalt";
3860             break;
3861         case 5:
3862             check_insn(env, ctx, ASE_MT);
3863             gen_helper_mtc0_tccontext(arg);
3864             rn = "TCContext";
3865             break;
3866         case 6:
3867             check_insn(env, ctx, ASE_MT);
3868             gen_helper_mtc0_tcschedule(arg);
3869             rn = "TCSchedule";
3870             break;
3871         case 7:
3872             check_insn(env, ctx, ASE_MT);
3873             gen_helper_mtc0_tcschefback(arg);
3874             rn = "TCScheFBack";
3875             break;
3876         default:
3877             goto die;
3878         }
3879         break;
3880     case 3:
3881         switch (sel) {
3882         case 0:
3883             gen_helper_mtc0_entrylo1(arg);
3884             rn = "EntryLo1";
3885             break;
3886         default:
3887             goto die;
3888         }
3889         break;
3890     case 4:
3891         switch (sel) {
3892         case 0:
3893             gen_helper_mtc0_context(arg);
3894             rn = "Context";
3895             break;
3896         case 1:
3897 //            gen_helper_mtc0_contextconfig(arg); /* SmartMIPS ASE */
3898             rn = "ContextConfig";
3899 //            break;
3900         default:
3901             goto die;
3902         }
3903         break;
3904     case 5:
3905         switch (sel) {
3906         case 0:
3907             gen_helper_mtc0_pagemask(arg);
3908             rn = "PageMask";
3909             break;
3910         case 1:
3911             check_insn(env, ctx, ISA_MIPS32R2);
3912             gen_helper_mtc0_pagegrain(arg);
3913             rn = "PageGrain";
3914             break;
3915         default:
3916             goto die;
3917         }
3918         break;
3919     case 6:
3920         switch (sel) {
3921         case 0:
3922             gen_helper_mtc0_wired(arg);
3923             rn = "Wired";
3924             break;
3925         case 1:
3926             check_insn(env, ctx, ISA_MIPS32R2);
3927             gen_helper_mtc0_srsconf0(arg);
3928             rn = "SRSConf0";
3929             break;
3930         case 2:
3931             check_insn(env, ctx, ISA_MIPS32R2);
3932             gen_helper_mtc0_srsconf1(arg);
3933             rn = "SRSConf1";
3934             break;
3935         case 3:
3936             check_insn(env, ctx, ISA_MIPS32R2);
3937             gen_helper_mtc0_srsconf2(arg);
3938             rn = "SRSConf2";
3939             break;
3940         case 4:
3941             check_insn(env, ctx, ISA_MIPS32R2);
3942             gen_helper_mtc0_srsconf3(arg);
3943             rn = "SRSConf3";
3944             break;
3945         case 5:
3946             check_insn(env, ctx, ISA_MIPS32R2);
3947             gen_helper_mtc0_srsconf4(arg);
3948             rn = "SRSConf4";
3949             break;
3950         default:
3951             goto die;
3952         }
3953         break;
3954     case 7:
3955         switch (sel) {
3956         case 0:
3957             check_insn(env, ctx, ISA_MIPS32R2);
3958             gen_helper_mtc0_hwrena(arg);
3959             rn = "HWREna";
3960             break;
3961         default:
3962             goto die;
3963         }
3964         break;
3965     case 8:
3966         /* ignored */
3967         rn = "BadVAddr";
3968         break;
3969     case 9:
3970         switch (sel) {
3971         case 0:
3972             gen_helper_mtc0_count(arg);
3973             rn = "Count";
3974             break;
3975         /* 6,7 are implementation dependent */
3976         default:
3977             goto die;
3978         }
3979         break;
3980     case 10:
3981         switch (sel) {
3982         case 0:
3983             gen_helper_mtc0_entryhi(arg);
3984             rn = "EntryHi";
3985             break;
3986         default:
3987             goto die;
3988         }
3989         break;
3990     case 11:
3991         switch (sel) {
3992         case 0:
3993             gen_helper_mtc0_compare(arg);
3994             rn = "Compare";
3995             break;
3996         /* 6,7 are implementation dependent */
3997         default:
3998             goto die;
3999         }
4000         break;
4001     case 12:
4002         switch (sel) {
4003         case 0:
4004             save_cpu_state(ctx, 1);
4005             gen_helper_mtc0_status(arg);
4006             /* BS_STOP isn't good enough here, hflags may have changed. */
4007             gen_save_pc(ctx->pc + 4);
4008             ctx->bstate = BS_EXCP;
4009             rn = "Status";
4010             break;
4011         case 1:
4012             check_insn(env, ctx, ISA_MIPS32R2);
4013             gen_helper_mtc0_intctl(arg);
4014             /* Stop translation as we may have switched the execution mode */
4015             ctx->bstate = BS_STOP;
4016             rn = "IntCtl";
4017             break;
4018         case 2:
4019             check_insn(env, ctx, ISA_MIPS32R2);
4020             gen_helper_mtc0_srsctl(arg);
4021             /* Stop translation as we may have switched the execution mode */
4022             ctx->bstate = BS_STOP;
4023             rn = "SRSCtl";
4024             break;
4025         case 3:
4026             check_insn(env, ctx, ISA_MIPS32R2);
4027             gen_mtc0_store32(arg, offsetof(CPUMIPSState, CP0_SRSMap));
4028             /* Stop translation as we may have switched the execution mode */
4029             ctx->bstate = BS_STOP;
4030             rn = "SRSMap";
4031             break;
4032         default:
4033             goto die;
4034         }
4035         break;
4036     case 13:
4037         switch (sel) {
4038         case 0:
4039             save_cpu_state(ctx, 1);
4040             gen_helper_mtc0_cause(arg);
4041             rn = "Cause";
4042             break;
4043         default:
4044             goto die;
4045         }
4046         break;
4047     case 14:
4048         switch (sel) {
4049         case 0:
4050             gen_mtc0_store64(arg, offsetof(CPUMIPSState, CP0_EPC));
4051             rn = "EPC";
4052             break;
4053         default:
4054             goto die;
4055         }
4056         break;
4057     case 15:
4058         switch (sel) {
4059         case 0:
4060             /* ignored */
4061             rn = "PRid";
4062             break;
4063         case 1:
4064             check_insn(env, ctx, ISA_MIPS32R2);
4065             gen_helper_mtc0_ebase(arg);
4066             rn = "EBase";
4067             break;
4068         default:
4069             goto die;
4070         }
4071         break;
4072     case 16:
4073         switch (sel) {
4074         case 0:
4075             gen_helper_mtc0_config0(arg);
4076             rn = "Config";
4077             /* Stop translation as we may have switched the execution mode */
4078             ctx->bstate = BS_STOP;
4079             break;
4080         case 1:
4081             /* ignored, read only */
4082             rn = "Config1";
4083             break;
4084         case 2:
4085             gen_helper_mtc0_config2(arg);
4086             rn = "Config2";
4087             /* Stop translation as we may have switched the execution mode */
4088             ctx->bstate = BS_STOP;
4089             break;
4090         case 3:
4091             /* ignored, read only */
4092             rn = "Config3";
4093             break;
4094         /* 4,5 are reserved */
4095         /* 6,7 are implementation dependent */
4096         case 6:
4097             /* ignored */
4098             rn = "Config6";
4099             break;
4100         case 7:
4101             /* ignored */
4102             rn = "Config7";
4103             break;
4104         default:
4105             rn = "Invalid config selector";
4106             goto die;
4107         }
4108         break;
4109     case 17:
4110         switch (sel) {
4111         case 0:
4112             gen_helper_mtc0_lladdr(arg);
4113             rn = "LLAddr";
4114             break;
4115         default:
4116             goto die;
4117         }
4118         break;
4119     case 18:
4120         switch (sel) {
4121         case 0 ... 7:
4122             gen_helper_1i(mtc0_watchlo, arg, sel);
4123             rn = "WatchLo";
4124             break;
4125         default:
4126             goto die;
4127         }
4128         break;
4129     case 19:
4130         switch (sel) {
4131         case 0 ... 7:
4132             gen_helper_1i(mtc0_watchhi, arg, sel);
4133             rn = "WatchHi";
4134             break;
4135         default:
4136             goto die;
4137         }
4138         break;
4139     case 20:
4140         switch (sel) {
4141         case 0:
4142 #if defined(TARGET_MIPS64)
4143             check_insn(env, ctx, ISA_MIPS3);
4144             gen_helper_mtc0_xcontext(arg);
4145             rn = "XContext";
4146             break;
4147 #endif
4148         default:
4149             goto die;
4150         }
4151         break;
4152     case 21:
4153        /* Officially reserved, but sel 0 is used for R1x000 framemask */
4154         switch (sel) {
4155         case 0:
4156             gen_helper_mtc0_framemask(arg);
4157             rn = "Framemask";
4158             break;
4159         default:
4160             goto die;
4161         }
4162         break;
4163     case 22:
4164         /* ignored */
4165         rn = "Diagnostic"; /* implementation dependent */
4166         break;
4167     case 23:
4168         switch (sel) {
4169         case 0:
4170             gen_helper_mtc0_debug(arg); /* EJTAG support */
4171             /* BS_STOP isn't good enough here, hflags may have changed. */
4172             gen_save_pc(ctx->pc + 4);
4173             ctx->bstate = BS_EXCP;
4174             rn = "Debug";
4175             break;
4176         case 1:
4177 //            gen_helper_mtc0_tracecontrol(arg); /* PDtrace support */
4178             rn = "TraceControl";
4179             /* Stop translation as we may have switched the execution mode */
4180             ctx->bstate = BS_STOP;
4181 //            break;
4182         case 2:
4183 //            gen_helper_mtc0_tracecontrol2(arg); /* PDtrace support */
4184             rn = "TraceControl2";
4185             /* Stop translation as we may have switched the execution mode */
4186             ctx->bstate = BS_STOP;
4187 //            break;
4188         case 3:
4189             /* Stop translation as we may have switched the execution mode */
4190             ctx->bstate = BS_STOP;
4191 //            gen_helper_mtc0_usertracedata(arg); /* PDtrace support */
4192             rn = "UserTraceData";
4193             /* Stop translation as we may have switched the execution mode */
4194             ctx->bstate = BS_STOP;
4195 //            break;
4196         case 4:
4197 //            gen_helper_mtc0_tracebpc(arg); /* PDtrace support */
4198             /* Stop translation as we may have switched the execution mode */
4199             ctx->bstate = BS_STOP;
4200             rn = "TraceBPC";
4201 //            break;
4202         default:
4203             goto die;
4204         }
4205         break;
4206     case 24:
4207         switch (sel) {
4208         case 0:
4209             /* EJTAG support */
4210             gen_mtc0_store64(arg, offsetof(CPUMIPSState, CP0_DEPC));
4211             rn = "DEPC";
4212             break;
4213         default:
4214             goto die;
4215         }
4216         break;
4217     case 25:
4218         switch (sel) {
4219         case 0:
4220             gen_helper_mtc0_performance0(arg);
4221             rn = "Performance0";
4222             break;
4223         case 1:
4224 //            gen_helper_mtc0_performance1(arg);
4225             rn = "Performance1";
4226 //            break;
4227         case 2:
4228 //            gen_helper_mtc0_performance2(arg);
4229             rn = "Performance2";
4230 //            break;
4231         case 3:
4232 //            gen_helper_mtc0_performance3(arg);
4233             rn = "Performance3";
4234 //            break;
4235         case 4:
4236 //            gen_helper_mtc0_performance4(arg);
4237             rn = "Performance4";
4238 //            break;
4239         case 5:
4240 //            gen_helper_mtc0_performance5(arg);
4241             rn = "Performance5";
4242 //            break;
4243         case 6:
4244 //            gen_helper_mtc0_performance6(arg);
4245             rn = "Performance6";
4246 //            break;
4247         case 7:
4248 //            gen_helper_mtc0_performance7(arg);
4249             rn = "Performance7";
4250 //            break;
4251         default:
4252             goto die;
4253         }
4254        break;
4255     case 26:
4256         /* ignored */
4257         rn = "ECC";
4258         break;
4259     case 27:
4260         switch (sel) {
4261         case 0 ... 3:
4262             /* ignored */
4263             rn = "CacheErr";
4264             break;
4265         default:
4266             goto die;
4267         }
4268        break;
4269     case 28:
4270         switch (sel) {
4271         case 0:
4272         case 2:
4273         case 4:
4274         case 6:
4275             gen_helper_mtc0_taglo(arg);
4276             rn = "TagLo";
4277             break;
4278         case 1:
4279         case 3:
4280         case 5:
4281         case 7:
4282             gen_helper_mtc0_datalo(arg);
4283             rn = "DataLo";
4284             break;
4285         default:
4286             goto die;
4287         }
4288         break;
4289     case 29:
4290         switch (sel) {
4291         case 0:
4292         case 2:
4293         case 4:
4294         case 6:
4295             gen_helper_mtc0_taghi(arg);
4296             rn = "TagHi";
4297             break;
4298         case 1:
4299         case 3:
4300         case 5:
4301         case 7:
4302             gen_helper_mtc0_datahi(arg);
4303             rn = "DataHi";
4304             break;
4305         default:
4306             rn = "invalid sel";
4307             goto die;
4308         }
4309        break;
4310     case 30:
4311         switch (sel) {
4312         case 0:
4313             gen_mtc0_store64(arg, offsetof(CPUMIPSState, CP0_ErrorEPC));
4314             rn = "ErrorEPC";
4315             break;
4316         default:
4317             goto die;
4318         }
4319         break;
4320     case 31:
4321         switch (sel) {
4322         case 0:
4323             /* EJTAG support */
4324             gen_mtc0_store32(arg, offsetof(CPUMIPSState, CP0_DESAVE));
4325             rn = "DESAVE";
4326             break;
4327         default:
4328             goto die;
4329         }
4330         /* Stop translation as we may have switched the execution mode */
4331         ctx->bstate = BS_STOP;
4332         break;
4333     default:
4334        goto die;
4335     }
4336     (void)rn; /* avoid a compiler warning */
4337     LOG_DISAS("mtc0 %s (reg %d sel %d)\n", rn, reg, sel);
4338     /* For simplicity assume that all writes can cause interrupts.  */
4339     if (use_icount) {
4340         gen_io_end();
4341         ctx->bstate = BS_STOP;
4342     }
4343     return;
4344
4345 die:
4346     LOG_DISAS("mtc0 %s (reg %d sel %d)\n", rn, reg, sel);
4347     generate_exception(ctx, EXCP_RI);
4348 }
4349
4350 #if defined(TARGET_MIPS64)
4351 static void gen_dmfc0 (CPUMIPSState *env, DisasContext *ctx, TCGv arg, int reg, int sel)
4352 {
4353     const char *rn = "invalid";
4354
4355     if (sel != 0)
4356         check_insn(env, ctx, ISA_MIPS64);
4357
4358     switch (reg) {
4359     case 0:
4360         switch (sel) {
4361         case 0:
4362             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Index));
4363             rn = "Index";
4364             break;
4365         case 1:
4366             check_insn(env, ctx, ASE_MT);
4367             gen_helper_mfc0_mvpcontrol(arg);
4368             rn = "MVPControl";
4369             break;
4370         case 2:
4371             check_insn(env, ctx, ASE_MT);
4372             gen_helper_mfc0_mvpconf0(arg);
4373             rn = "MVPConf0";
4374             break;
4375         case 3:
4376             check_insn(env, ctx, ASE_MT);
4377             gen_helper_mfc0_mvpconf1(arg);
4378             rn = "MVPConf1";
4379             break;
4380         default:
4381             goto die;
4382         }
4383         break;
4384     case 1:
4385         switch (sel) {
4386         case 0:
4387             gen_helper_mfc0_random(arg);
4388             rn = "Random";
4389             break;
4390         case 1:
4391             check_insn(env, ctx, ASE_MT);
4392             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEControl));
4393             rn = "VPEControl";
4394             break;
4395         case 2:
4396             check_insn(env, ctx, ASE_MT);
4397             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEConf0));
4398             rn = "VPEConf0";
4399             break;
4400         case 3:
4401             check_insn(env, ctx, ASE_MT);
4402             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEConf1));
4403             rn = "VPEConf1";
4404             break;
4405         case 4:
4406             check_insn(env, ctx, ASE_MT);
4407             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_YQMask));
4408             rn = "YQMask";
4409             break;
4410         case 5:
4411             check_insn(env, ctx, ASE_MT);
4412             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_VPESchedule));
4413             rn = "VPESchedule";
4414             break;
4415         case 6:
4416             check_insn(env, ctx, ASE_MT);
4417             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_VPEScheFBack));
4418             rn = "VPEScheFBack";
4419             break;
4420         case 7:
4421             check_insn(env, ctx, ASE_MT);
4422             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEOpt));
4423             rn = "VPEOpt";
4424             break;
4425         default:
4426             goto die;
4427         }
4428         break;
4429     case 2:
4430         switch (sel) {
4431         case 0:
4432             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_EntryLo0));
4433             rn = "EntryLo0";
4434             break;
4435         case 1:
4436             check_insn(env, ctx, ASE_MT);
4437             gen_helper_mfc0_tcstatus(arg);
4438             rn = "TCStatus";
4439             break;
4440         case 2:
4441             check_insn(env, ctx, ASE_MT);
4442             gen_helper_mfc0_tcbind(arg);
4443             rn = "TCBind";
4444             break;
4445         case 3:
4446             check_insn(env, ctx, ASE_MT);
4447             gen_helper_dmfc0_tcrestart(arg);
4448             rn = "TCRestart";
4449             break;
4450         case 4:
4451             check_insn(env, ctx, ASE_MT);
4452             gen_helper_dmfc0_tchalt(arg);
4453             rn = "TCHalt";
4454             break;
4455         case 5:
4456             check_insn(env, ctx, ASE_MT);
4457             gen_helper_dmfc0_tccontext(arg);
4458             rn = "TCContext";
4459             break;
4460         case 6:
4461             check_insn(env, ctx, ASE_MT);
4462             gen_helper_dmfc0_tcschedule(arg);
4463             rn = "TCSchedule";
4464             break;
4465         case 7:
4466             check_insn(env, ctx, ASE_MT);
4467             gen_helper_dmfc0_tcschefback(arg);
4468             rn = "TCScheFBack";
4469             break;
4470         default:
4471             goto die;
4472         }
4473         break;
4474     case 3:
4475         switch (sel) {
4476         case 0:
4477             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_EntryLo1));
4478             rn = "EntryLo1";
4479             break;
4480         default:
4481             goto die;
4482         }
4483         break;
4484     case 4:
4485         switch (sel) {
4486         case 0:
4487             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_Context));
4488             rn = "Context";
4489             break;
4490         case 1:
4491 //            gen_helper_dmfc0_contextconfig(arg); /* SmartMIPS ASE */
4492             rn = "ContextConfig";
4493 //            break;
4494         default:
4495             goto die;
4496         }
4497         break;
4498     case 5:
4499         switch (sel) {
4500         case 0:
4501             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PageMask));
4502             rn = "PageMask";
4503             break;
4504         case 1:
4505             check_insn(env, ctx, ISA_MIPS32R2);
4506             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PageGrain));
4507             rn = "PageGrain";
4508             break;
4509         default:
4510             goto die;
4511         }
4512         break;
4513     case 6:
4514         switch (sel) {
4515         case 0:
4516             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Wired));
4517             rn = "Wired";
4518             break;
4519         case 1:
4520             check_insn(env, ctx, ISA_MIPS32R2);
4521             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf0));
4522             rn = "SRSConf0";
4523             break;
4524         case 2:
4525             check_insn(env, ctx, ISA_MIPS32R2);
4526             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf1));
4527             rn = "SRSConf1";
4528             break;
4529         case 3:
4530             check_insn(env, ctx, ISA_MIPS32R2);
4531             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf2));
4532             rn = "SRSConf2";
4533             break;
4534         case 4:
4535             check_insn(env, ctx, ISA_MIPS32R2);
4536             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf3));
4537             rn = "SRSConf3";
4538             break;
4539         case 5:
4540             check_insn(env, ctx, ISA_MIPS32R2);
4541             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf4));
4542             rn = "SRSConf4";
4543             break;
4544         default:
4545             goto die;
4546         }
4547         break;
4548     case 7:
4549         switch (sel) {
4550         case 0:
4551             check_insn(env, ctx, ISA_MIPS32R2);
4552             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_HWREna));
4553             rn = "HWREna";
4554             break;
4555         default:
4556             goto die;
4557         }
4558         break;
4559     case 8:
4560         switch (sel) {
4561         case 0:
4562             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_BadVAddr));
4563             rn = "BadVAddr";
4564             break;
4565         default:
4566             goto die;
4567         }
4568         break;
4569     case 9:
4570         switch (sel) {
4571         case 0:
4572             /* Mark as an IO operation because we read the time.  */
4573             if (use_icount)
4574                 gen_io_start();
4575             gen_helper_mfc0_count(arg);
4576             if (use_icount) {
4577                 gen_io_end();
4578             }
4579             /* Break the TB to be able to take timer interrupts immediately
4580                after reading count.  */
4581             ctx->bstate = BS_STOP;
4582             rn = "Count";
4583             break;
4584         /* 6,7 are implementation dependent */
4585         default:
4586             goto die;
4587         }
4588         break;
4589     case 10:
4590         switch (sel) {
4591         case 0:
4592             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_EntryHi));
4593             rn = "EntryHi";
4594             break;
4595         default:
4596             goto die;
4597         }
4598         break;
4599     case 11:
4600         switch (sel) {
4601         case 0:
4602             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Compare));
4603             rn = "Compare";
4604             break;
4605         /* 6,7 are implementation dependent */
4606         default:
4607             goto die;
4608         }
4609         break;
4610     case 12:
4611         switch (sel) {
4612         case 0:
4613             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Status));
4614             rn = "Status";
4615             break;
4616         case 1:
4617             check_insn(env, ctx, ISA_MIPS32R2);
4618             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_IntCtl));
4619             rn = "IntCtl";
4620             break;
4621         case 2:
4622             check_insn(env, ctx, ISA_MIPS32R2);
4623             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSCtl));
4624             rn = "SRSCtl";
4625             break;
4626         case 3:
4627             check_insn(env, ctx, ISA_MIPS32R2);
4628             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSMap));
4629             rn = "SRSMap";
4630             break;
4631         default:
4632             goto die;
4633         }
4634         break;
4635     case 13:
4636         switch (sel) {
4637         case 0:
4638             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Cause));
4639             rn = "Cause";
4640             break;
4641         default:
4642             goto die;
4643         }
4644         break;
4645     case 14:
4646         switch (sel) {
4647         case 0:
4648             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_EPC));
4649             rn = "EPC";
4650             break;
4651         default:
4652             goto die;
4653         }
4654         break;
4655     case 15:
4656         switch (sel) {
4657         case 0:
4658             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PRid));
4659             rn = "PRid";
4660             break;
4661         case 1:
4662             check_insn(env, ctx, ISA_MIPS32R2);
4663             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_EBase));
4664             rn = "EBase";
4665             break;
4666         default:
4667             goto die;
4668         }
4669         break;
4670     case 16:
4671         switch (sel) {
4672         case 0:
4673             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config0));
4674             rn = "Config";
4675             break;
4676         case 1:
4677             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config1));
4678             rn = "Config1";
4679             break;
4680         case 2:
4681             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config2));
4682             rn = "Config2";
4683             break;
4684         case 3:
4685             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config3));
4686             rn = "Config3";
4687             break;
4688        /* 6,7 are implementation dependent */
4689         case 6:
4690             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config6));
4691             rn = "Config6";
4692             break;
4693         case 7:
4694             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config7));
4695             rn = "Config7";
4696             break;
4697         default:
4698             goto die;
4699         }
4700         break;
4701     case 17:
4702         switch (sel) {
4703         case 0:
4704             gen_helper_dmfc0_lladdr(arg);
4705             rn = "LLAddr";
4706             break;
4707         default:
4708             goto die;
4709         }
4710         break;
4711     case 18:
4712         switch (sel) {
4713         case 0 ... 7:
4714             gen_helper_1i(dmfc0_watchlo, arg, sel);
4715             rn = "WatchLo";
4716             break;
4717         default:
4718             goto die;
4719         }
4720         break;
4721     case 19:
4722         switch (sel) {
4723         case 0 ... 7:
4724             gen_helper_1i(mfc0_watchhi, arg, sel);
4725             rn = "WatchHi";
4726             break;
4727         default:
4728             goto die;
4729         }
4730         break;
4731     case 20:
4732         switch (sel) {
4733         case 0:
4734             check_insn(env, ctx, ISA_MIPS3);
4735             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_XContext));
4736             rn = "XContext";
4737             break;
4738         default:
4739             goto die;
4740         }
4741         break;
4742     case 21:
4743        /* Officially reserved, but sel 0 is used for R1x000 framemask */
4744         switch (sel) {
4745         case 0:
4746             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Framemask));
4747             rn = "Framemask";
4748             break;
4749         default:
4750             goto die;
4751         }
4752         break;
4753     case 22:
4754         tcg_gen_movi_tl(arg, 0); /* unimplemented */
4755         rn = "'Diagnostic"; /* implementation dependent */
4756         break;
4757     case 23:
4758         switch (sel) {
4759         case 0:
4760             gen_helper_mfc0_debug(arg); /* EJTAG support */
4761             rn = "Debug";
4762             break;
4763         case 1:
4764 //            gen_helper_dmfc0_tracecontrol(arg); /* PDtrace support */
4765             rn = "TraceControl";
4766 //            break;
4767         case 2:
4768 //            gen_helper_dmfc0_tracecontrol2(arg); /* PDtrace support */
4769             rn = "TraceControl2";
4770 //            break;
4771         case 3:
4772 //            gen_helper_dmfc0_usertracedata(arg); /* PDtrace support */
4773             rn = "UserTraceData";
4774 //            break;
4775         case 4:
4776 //            gen_helper_dmfc0_tracebpc(arg); /* PDtrace support */
4777             rn = "TraceBPC";
4778 //            break;
4779         default:
4780             goto die;
4781         }
4782         break;
4783     case 24:
4784         switch (sel) {
4785         case 0:
4786             /* EJTAG support */
4787             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_DEPC));
4788             rn = "DEPC";
4789             break;
4790         default:
4791             goto die;
4792         }
4793         break;
4794     case 25:
4795         switch (sel) {
4796         case 0:
4797             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Performance0));
4798             rn = "Performance0";
4799             break;
4800         case 1:
4801 //            gen_helper_dmfc0_performance1(arg);
4802             rn = "Performance1";
4803 //            break;
4804         case 2:
4805 //            gen_helper_dmfc0_performance2(arg);
4806             rn = "Performance2";
4807 //            break;
4808         case 3:
4809 //            gen_helper_dmfc0_performance3(arg);
4810             rn = "Performance3";
4811 //            break;
4812         case 4:
4813 //            gen_helper_dmfc0_performance4(arg);
4814             rn = "Performance4";
4815 //            break;
4816         case 5:
4817 //            gen_helper_dmfc0_performance5(arg);
4818             rn = "Performance5";
4819 //            break;
4820         case 6:
4821 //            gen_helper_dmfc0_performance6(arg);
4822             rn = "Performance6";
4823 //            break;
4824         case 7:
4825 //            gen_helper_dmfc0_performance7(arg);
4826             rn = "Performance7";
4827 //            break;
4828         default:
4829             goto die;
4830         }
4831         break;
4832     case 26:
4833         tcg_gen_movi_tl(arg, 0); /* unimplemented */
4834         rn = "ECC";
4835         break;
4836     case 27:
4837         switch (sel) {
4838         /* ignored */
4839         case 0 ... 3:
4840             tcg_gen_movi_tl(arg, 0); /* unimplemented */
4841             rn = "CacheErr";
4842             break;
4843         default:
4844             goto die;
4845         }
4846         break;
4847     case 28:
4848         switch (sel) {
4849         case 0:
4850         case 2:
4851         case 4:
4852         case 6:
4853             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_TagLo));
4854             rn = "TagLo";
4855             break;
4856         case 1:
4857         case 3:
4858         case 5:
4859         case 7:
4860             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DataLo));
4861             rn = "DataLo";
4862             break;
4863         default:
4864             goto die;
4865         }
4866         break;
4867     case 29:
4868         switch (sel) {
4869         case 0:
4870         case 2:
4871         case 4:
4872         case 6:
4873             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_TagHi));
4874             rn = "TagHi";
4875             break;
4876         case 1:
4877         case 3:
4878         case 5:
4879         case 7:
4880             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DataHi));
4881             rn = "DataHi";
4882             break;
4883         default:
4884             goto die;
4885         }
4886         break;
4887     case 30:
4888         switch (sel) {
4889         case 0:
4890             tcg_gen_ld_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_ErrorEPC));
4891             rn = "ErrorEPC";
4892             break;
4893         default:
4894             goto die;
4895         }
4896         break;
4897     case 31:
4898         switch (sel) {
4899         case 0:
4900             /* EJTAG support */
4901             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DESAVE));
4902             rn = "DESAVE";
4903             break;
4904         default:
4905             goto die;
4906         }
4907         break;
4908     default:
4909         goto die;
4910     }
4911     (void)rn; /* avoid a compiler warning */
4912     LOG_DISAS("dmfc0 %s (reg %d sel %d)\n", rn, reg, sel);
4913     return;
4914
4915 die:
4916     LOG_DISAS("dmfc0 %s (reg %d sel %d)\n", rn, reg, sel);
4917     generate_exception(ctx, EXCP_RI);
4918 }
4919
4920 static void gen_dmtc0 (CPUMIPSState *env, DisasContext *ctx, TCGv arg, int reg, int sel)
4921 {
4922     const char *rn = "invalid";
4923
4924     if (sel != 0)
4925         check_insn(env, ctx, ISA_MIPS64);
4926
4927     if (use_icount)
4928         gen_io_start();
4929
4930     switch (reg) {
4931     case 0:
4932         switch (sel) {
4933         case 0:
4934             gen_helper_mtc0_index(arg);
4935             rn = "Index";
4936             break;
4937         case 1:
4938             check_insn(env, ctx, ASE_MT);
4939             gen_helper_mtc0_mvpcontrol(arg);
4940             rn = "MVPControl";
4941             break;
4942         case 2:
4943             check_insn(env, ctx, ASE_MT);
4944             /* ignored */
4945             rn = "MVPConf0";
4946             break;
4947         case 3:
4948             check_insn(env, ctx, ASE_MT);
4949             /* ignored */
4950             rn = "MVPConf1";
4951             break;
4952         default:
4953             goto die;
4954         }
4955         break;
4956     case 1:
4957         switch (sel) {
4958         case 0:
4959             /* ignored */
4960             rn = "Random";
4961             break;
4962         case 1:
4963             check_insn(env, ctx, ASE_MT);
4964             gen_helper_mtc0_vpecontrol(arg);
4965             rn = "VPEControl";
4966             break;
4967         case 2:
4968             check_insn(env, ctx, ASE_MT);
4969             gen_helper_mtc0_vpeconf0(arg);
4970             rn = "VPEConf0";
4971             break;
4972         case 3:
4973             check_insn(env, ctx, ASE_MT);
4974             gen_helper_mtc0_vpeconf1(arg);
4975             rn = "VPEConf1";
4976             break;
4977         case 4:
4978             check_insn(env, ctx, ASE_MT);
4979             gen_helper_mtc0_yqmask(arg);
4980             rn = "YQMask";
4981             break;
4982         case 5:
4983             check_insn(env, ctx, ASE_MT);
4984             tcg_gen_st_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_VPESchedule));
4985             rn = "VPESchedule";
4986             break;
4987         case 6:
4988             check_insn(env, ctx, ASE_MT);
4989             tcg_gen_st_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_VPEScheFBack));
4990             rn = "VPEScheFBack";
4991             break;
4992         case 7:
4993             check_insn(env, ctx, ASE_MT);
4994             gen_helper_mtc0_vpeopt(arg);
4995             rn = "VPEOpt";
4996             break;
4997         default:
4998             goto die;
4999         }
5000         break;
5001     case 2:
5002         switch (sel) {
5003         case 0:
5004             gen_helper_mtc0_entrylo0(arg);
5005             rn = "EntryLo0";
5006             break;
5007         case 1:
5008             check_insn(env, ctx, ASE_MT);
5009             gen_helper_mtc0_tcstatus(arg);
5010             rn = "TCStatus";
5011             break;
5012         case 2:
5013             check_insn(env, ctx, ASE_MT);
5014             gen_helper_mtc0_tcbind(arg);
5015             rn = "TCBind";
5016             break;
5017         case 3:
5018             check_insn(env, ctx, ASE_MT);
5019             gen_helper_mtc0_tcrestart(arg);
5020             rn = "TCRestart";
5021             break;
5022         case 4:
5023             check_insn(env, ctx, ASE_MT);
5024             gen_helper_mtc0_tchalt(arg);
5025             rn = "TCHalt";
5026             break;
5027         case 5:
5028             check_insn(env, ctx, ASE_MT);
5029             gen_helper_mtc0_tccontext(arg);
5030             rn = "TCContext";
5031             break;
5032         case 6:
5033             check_insn(env, ctx, ASE_MT);
5034             gen_helper_mtc0_tcschedule(arg);
5035             rn = "TCSchedule";
5036             break;
5037         case 7:
5038             check_insn(env, ctx, ASE_MT);
5039             gen_helper_mtc0_tcschefback(arg);
5040             rn = "TCScheFBack";
5041             break;
5042         default:
5043             goto die;
5044         }
5045         break;
5046     case 3:
5047         switch (sel) {
5048         case 0:
5049             gen_helper_mtc0_entrylo1(arg);
5050             rn = "EntryLo1";
5051             break;
5052         default:
5053             goto die;
5054         }
5055         break;
5056     case 4:
5057         switch (sel) {
5058         case 0:
5059             gen_helper_mtc0_context(arg);
5060             rn = "Context";
5061             break;
5062         case 1:
5063 //           gen_helper_mtc0_contextconfig(arg); /* SmartMIPS ASE */
5064             rn = "ContextConfig";
5065 //           break;
5066         default:
5067             goto die;
5068         }
5069         break;
5070     case 5:
5071         switch (sel) {
5072         case 0:
5073             gen_helper_mtc0_pagemask(arg);
5074             rn = "PageMask";
5075             break;
5076         case 1:
5077             check_insn(env, ctx, ISA_MIPS32R2);
5078             gen_helper_mtc0_pagegrain(arg);
5079             rn = "PageGrain";
5080             break;
5081         default:
5082             goto die;
5083         }
5084         break;
5085     case 6:
5086         switch (sel) {
5087         case 0:
5088             gen_helper_mtc0_wired(arg);
5089             rn = "Wired";
5090             break;
5091         case 1:
5092             check_insn(env, ctx, ISA_MIPS32R2);
5093             gen_helper_mtc0_srsconf0(arg);
5094             rn = "SRSConf0";
5095             break;
5096         case 2:
5097             check_insn(env, ctx, ISA_MIPS32R2);
5098             gen_helper_mtc0_srsconf1(arg);
5099             rn = "SRSConf1";
5100             break;
5101         case 3:
5102             check_insn(env, ctx, ISA_MIPS32R2);
5103             gen_helper_mtc0_srsconf2(arg);
5104             rn = "SRSConf2";
5105             break;
5106         case 4:
5107             check_insn(env, ctx, ISA_MIPS32R2);
5108             gen_helper_mtc0_srsconf3(arg);
5109             rn = "SRSConf3";
5110             break;
5111         case 5:
5112             check_insn(env, ctx, ISA_MIPS32R2);
5113             gen_helper_mtc0_srsconf4(arg);
5114             rn = "SRSConf4";
5115             break;
5116         default:
5117             goto die;
5118         }
5119         break;
5120     case 7:
5121         switch (sel) {
5122         case 0:
5123             check_insn(env, ctx, ISA_MIPS32R2);
5124             gen_helper_mtc0_hwrena(arg);
5125             rn = "HWREna";
5126             break;
5127         default:
5128             goto die;
5129         }
5130         break;
5131     case 8:
5132         /* ignored */
5133         rn = "BadVAddr";
5134         break;
5135     case 9:
5136         switch (sel) {
5137         case 0:
5138             gen_helper_mtc0_count(arg);
5139             rn = "Count";
5140             break;
5141         /* 6,7 are implementation dependent */
5142         default:
5143             goto die;
5144         }
5145         /* Stop translation as we may have switched the execution mode */
5146         ctx->bstate = BS_STOP;
5147         break;
5148     case 10:
5149         switch (sel) {
5150         case 0:
5151             gen_helper_mtc0_entryhi(arg);
5152             rn = "EntryHi";
5153             break;
5154         default:
5155             goto die;
5156         }
5157         break;
5158     case 11:
5159         switch (sel) {
5160         case 0:
5161             gen_helper_mtc0_compare(arg);
5162             rn = "Compare";
5163             break;
5164         /* 6,7 are implementation dependent */
5165         default:
5166             goto die;
5167         }
5168         /* Stop translation as we may have switched the execution mode */
5169         ctx->bstate = BS_STOP;
5170         break;
5171     case 12:
5172         switch (sel) {
5173         case 0:
5174             save_cpu_state(ctx, 1);
5175             gen_helper_mtc0_status(arg);
5176             /* BS_STOP isn't good enough here, hflags may have changed. */
5177             gen_save_pc(ctx->pc + 4);
5178             ctx->bstate = BS_EXCP;
5179             rn = "Status";
5180             break;
5181         case 1:
5182             check_insn(env, ctx, ISA_MIPS32R2);
5183             gen_helper_mtc0_intctl(arg);
5184             /* Stop translation as we may have switched the execution mode */
5185             ctx->bstate = BS_STOP;
5186             rn = "IntCtl";
5187             break;
5188         case 2:
5189             check_insn(env, ctx, ISA_MIPS32R2);
5190             gen_helper_mtc0_srsctl(arg);
5191             /* Stop translation as we may have switched the execution mode */
5192             ctx->bstate = BS_STOP;
5193             rn = "SRSCtl";
5194             break;
5195         case 3:
5196             check_insn(env, ctx, ISA_MIPS32R2);
5197             gen_mtc0_store32(arg, offsetof(CPUMIPSState, CP0_SRSMap));
5198             /* Stop translation as we may have switched the execution mode */
5199             ctx->bstate = BS_STOP;
5200             rn = "SRSMap";
5201             break;
5202         default:
5203             goto die;
5204         }
5205         break;
5206     case 13:
5207         switch (sel) {
5208         case 0:
5209             save_cpu_state(ctx, 1);
5210             /* Mark as an IO operation because we may trigger a software
5211                interrupt.  */
5212             if (use_icount) {
5213                 gen_io_start();
5214             }
5215             gen_helper_mtc0_cause(arg);
5216             if (use_icount) {
5217                 gen_io_end();
5218             }
5219             /* Stop translation as we may have triggered an intetrupt */
5220             ctx->bstate = BS_STOP;
5221             rn = "Cause";
5222             break;
5223         default:
5224             goto die;
5225         }
5226         break;
5227     case 14:
5228         switch (sel) {
5229         case 0:
5230             tcg_gen_st_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_EPC));
5231             rn = "EPC";
5232             break;
5233         default:
5234             goto die;
5235         }
5236         break;
5237     case 15:
5238         switch (sel) {
5239         case 0:
5240             /* ignored */
5241             rn = "PRid";
5242             break;
5243         case 1:
5244             check_insn(env, ctx, ISA_MIPS32R2);
5245             gen_helper_mtc0_ebase(arg);
5246             rn = "EBase";
5247             break;
5248         default:
5249             goto die;
5250         }
5251         break;
5252     case 16:
5253         switch (sel) {
5254         case 0:
5255             gen_helper_mtc0_config0(arg);
5256             rn = "Config";
5257             /* Stop translation as we may have switched the execution mode */
5258             ctx->bstate = BS_STOP;
5259             break;
5260         case 1:
5261             /* ignored, read only */
5262             rn = "Config1";
5263             break;
5264         case 2:
5265             gen_helper_mtc0_config2(arg);
5266             rn = "Config2";
5267             /* Stop translation as we may have switched the execution mode */
5268             ctx->bstate = BS_STOP;
5269             break;
5270         case 3:
5271             /* ignored */
5272             rn = "Config3";
5273             break;
5274         /* 6,7 are implementation dependent */
5275         default:
5276             rn = "Invalid config selector";
5277             goto die;
5278         }
5279         break;
5280     case 17:
5281         switch (sel) {
5282         case 0:
5283             gen_helper_mtc0_lladdr(arg);
5284             rn = "LLAddr";
5285             break;
5286         default:
5287             goto die;
5288         }
5289         break;
5290     case 18:
5291         switch (sel) {
5292         case 0 ... 7:
5293             gen_helper_1i(mtc0_watchlo, arg, sel);
5294             rn = "WatchLo";
5295             break;
5296         default:
5297             goto die;
5298         }
5299         break;
5300     case 19:
5301         switch (sel) {
5302         case 0 ... 7:
5303             gen_helper_1i(mtc0_watchhi, arg, sel);
5304             rn = "WatchHi";
5305             break;
5306         default:
5307             goto die;
5308         }
5309         break;
5310     case 20:
5311         switch (sel) {
5312         case 0:
5313             check_insn(env, ctx, ISA_MIPS3);
5314             gen_helper_mtc0_xcontext(arg);
5315             rn = "XContext";
5316             break;
5317         default:
5318             goto die;
5319         }
5320         break;
5321     case 21:
5322        /* Officially reserved, but sel 0 is used for R1x000 framemask */
5323         switch (sel) {
5324         case 0:
5325             gen_helper_mtc0_framemask(arg);
5326             rn = "Framemask";
5327             break;
5328         default:
5329             goto die;
5330         }
5331         break;
5332     case 22:
5333         /* ignored */
5334         rn = "Diagnostic"; /* implementation dependent */
5335         break;
5336     case 23:
5337         switch (sel) {
5338         case 0:
5339             gen_helper_mtc0_debug(arg); /* EJTAG support */
5340             /* BS_STOP isn't good enough here, hflags may have changed. */
5341             gen_save_pc(ctx->pc + 4);
5342             ctx->bstate = BS_EXCP;
5343             rn = "Debug";
5344             break;
5345         case 1:
5346 //            gen_helper_mtc0_tracecontrol(arg); /* PDtrace support */
5347             /* Stop translation as we may have switched the execution mode */
5348             ctx->bstate = BS_STOP;
5349             rn = "TraceControl";
5350 //            break;
5351         case 2:
5352 //            gen_helper_mtc0_tracecontrol2(arg); /* PDtrace support */
5353             /* Stop translation as we may have switched the execution mode */
5354             ctx->bstate = BS_STOP;
5355             rn = "TraceControl2";
5356 //            break;
5357         case 3:
5358 //            gen_helper_mtc0_usertracedata(arg); /* PDtrace support */
5359             /* Stop translation as we may have switched the execution mode */
5360             ctx->bstate = BS_STOP;
5361             rn = "UserTraceData";
5362 //            break;
5363         case 4:
5364 //            gen_helper_mtc0_tracebpc(arg); /* PDtrace support */
5365             /* Stop translation as we may have switched the execution mode */
5366             ctx->bstate = BS_STOP;
5367             rn = "TraceBPC";
5368 //            break;
5369         default:
5370             goto die;
5371         }
5372         break;
5373     case 24:
5374         switch (sel) {
5375         case 0:
5376             /* EJTAG support */
5377             tcg_gen_st_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_DEPC));
5378             rn = "DEPC";
5379             break;
5380         default:
5381             goto die;
5382         }
5383         break;
5384     case 25:
5385         switch (sel) {
5386         case 0:
5387             gen_helper_mtc0_performance0(arg);
5388             rn = "Performance0";
5389             break;
5390         case 1:
5391 //            gen_helper_mtc0_performance1(arg);
5392             rn = "Performance1";
5393 //            break;
5394         case 2:
5395 //            gen_helper_mtc0_performance2(arg);
5396             rn = "Performance2";
5397 //            break;
5398         case 3:
5399 //            gen_helper_mtc0_performance3(arg);
5400             rn = "Performance3";
5401 //            break;
5402         case 4:
5403 //            gen_helper_mtc0_performance4(arg);
5404             rn = "Performance4";
5405 //            break;
5406         case 5:
5407 //            gen_helper_mtc0_performance5(arg);
5408             rn = "Performance5";
5409 //            break;
5410         case 6:
5411 //            gen_helper_mtc0_performance6(arg);
5412             rn = "Performance6";
5413 //            break;
5414         case 7:
5415 //            gen_helper_mtc0_performance7(arg);
5416             rn = "Performance7";
5417 //            break;
5418         default:
5419             goto die;
5420         }
5421         break;
5422     case 26:
5423         /* ignored */
5424         rn = "ECC";
5425         break;
5426     case 27:
5427         switch (sel) {
5428         case 0 ... 3:
5429             /* ignored */
5430             rn = "CacheErr";
5431             break;
5432         default:
5433             goto die;
5434         }
5435         break;
5436     case 28:
5437         switch (sel) {
5438         case 0:
5439         case 2:
5440         case 4:
5441         case 6:
5442             gen_helper_mtc0_taglo(arg);
5443             rn = "TagLo";
5444             break;
5445         case 1:
5446         case 3:
5447         case 5:
5448         case 7:
5449             gen_helper_mtc0_datalo(arg);
5450             rn = "DataLo";
5451             break;
5452         default:
5453             goto die;
5454         }
5455         break;
5456     case 29:
5457         switch (sel) {
5458         case 0:
5459         case 2:
5460         case 4:
5461         case 6:
5462             gen_helper_mtc0_taghi(arg);
5463             rn = "TagHi";
5464             break;
5465         case 1:
5466         case 3:
5467         case 5:
5468         case 7:
5469             gen_helper_mtc0_datahi(arg);
5470             rn = "DataHi";
5471             break;
5472         default:
5473             rn = "invalid sel";
5474             goto die;
5475         }
5476         break;
5477     case 30:
5478         switch (sel) {
5479         case 0:
5480             tcg_gen_st_tl(arg, cpu_env, offsetof(CPUMIPSState, CP0_ErrorEPC));
5481             rn = "ErrorEPC";
5482             break;
5483         default:
5484             goto die;
5485         }
5486         break;
5487     case 31:
5488         switch (sel) {
5489         case 0:
5490             /* EJTAG support */
5491             gen_mtc0_store32(arg, offsetof(CPUMIPSState, CP0_DESAVE));
5492             rn = "DESAVE";
5493             break;
5494         default:
5495             goto die;
5496         }
5497         /* Stop translation as we may have switched the execution mode */
5498         ctx->bstate = BS_STOP;
5499         break;
5500     default:
5501         goto die;
5502     }
5503     (void)rn; /* avoid a compiler warning */
5504     LOG_DISAS("dmtc0 %s (reg %d sel %d)\n", rn, reg, sel);
5505     /* For simplicity assume that all writes can cause interrupts.  */
5506     if (use_icount) {
5507         gen_io_end();
5508         ctx->bstate = BS_STOP;
5509     }
5510     return;
5511
5512 die:
5513     LOG_DISAS("dmtc0 %s (reg %d sel %d)\n", rn, reg, sel);
5514     generate_exception(ctx, EXCP_RI);
5515 }
5516 #endif /* TARGET_MIPS64 */
5517
5518 static void gen_mftr(CPUMIPSState *env, DisasContext *ctx, int rt, int rd,
5519                      int u, int sel, int h)
5520 {
5521     int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
5522     TCGv t0 = tcg_temp_local_new();
5523
5524     if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
5525         ((env->tcs[other_tc].CP0_TCBind & (0xf << CP0TCBd_CurVPE)) !=
5526          (env->active_tc.CP0_TCBind & (0xf << CP0TCBd_CurVPE))))
5527         tcg_gen_movi_tl(t0, -1);
5528     else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
5529              (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC)))
5530         tcg_gen_movi_tl(t0, -1);
5531     else if (u == 0) {
5532         switch (rt) {
5533         case 1:
5534             switch (sel) {
5535             case 1:
5536                 gen_helper_mftc0_vpecontrol(t0);
5537                 break;
5538             case 2:
5539                 gen_helper_mftc0_vpeconf0(t0);
5540                 break;
5541             default:
5542                 goto die;
5543                 break;
5544             }
5545             break;
5546         case 2:
5547             switch (sel) {
5548             case 1:
5549                 gen_helper_mftc0_tcstatus(t0);
5550                 break;
5551             case 2:
5552                 gen_helper_mftc0_tcbind(t0);
5553                 break;
5554             case 3:
5555                 gen_helper_mftc0_tcrestart(t0);
5556                 break;
5557             case 4:
5558                 gen_helper_mftc0_tchalt(t0);
5559                 break;
5560             case 5:
5561                 gen_helper_mftc0_tccontext(t0);
5562                 break;
5563             case 6:
5564                 gen_helper_mftc0_tcschedule(t0);
5565                 break;
5566             case 7:
5567                 gen_helper_mftc0_tcschefback(t0);
5568                 break;
5569             default:
5570                 gen_mfc0(env, ctx, t0, rt, sel);
5571                 break;
5572             }
5573             break;
5574         case 10:
5575             switch (sel) {
5576             case 0:
5577                 gen_helper_mftc0_entryhi(t0);
5578                 break;
5579             default:
5580                 gen_mfc0(env, ctx, t0, rt, sel);
5581                 break;
5582             }
5583         case 12:
5584             switch (sel) {
5585             case 0:
5586                 gen_helper_mftc0_status(t0);
5587                 break;
5588             default:
5589                 gen_mfc0(env, ctx, t0, rt, sel);
5590                 break;
5591             }
5592         case 13:
5593             switch (sel) {
5594             case 0:
5595                 gen_helper_mftc0_cause(t0);
5596                 break;
5597             default:
5598                 goto die;
5599                 break;
5600             }
5601             break;
5602         case 14:
5603             switch (sel) {
5604             case 0:
5605                 gen_helper_mftc0_epc(t0);
5606                 break;
5607             default:
5608                 goto die;
5609                 break;
5610             }
5611             break;
5612         case 15:
5613             switch (sel) {
5614             case 1:
5615                 gen_helper_mftc0_ebase(t0);
5616                 break;
5617             default:
5618                 goto die;
5619                 break;
5620             }
5621             break;
5622         case 16:
5623             switch (sel) {
5624             case 0 ... 7:
5625                 gen_helper_mftc0_configx(t0, tcg_const_tl(sel));
5626                 break;
5627             default:
5628                 goto die;
5629                 break;
5630             }
5631             break;
5632         case 23:
5633             switch (sel) {
5634             case 0:
5635                 gen_helper_mftc0_debug(t0);
5636                 break;
5637             default:
5638                 gen_mfc0(env, ctx, t0, rt, sel);
5639                 break;
5640             }
5641             break;
5642         default:
5643             gen_mfc0(env, ctx, t0, rt, sel);
5644         }
5645     } else switch (sel) {
5646     /* GPR registers. */
5647     case 0:
5648         gen_helper_1i(mftgpr, t0, rt);
5649         break;
5650     /* Auxiliary CPU registers */
5651     case 1:
5652         switch (rt) {
5653         case 0:
5654             gen_helper_1i(mftlo, t0, 0);
5655             break;
5656         case 1:
5657             gen_helper_1i(mfthi, t0, 0);
5658             break;
5659         case 2:
5660             gen_helper_1i(mftacx, t0, 0);
5661             break;
5662         case 4:
5663             gen_helper_1i(mftlo, t0, 1);
5664             break;
5665         case 5:
5666             gen_helper_1i(mfthi, t0, 1);
5667             break;
5668         case 6:
5669             gen_helper_1i(mftacx, t0, 1);
5670             break;
5671         case 8:
5672             gen_helper_1i(mftlo, t0, 2);
5673             break;
5674         case 9:
5675             gen_helper_1i(mfthi, t0, 2);
5676             break;
5677         case 10:
5678             gen_helper_1i(mftacx, t0, 2);
5679             break;
5680         case 12:
5681             gen_helper_1i(mftlo, t0, 3);
5682             break;
5683         case 13:
5684             gen_helper_1i(mfthi, t0, 3);
5685             break;
5686         case 14:
5687             gen_helper_1i(mftacx, t0, 3);
5688             break;
5689         case 16:
5690             gen_helper_mftdsp(t0);
5691             break;
5692         default:
5693             goto die;
5694         }
5695         break;
5696     /* Floating point (COP1). */
5697     case 2:
5698         /* XXX: For now we support only a single FPU context. */
5699         if (h == 0) {
5700             TCGv_i32 fp0 = tcg_temp_new_i32();
5701
5702             gen_load_fpr32(fp0, rt);
5703             tcg_gen_ext_i32_tl(t0, fp0);
5704             tcg_temp_free_i32(fp0);
5705         } else {
5706             TCGv_i32 fp0 = tcg_temp_new_i32();
5707
5708             gen_load_fpr32h(fp0, rt);
5709             tcg_gen_ext_i32_tl(t0, fp0);
5710             tcg_temp_free_i32(fp0);
5711         }
5712         break;
5713     case 3:
5714         /* XXX: For now we support only a single FPU context. */
5715         gen_helper_1i(cfc1, t0, rt);
5716         break;
5717     /* COP2: Not implemented. */
5718     case 4:
5719     case 5:
5720         /* fall through */
5721     default:
5722         goto die;
5723     }
5724     LOG_DISAS("mftr (reg %d u %d sel %d h %d)\n", rt, u, sel, h);
5725     gen_store_gpr(t0, rd);
5726     tcg_temp_free(t0);
5727     return;
5728
5729 die:
5730     tcg_temp_free(t0);
5731     LOG_DISAS("mftr (reg %d u %d sel %d h %d)\n", rt, u, sel, h);
5732     generate_exception(ctx, EXCP_RI);
5733 }
5734
5735 static void gen_mttr(CPUMIPSState *env, DisasContext *ctx, int rd, int rt,
5736                      int u, int sel, int h)
5737 {
5738     int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
5739     TCGv t0 = tcg_temp_local_new();
5740
5741     gen_load_gpr(t0, rt);
5742     if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
5743         ((env->tcs[other_tc].CP0_TCBind & (0xf << CP0TCBd_CurVPE)) !=
5744          (env->active_tc.CP0_TCBind & (0xf << CP0TCBd_CurVPE))))
5745         /* NOP */ ;
5746     else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
5747              (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC)))
5748         /* NOP */ ;
5749     else if (u == 0) {
5750         switch (rd) {
5751         case 1:
5752             switch (sel) {
5753             case 1:
5754                 gen_helper_mttc0_vpecontrol(t0);
5755                 break;
5756             case 2:
5757                 gen_helper_mttc0_vpeconf0(t0);
5758                 break;
5759             default:
5760                 goto die;
5761                 break;
5762             }
5763             break;
5764         case 2:
5765             switch (sel) {
5766             case 1:
5767                 gen_helper_mttc0_tcstatus(t0);
5768                 break;
5769             case 2:
5770                 gen_helper_mttc0_tcbind(t0);
5771                 break;
5772             case 3:
5773                 gen_helper_mttc0_tcrestart(t0);
5774                 break;
5775             case 4:
5776                 gen_helper_mttc0_tchalt(t0);
5777                 break;
5778             case 5:
5779                 gen_helper_mttc0_tccontext(t0);
5780                 break;
5781             case 6:
5782                 gen_helper_mttc0_tcschedule(t0);
5783                 break;
5784             case 7:
5785                 gen_helper_mttc0_tcschefback(t0);
5786                 break;
5787             default:
5788                 gen_mtc0(env, ctx, t0, rd, sel);
5789                 break;
5790             }
5791             break;
5792         case 10:
5793             switch (sel) {
5794             case 0:
5795                 gen_helper_mttc0_entryhi(t0);
5796                 break;
5797             default:
5798                 gen_mtc0(env, ctx, t0, rd, sel);
5799                 break;
5800             }
5801         case 12:
5802             switch (sel) {
5803             case 0:
5804                 gen_helper_mttc0_status(t0);
5805                 break;
5806             default:
5807                 gen_mtc0(env, ctx, t0, rd, sel);
5808                 break;
5809             }
5810         case 13:
5811             switch (sel) {
5812             case 0:
5813                 gen_helper_mttc0_cause(t0);
5814                 break;
5815             default:
5816                 goto die;
5817                 break;
5818             }
5819             break;
5820         case 15:
5821             switch (sel) {
5822             case 1:
5823                 gen_helper_mttc0_ebase(t0);
5824                 break;
5825             default:
5826                 goto die;
5827                 break;
5828             }
5829             break;
5830         case 23:
5831             switch (sel) {
5832             case 0:
5833                 gen_helper_mttc0_debug(t0);
5834                 break;
5835             default:
5836                 gen_mtc0(env, ctx, t0, rd, sel);
5837                 break;
5838             }
5839             break;
5840         default:
5841             gen_mtc0(env, ctx, t0, rd, sel);
5842         }
5843     } else switch (sel) {
5844     /* GPR registers. */
5845     case 0:
5846         gen_helper_1i(mttgpr, t0, rd);
5847         break;
5848     /* Auxiliary CPU registers */
5849     case 1:
5850         switch (rd) {
5851         case 0:
5852             gen_helper_1i(mttlo, t0, 0);
5853             break;
5854         case 1:
5855             gen_helper_1i(mtthi, t0, 0);
5856             break;
5857         case 2:
5858             gen_helper_1i(mttacx, t0, 0);
5859             break;
5860         case 4:
5861             gen_helper_1i(mttlo, t0, 1);
5862             break;
5863         case 5:
5864             gen_helper_1i(mtthi, t0, 1);
5865             break;
5866         case 6:
5867             gen_helper_1i(mttacx, t0, 1);
5868             break;
5869         case 8:
5870             gen_helper_1i(mttlo, t0, 2);
5871             break;
5872         case 9:
5873             gen_helper_1i(mtthi, t0, 2);
5874             break;
5875         case 10:
5876             gen_helper_1i(mttacx, t0, 2);
5877             break;
5878         case 12:
5879             gen_helper_1i(mttlo, t0, 3);
5880             break;
5881         case 13:
5882             gen_helper_1i(mtthi, t0, 3);
5883             break;
5884         case 14:
5885             gen_helper_1i(mttacx, t0, 3);
5886             break;
5887         case 16:
5888             gen_helper_mttdsp(t0);
5889             break;
5890         default:
5891             goto die;
5892         }
5893         break;
5894     /* Floating point (COP1). */
5895     case 2:
5896         /* XXX: For now we support only a single FPU context. */
5897         if (h == 0) {
5898             TCGv_i32 fp0 = tcg_temp_new_i32();
5899
5900             tcg_gen_trunc_tl_i32(fp0, t0);
5901             gen_store_fpr32(fp0, rd);
5902             tcg_temp_free_i32(fp0);
5903         } else {
5904             TCGv_i32 fp0 = tcg_temp_new_i32();
5905
5906             tcg_gen_trunc_tl_i32(fp0, t0);
5907             gen_store_fpr32h(fp0, rd);
5908             tcg_temp_free_i32(fp0);
5909         }
5910         break;
5911     case 3:
5912         /* XXX: For now we support only a single FPU context. */
5913         gen_helper_1i(ctc1, t0, rd);
5914         break;
5915     /* COP2: Not implemented. */
5916     case 4:
5917     case 5:
5918         /* fall through */
5919     default:
5920         goto die;
5921     }
5922     LOG_DISAS("mttr (reg %d u %d sel %d h %d)\n", rd, u, sel, h);
5923     tcg_temp_free(t0);
5924     return;
5925
5926 die:
5927     tcg_temp_free(t0);
5928     LOG_DISAS("mttr (reg %d u %d sel %d h %d)\n", rd, u, sel, h);
5929     generate_exception(ctx, EXCP_RI);
5930 }
5931
5932 static void gen_cp0 (CPUMIPSState *env, DisasContext *ctx, uint32_t opc, int rt, int rd)
5933 {
5934     const char *opn = "ldst";
5935
5936     check_cp0_enabled(ctx);
5937     switch (opc) {
5938     case OPC_MFC0:
5939         if (rt == 0) {
5940             /* Treat as NOP. */
5941             return;
5942         }
5943         gen_mfc0(env, ctx, cpu_gpr[rt], rd, ctx->opcode & 0x7);
5944         opn = "mfc0";
5945         break;
5946     case OPC_MTC0:
5947         {
5948             TCGv t0 = tcg_temp_new();
5949
5950             gen_load_gpr(t0, rt);
5951             gen_mtc0(env, ctx, t0, rd, ctx->opcode & 0x7);
5952             tcg_temp_free(t0);
5953         }
5954         opn = "mtc0";
5955         break;
5956 #if defined(TARGET_MIPS64)
5957     case OPC_DMFC0:
5958         check_insn(env, ctx, ISA_MIPS3);
5959         if (rt == 0) {
5960             /* Treat as NOP. */
5961             return;
5962         }
5963         gen_dmfc0(env, ctx, cpu_gpr[rt], rd, ctx->opcode & 0x7);
5964         opn = "dmfc0";
5965         break;
5966     case OPC_DMTC0:
5967         check_insn(env, ctx, ISA_MIPS3);
5968         {
5969             TCGv t0 = tcg_temp_new();
5970
5971             gen_load_gpr(t0, rt);
5972             gen_dmtc0(env, ctx, t0, rd, ctx->opcode & 0x7);
5973             tcg_temp_free(t0);
5974         }
5975         opn = "dmtc0";
5976         break;
5977 #endif
5978     case OPC_MFTR:
5979         check_insn(env, ctx, ASE_MT);
5980         if (rd == 0) {
5981             /* Treat as NOP. */
5982             return;
5983         }
5984         gen_mftr(env, ctx, rt, rd, (ctx->opcode >> 5) & 1,
5985                  ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
5986         opn = "mftr";
5987         break;
5988     case OPC_MTTR:
5989         check_insn(env, ctx, ASE_MT);
5990         gen_mttr(env, ctx, rd, rt, (ctx->opcode >> 5) & 1,
5991                  ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
5992         opn = "mttr";
5993         break;
5994     case OPC_TLBWI:
5995         opn = "tlbwi";
5996         if (!env->tlb->helper_tlbwi)
5997             goto die;
5998         gen_helper_tlbwi();
5999         break;
6000     case OPC_TLBWR:
6001         opn = "tlbwr";
6002         if (!env->tlb->helper_tlbwr)
6003             goto die;
6004         gen_helper_tlbwr();
6005         break;
6006     case OPC_TLBP:
6007         opn = "tlbp";
6008         if (!env->tlb->helper_tlbp)
6009             goto die;
6010         gen_helper_tlbp();
6011         break;
6012     case OPC_TLBR:
6013         opn = "tlbr";
6014         if (!env->tlb->helper_tlbr)
6015             goto die;
6016         gen_helper_tlbr();
6017         break;
6018     case OPC_ERET:
6019         opn = "eret";
6020         check_insn(env, ctx, ISA_MIPS2);
6021         gen_helper_eret();
6022         ctx->bstate = BS_EXCP;
6023         break;
6024     case OPC_DERET:
6025         opn = "deret";
6026         check_insn(env, ctx, ISA_MIPS32);
6027         if (!(ctx->hflags & MIPS_HFLAG_DM)) {
6028             MIPS_INVAL(opn);
6029             generate_exception(ctx, EXCP_RI);
6030         } else {
6031             gen_helper_deret();
6032             ctx->bstate = BS_EXCP;
6033         }
6034         break;
6035     case OPC_WAIT:
6036         opn = "wait";
6037         check_insn(env, ctx, ISA_MIPS3 | ISA_MIPS32);
6038         /* If we get an exception, we want to restart at next instruction */
6039         ctx->pc += 4;
6040         save_cpu_state(ctx, 1);
6041         ctx->pc -= 4;
6042         gen_helper_wait();
6043         ctx->bstate = BS_EXCP;
6044         break;
6045     default:
6046  die:
6047         MIPS_INVAL(opn);
6048         generate_exception(ctx, EXCP_RI);
6049         return;
6050     }
6051     (void)opn; /* avoid a compiler warning */
6052     MIPS_DEBUG("%s %s %d", opn, regnames[rt], rd);
6053 }
6054 #endif /* !CONFIG_USER_ONLY */
6055
6056 /* CP1 Branches (before delay slot) */
6057 static void gen_compute_branch1 (CPUMIPSState *env, DisasContext *ctx, uint32_t op,
6058                                  int32_t cc, int32_t offset)
6059 {
6060     target_ulong btarget;
6061     const char *opn = "cp1 cond branch";
6062     TCGv_i32 t0 = tcg_temp_new_i32();
6063
6064     if (cc != 0)
6065         check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
6066
6067     btarget = ctx->pc + 4 + offset;
6068
6069     switch (op) {
6070     case OPC_BC1F:
6071         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6072         tcg_gen_not_i32(t0, t0);
6073         tcg_gen_andi_i32(t0, t0, 1);
6074         tcg_gen_extu_i32_tl(bcond, t0);
6075         opn = "bc1f";
6076         goto not_likely;
6077     case OPC_BC1FL:
6078         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6079         tcg_gen_not_i32(t0, t0);
6080         tcg_gen_andi_i32(t0, t0, 1);
6081         tcg_gen_extu_i32_tl(bcond, t0);
6082         opn = "bc1fl";
6083         goto likely;
6084     case OPC_BC1T:
6085         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6086         tcg_gen_andi_i32(t0, t0, 1);
6087         tcg_gen_extu_i32_tl(bcond, t0);
6088         opn = "bc1t";
6089         goto not_likely;
6090     case OPC_BC1TL:
6091         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6092         tcg_gen_andi_i32(t0, t0, 1);
6093         tcg_gen_extu_i32_tl(bcond, t0);
6094         opn = "bc1tl";
6095     likely:
6096         ctx->hflags |= MIPS_HFLAG_BL;
6097         break;
6098     case OPC_BC1FANY2:
6099         {
6100             TCGv_i32 t1 = tcg_temp_new_i32();
6101             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6102             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
6103             tcg_gen_nand_i32(t0, t0, t1);
6104             tcg_temp_free_i32(t1);
6105             tcg_gen_andi_i32(t0, t0, 1);
6106             tcg_gen_extu_i32_tl(bcond, t0);
6107         }
6108         opn = "bc1any2f";
6109         goto not_likely;
6110     case OPC_BC1TANY2:
6111         {
6112             TCGv_i32 t1 = tcg_temp_new_i32();
6113             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6114             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
6115             tcg_gen_or_i32(t0, t0, t1);
6116             tcg_temp_free_i32(t1);
6117             tcg_gen_andi_i32(t0, t0, 1);
6118             tcg_gen_extu_i32_tl(bcond, t0);
6119         }
6120         opn = "bc1any2t";
6121         goto not_likely;
6122     case OPC_BC1FANY4:
6123         {
6124             TCGv_i32 t1 = tcg_temp_new_i32();
6125             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6126             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
6127             tcg_gen_and_i32(t0, t0, t1);
6128             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+2));
6129             tcg_gen_and_i32(t0, t0, t1);
6130             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+3));
6131             tcg_gen_nand_i32(t0, t0, t1);
6132             tcg_temp_free_i32(t1);
6133             tcg_gen_andi_i32(t0, t0, 1);
6134             tcg_gen_extu_i32_tl(bcond, t0);
6135         }
6136         opn = "bc1any4f";
6137         goto not_likely;
6138     case OPC_BC1TANY4:
6139         {
6140             TCGv_i32 t1 = tcg_temp_new_i32();
6141             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
6142             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+1));
6143             tcg_gen_or_i32(t0, t0, t1);
6144             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+2));
6145             tcg_gen_or_i32(t0, t0, t1);
6146             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc+3));
6147             tcg_gen_or_i32(t0, t0, t1);
6148             tcg_temp_free_i32(t1);
6149             tcg_gen_andi_i32(t0, t0, 1);
6150             tcg_gen_extu_i32_tl(bcond, t0);
6151         }
6152         opn = "bc1any4t";
6153     not_likely:
6154         ctx->hflags |= MIPS_HFLAG_BC;
6155         break;
6156     default:
6157         MIPS_INVAL(opn);
6158         generate_exception (ctx, EXCP_RI);
6159         goto out;
6160     }
6161     (void)opn; /* avoid a compiler warning */
6162     MIPS_DEBUG("%s: cond %02x target " TARGET_FMT_lx, opn,
6163                ctx->hflags, btarget);
6164     ctx->btarget = btarget;
6165
6166  out:
6167     tcg_temp_free_i32(t0);
6168 }
6169
6170 /* Coprocessor 1 (FPU) */
6171
6172 #define FOP(func, fmt) (((fmt) << 21) | (func))
6173
6174 enum fopcode {
6175     OPC_ADD_S = FOP(0, FMT_S),
6176     OPC_SUB_S = FOP(1, FMT_S),
6177     OPC_MUL_S = FOP(2, FMT_S),
6178     OPC_DIV_S = FOP(3, FMT_S),
6179     OPC_SQRT_S = FOP(4, FMT_S),
6180     OPC_ABS_S = FOP(5, FMT_S),
6181     OPC_MOV_S = FOP(6, FMT_S),
6182     OPC_NEG_S = FOP(7, FMT_S),
6183     OPC_ROUND_L_S = FOP(8, FMT_S),
6184     OPC_TRUNC_L_S = FOP(9, FMT_S),
6185     OPC_CEIL_L_S = FOP(10, FMT_S),
6186     OPC_FLOOR_L_S = FOP(11, FMT_S),
6187     OPC_ROUND_W_S = FOP(12, FMT_S),
6188     OPC_TRUNC_W_S = FOP(13, FMT_S),
6189     OPC_CEIL_W_S = FOP(14, FMT_S),
6190     OPC_FLOOR_W_S = FOP(15, FMT_S),
6191     OPC_MOVCF_S = FOP(17, FMT_S),
6192     OPC_MOVZ_S = FOP(18, FMT_S),
6193     OPC_MOVN_S = FOP(19, FMT_S),
6194     OPC_RECIP_S = FOP(21, FMT_S),
6195     OPC_RSQRT_S = FOP(22, FMT_S),
6196     OPC_RECIP2_S = FOP(28, FMT_S),
6197     OPC_RECIP1_S = FOP(29, FMT_S),
6198     OPC_RSQRT1_S = FOP(30, FMT_S),
6199     OPC_RSQRT2_S = FOP(31, FMT_S),
6200     OPC_CVT_D_S = FOP(33, FMT_S),
6201     OPC_CVT_W_S = FOP(36, FMT_S),
6202     OPC_CVT_L_S = FOP(37, FMT_S),
6203     OPC_CVT_PS_S = FOP(38, FMT_S),
6204     OPC_CMP_F_S = FOP (48, FMT_S),
6205     OPC_CMP_UN_S = FOP (49, FMT_S),
6206     OPC_CMP_EQ_S = FOP (50, FMT_S),
6207     OPC_CMP_UEQ_S = FOP (51, FMT_S),
6208     OPC_CMP_OLT_S = FOP (52, FMT_S),
6209     OPC_CMP_ULT_S = FOP (53, FMT_S),
6210     OPC_CMP_OLE_S = FOP (54, FMT_S),
6211     OPC_CMP_ULE_S = FOP (55, FMT_S),
6212     OPC_CMP_SF_S = FOP (56, FMT_S),
6213     OPC_CMP_NGLE_S = FOP (57, FMT_S),
6214     OPC_CMP_SEQ_S = FOP (58, FMT_S),
6215     OPC_CMP_NGL_S = FOP (59, FMT_S),
6216     OPC_CMP_LT_S = FOP (60, FMT_S),
6217     OPC_CMP_NGE_S = FOP (61, FMT_S),
6218     OPC_CMP_LE_S = FOP (62, FMT_S),
6219     OPC_CMP_NGT_S = FOP (63, FMT_S),
6220
6221     OPC_ADD_D = FOP(0, FMT_D),
6222     OPC_SUB_D = FOP(1, FMT_D),
6223     OPC_MUL_D = FOP(2, FMT_D),
6224     OPC_DIV_D = FOP(3, FMT_D),
6225     OPC_SQRT_D = FOP(4, FMT_D),
6226     OPC_ABS_D = FOP(5, FMT_D),
6227     OPC_MOV_D = FOP(6, FMT_D),
6228     OPC_NEG_D = FOP(7, FMT_D),
6229     OPC_ROUND_L_D = FOP(8, FMT_D),
6230     OPC_TRUNC_L_D = FOP(9, FMT_D),
6231     OPC_CEIL_L_D = FOP(10, FMT_D),
6232     OPC_FLOOR_L_D = FOP(11, FMT_D),
6233     OPC_ROUND_W_D = FOP(12, FMT_D),
6234     OPC_TRUNC_W_D = FOP(13, FMT_D),
6235     OPC_CEIL_W_D = FOP(14, FMT_D),
6236     OPC_FLOOR_W_D = FOP(15, FMT_D),
6237     OPC_MOVCF_D = FOP(17, FMT_D),
6238     OPC_MOVZ_D = FOP(18, FMT_D),
6239     OPC_MOVN_D = FOP(19, FMT_D),
6240     OPC_RECIP_D = FOP(21, FMT_D),
6241     OPC_RSQRT_D = FOP(22, FMT_D),
6242     OPC_RECIP2_D = FOP(28, FMT_D),
6243     OPC_RECIP1_D = FOP(29, FMT_D),
6244     OPC_RSQRT1_D = FOP(30, FMT_D),
6245     OPC_RSQRT2_D = FOP(31, FMT_D),
6246     OPC_CVT_S_D = FOP(32, FMT_D),
6247     OPC_CVT_W_D = FOP(36, FMT_D),
6248     OPC_CVT_L_D = FOP(37, FMT_D),
6249     OPC_CMP_F_D = FOP (48, FMT_D),
6250     OPC_CMP_UN_D = FOP (49, FMT_D),
6251     OPC_CMP_EQ_D = FOP (50, FMT_D),
6252     OPC_CMP_UEQ_D = FOP (51, FMT_D),
6253     OPC_CMP_OLT_D = FOP (52, FMT_D),
6254     OPC_CMP_ULT_D = FOP (53, FMT_D),
6255     OPC_CMP_OLE_D = FOP (54, FMT_D),
6256     OPC_CMP_ULE_D = FOP (55, FMT_D),
6257     OPC_CMP_SF_D = FOP (56, FMT_D),
6258     OPC_CMP_NGLE_D = FOP (57, FMT_D),
6259     OPC_CMP_SEQ_D = FOP (58, FMT_D),
6260     OPC_CMP_NGL_D = FOP (59, FMT_D),
6261     OPC_CMP_LT_D = FOP (60, FMT_D),
6262     OPC_CMP_NGE_D = FOP (61, FMT_D),
6263     OPC_CMP_LE_D = FOP (62, FMT_D),
6264     OPC_CMP_NGT_D = FOP (63, FMT_D),
6265
6266     OPC_CVT_S_W = FOP(32, FMT_W),
6267     OPC_CVT_D_W = FOP(33, FMT_W),
6268     OPC_CVT_S_L = FOP(32, FMT_L),
6269     OPC_CVT_D_L = FOP(33, FMT_L),
6270     OPC_CVT_PS_PW = FOP(38, FMT_W),
6271
6272     OPC_ADD_PS = FOP(0, FMT_PS),
6273     OPC_SUB_PS = FOP(1, FMT_PS),
6274     OPC_MUL_PS = FOP(2, FMT_PS),
6275     OPC_DIV_PS = FOP(3, FMT_PS),
6276     OPC_ABS_PS = FOP(5, FMT_PS),
6277     OPC_MOV_PS = FOP(6, FMT_PS),
6278     OPC_NEG_PS = FOP(7, FMT_PS),
6279     OPC_MOVCF_PS = FOP(17, FMT_PS),
6280     OPC_MOVZ_PS = FOP(18, FMT_PS),
6281     OPC_MOVN_PS = FOP(19, FMT_PS),
6282     OPC_ADDR_PS = FOP(24, FMT_PS),
6283     OPC_MULR_PS = FOP(26, FMT_PS),
6284     OPC_RECIP2_PS = FOP(28, FMT_PS),
6285     OPC_RECIP1_PS = FOP(29, FMT_PS),
6286     OPC_RSQRT1_PS = FOP(30, FMT_PS),
6287     OPC_RSQRT2_PS = FOP(31, FMT_PS),
6288
6289     OPC_CVT_S_PU = FOP(32, FMT_PS),
6290     OPC_CVT_PW_PS = FOP(36, FMT_PS),
6291     OPC_CVT_S_PL = FOP(40, FMT_PS),
6292     OPC_PLL_PS = FOP(44, FMT_PS),
6293     OPC_PLU_PS = FOP(45, FMT_PS),
6294     OPC_PUL_PS = FOP(46, FMT_PS),
6295     OPC_PUU_PS = FOP(47, FMT_PS),
6296     OPC_CMP_F_PS = FOP (48, FMT_PS),
6297     OPC_CMP_UN_PS = FOP (49, FMT_PS),
6298     OPC_CMP_EQ_PS = FOP (50, FMT_PS),
6299     OPC_CMP_UEQ_PS = FOP (51, FMT_PS),
6300     OPC_CMP_OLT_PS = FOP (52, FMT_PS),
6301     OPC_CMP_ULT_PS = FOP (53, FMT_PS),
6302     OPC_CMP_OLE_PS = FOP (54, FMT_PS),
6303     OPC_CMP_ULE_PS = FOP (55, FMT_PS),
6304     OPC_CMP_SF_PS = FOP (56, FMT_PS),
6305     OPC_CMP_NGLE_PS = FOP (57, FMT_PS),
6306     OPC_CMP_SEQ_PS = FOP (58, FMT_PS),
6307     OPC_CMP_NGL_PS = FOP (59, FMT_PS),
6308     OPC_CMP_LT_PS = FOP (60, FMT_PS),
6309     OPC_CMP_NGE_PS = FOP (61, FMT_PS),
6310     OPC_CMP_LE_PS = FOP (62, FMT_PS),
6311     OPC_CMP_NGT_PS = FOP (63, FMT_PS),
6312 };
6313
6314 static void gen_cp1 (DisasContext *ctx, uint32_t opc, int rt, int fs)
6315 {
6316     const char *opn = "cp1 move";
6317     TCGv t0 = tcg_temp_new();
6318
6319     switch (opc) {
6320     case OPC_MFC1:
6321         {
6322             TCGv_i32 fp0 = tcg_temp_new_i32();
6323
6324             gen_load_fpr32(fp0, fs);
6325             tcg_gen_ext_i32_tl(t0, fp0);
6326             tcg_temp_free_i32(fp0);
6327         }
6328         gen_store_gpr(t0, rt);
6329         opn = "mfc1";
6330         break;
6331     case OPC_MTC1:
6332         gen_load_gpr(t0, rt);
6333         {
6334             TCGv_i32 fp0 = tcg_temp_new_i32();
6335
6336             tcg_gen_trunc_tl_i32(fp0, t0);
6337             gen_store_fpr32(fp0, fs);
6338             tcg_temp_free_i32(fp0);
6339         }
6340         opn = "mtc1";
6341         break;
6342     case OPC_CFC1:
6343         gen_helper_1i(cfc1, t0, fs);
6344         gen_store_gpr(t0, rt);
6345         opn = "cfc1";
6346         break;
6347     case OPC_CTC1:
6348         gen_load_gpr(t0, rt);
6349         gen_helper_1i(ctc1, t0, fs);
6350         opn = "ctc1";
6351         break;
6352 #if defined(TARGET_MIPS64)
6353     case OPC_DMFC1:
6354         gen_load_fpr64(ctx, t0, fs);
6355         gen_store_gpr(t0, rt);
6356         opn = "dmfc1";
6357         break;
6358     case OPC_DMTC1:
6359         gen_load_gpr(t0, rt);
6360         gen_store_fpr64(ctx, t0, fs);
6361         opn = "dmtc1";
6362         break;
6363 #endif
6364     case OPC_MFHC1:
6365         {
6366             TCGv_i32 fp0 = tcg_temp_new_i32();
6367
6368             gen_load_fpr32h(fp0, fs);
6369             tcg_gen_ext_i32_tl(t0, fp0);
6370             tcg_temp_free_i32(fp0);
6371         }
6372         gen_store_gpr(t0, rt);
6373         opn = "mfhc1";
6374         break;
6375     case OPC_MTHC1:
6376         gen_load_gpr(t0, rt);
6377         {
6378             TCGv_i32 fp0 = tcg_temp_new_i32();
6379
6380             tcg_gen_trunc_tl_i32(fp0, t0);
6381             gen_store_fpr32h(fp0, fs);
6382             tcg_temp_free_i32(fp0);
6383         }
6384         opn = "mthc1";
6385         break;
6386     default:
6387         MIPS_INVAL(opn);
6388         generate_exception (ctx, EXCP_RI);
6389         goto out;
6390     }
6391     (void)opn; /* avoid a compiler warning */
6392     MIPS_DEBUG("%s %s %s", opn, regnames[rt], fregnames[fs]);
6393
6394  out:
6395     tcg_temp_free(t0);
6396 }
6397
6398 static void gen_movci (DisasContext *ctx, int rd, int rs, int cc, int tf)
6399 {
6400     int l1;
6401     TCGCond cond;
6402     TCGv_i32 t0;
6403
6404     if (rd == 0) {
6405         /* Treat as NOP. */
6406         return;
6407     }
6408
6409     if (tf)
6410         cond = TCG_COND_EQ;
6411     else
6412         cond = TCG_COND_NE;
6413
6414     l1 = gen_new_label();
6415     t0 = tcg_temp_new_i32();
6416     tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
6417     tcg_gen_brcondi_i32(cond, t0, 0, l1);
6418     tcg_temp_free_i32(t0);
6419     if (rs == 0) {
6420         tcg_gen_movi_tl(cpu_gpr[rd], 0);
6421     } else {
6422         tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
6423     }
6424     gen_set_label(l1);
6425 }
6426
6427 static inline void gen_movcf_s (int fs, int fd, int cc, int tf)
6428 {
6429     int cond;
6430     TCGv_i32 t0 = tcg_temp_new_i32();
6431     int l1 = gen_new_label();
6432
6433     if (tf)
6434         cond = TCG_COND_EQ;
6435     else
6436         cond = TCG_COND_NE;
6437
6438     tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
6439     tcg_gen_brcondi_i32(cond, t0, 0, l1);
6440     gen_load_fpr32(t0, fs);
6441     gen_store_fpr32(t0, fd);
6442     gen_set_label(l1);
6443     tcg_temp_free_i32(t0);
6444 }
6445
6446 static inline void gen_movcf_d (DisasContext *ctx, int fs, int fd, int cc, int tf)
6447 {
6448     int cond;
6449     TCGv_i32 t0 = tcg_temp_new_i32();
6450     TCGv_i64 fp0;
6451     int l1 = gen_new_label();
6452
6453     if (tf)
6454         cond = TCG_COND_EQ;
6455     else
6456         cond = TCG_COND_NE;
6457
6458     tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
6459     tcg_gen_brcondi_i32(cond, t0, 0, l1);
6460     tcg_temp_free_i32(t0);
6461     fp0 = tcg_temp_new_i64();
6462     gen_load_fpr64(ctx, fp0, fs);
6463     gen_store_fpr64(ctx, fp0, fd);
6464     tcg_temp_free_i64(fp0);
6465     gen_set_label(l1);
6466 }
6467
6468 static inline void gen_movcf_ps (int fs, int fd, int cc, int tf)
6469 {
6470     int cond;
6471     TCGv_i32 t0 = tcg_temp_new_i32();
6472     int l1 = gen_new_label();
6473     int l2 = gen_new_label();
6474
6475     if (tf)
6476         cond = TCG_COND_EQ;
6477     else
6478         cond = TCG_COND_NE;
6479
6480     tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
6481     tcg_gen_brcondi_i32(cond, t0, 0, l1);
6482     gen_load_fpr32(t0, fs);
6483     gen_store_fpr32(t0, fd);
6484     gen_set_label(l1);
6485
6486     tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc+1));
6487     tcg_gen_brcondi_i32(cond, t0, 0, l2);
6488     gen_load_fpr32h(t0, fs);
6489     gen_store_fpr32h(t0, fd);
6490     tcg_temp_free_i32(t0);
6491     gen_set_label(l2);
6492 }
6493
6494
6495 static void gen_farith (DisasContext *ctx, enum fopcode op1,
6496                         int ft, int fs, int fd, int cc)
6497 {
6498     const char *opn = "farith";
6499     const char *condnames[] = {
6500             "c.f",
6501             "c.un",
6502             "c.eq",
6503             "c.ueq",
6504             "c.olt",
6505             "c.ult",
6506             "c.ole",
6507             "c.ule",
6508             "c.sf",
6509             "c.ngle",
6510             "c.seq",
6511             "c.ngl",
6512             "c.lt",
6513             "c.nge",
6514             "c.le",
6515             "c.ngt",
6516     };
6517     const char *condnames_abs[] = {
6518             "cabs.f",
6519             "cabs.un",
6520             "cabs.eq",
6521             "cabs.ueq",
6522             "cabs.olt",
6523             "cabs.ult",
6524             "cabs.ole",
6525             "cabs.ule",
6526             "cabs.sf",
6527             "cabs.ngle",
6528             "cabs.seq",
6529             "cabs.ngl",
6530             "cabs.lt",
6531             "cabs.nge",
6532             "cabs.le",
6533             "cabs.ngt",
6534     };
6535     enum { BINOP, CMPOP, OTHEROP } optype = OTHEROP;
6536     uint32_t func = ctx->opcode & 0x3f;
6537
6538     switch (op1) {
6539     case OPC_ADD_S:
6540         {
6541             TCGv_i32 fp0 = tcg_temp_new_i32();
6542             TCGv_i32 fp1 = tcg_temp_new_i32();
6543
6544             gen_load_fpr32(fp0, fs);
6545             gen_load_fpr32(fp1, ft);
6546             gen_helper_float_add_s(fp0, fp0, fp1);
6547             tcg_temp_free_i32(fp1);
6548             gen_store_fpr32(fp0, fd);
6549             tcg_temp_free_i32(fp0);
6550         }
6551         opn = "add.s";
6552         optype = BINOP;
6553         break;
6554     case OPC_SUB_S:
6555         {
6556             TCGv_i32 fp0 = tcg_temp_new_i32();
6557             TCGv_i32 fp1 = tcg_temp_new_i32();
6558
6559             gen_load_fpr32(fp0, fs);
6560             gen_load_fpr32(fp1, ft);
6561             gen_helper_float_sub_s(fp0, fp0, fp1);
6562             tcg_temp_free_i32(fp1);
6563             gen_store_fpr32(fp0, fd);
6564             tcg_temp_free_i32(fp0);
6565         }
6566         opn = "sub.s";
6567         optype = BINOP;
6568         break;
6569     case OPC_MUL_S:
6570         {
6571             TCGv_i32 fp0 = tcg_temp_new_i32();
6572             TCGv_i32 fp1 = tcg_temp_new_i32();
6573
6574             gen_load_fpr32(fp0, fs);
6575             gen_load_fpr32(fp1, ft);
6576             gen_helper_float_mul_s(fp0, fp0, fp1);
6577             tcg_temp_free_i32(fp1);
6578             gen_store_fpr32(fp0, fd);
6579             tcg_temp_free_i32(fp0);
6580         }
6581         opn = "mul.s";
6582         optype = BINOP;
6583         break;
6584     case OPC_DIV_S:
6585         {
6586             TCGv_i32 fp0 = tcg_temp_new_i32();
6587             TCGv_i32 fp1 = tcg_temp_new_i32();
6588
6589             gen_load_fpr32(fp0, fs);
6590             gen_load_fpr32(fp1, ft);
6591             gen_helper_float_div_s(fp0, fp0, fp1);
6592             tcg_temp_free_i32(fp1);
6593             gen_store_fpr32(fp0, fd);
6594             tcg_temp_free_i32(fp0);
6595         }
6596         opn = "div.s";
6597         optype = BINOP;
6598         break;
6599     case OPC_SQRT_S:
6600         {
6601             TCGv_i32 fp0 = tcg_temp_new_i32();
6602
6603             gen_load_fpr32(fp0, fs);
6604             gen_helper_float_sqrt_s(fp0, fp0);
6605             gen_store_fpr32(fp0, fd);
6606             tcg_temp_free_i32(fp0);
6607         }
6608         opn = "sqrt.s";
6609         break;
6610     case OPC_ABS_S:
6611         {
6612             TCGv_i32 fp0 = tcg_temp_new_i32();
6613
6614             gen_load_fpr32(fp0, fs);
6615             gen_helper_float_abs_s(fp0, fp0);
6616             gen_store_fpr32(fp0, fd);
6617             tcg_temp_free_i32(fp0);
6618         }
6619         opn = "abs.s";
6620         break;
6621     case OPC_MOV_S:
6622         {
6623             TCGv_i32 fp0 = tcg_temp_new_i32();
6624
6625             gen_load_fpr32(fp0, fs);
6626             gen_store_fpr32(fp0, fd);
6627             tcg_temp_free_i32(fp0);
6628         }
6629         opn = "mov.s";
6630         break;
6631     case OPC_NEG_S:
6632         {
6633             TCGv_i32 fp0 = tcg_temp_new_i32();
6634
6635             gen_load_fpr32(fp0, fs);
6636             gen_helper_float_chs_s(fp0, fp0);
6637             gen_store_fpr32(fp0, fd);
6638             tcg_temp_free_i32(fp0);
6639         }
6640         opn = "neg.s";
6641         break;
6642     case OPC_ROUND_L_S:
6643         check_cp1_64bitmode(ctx);
6644         {
6645             TCGv_i32 fp32 = tcg_temp_new_i32();
6646             TCGv_i64 fp64 = tcg_temp_new_i64();
6647
6648             gen_load_fpr32(fp32, fs);
6649             gen_helper_float_roundl_s(fp64, fp32);
6650             tcg_temp_free_i32(fp32);
6651             gen_store_fpr64(ctx, fp64, fd);
6652             tcg_temp_free_i64(fp64);
6653         }
6654         opn = "round.l.s";
6655         break;
6656     case OPC_TRUNC_L_S:
6657         check_cp1_64bitmode(ctx);
6658         {
6659             TCGv_i32 fp32 = tcg_temp_new_i32();
6660             TCGv_i64 fp64 = tcg_temp_new_i64();
6661
6662             gen_load_fpr32(fp32, fs);
6663             gen_helper_float_truncl_s(fp64, fp32);
6664             tcg_temp_free_i32(fp32);
6665             gen_store_fpr64(ctx, fp64, fd);
6666             tcg_temp_free_i64(fp64);
6667         }
6668         opn = "trunc.l.s";
6669         break;
6670     case OPC_CEIL_L_S:
6671         check_cp1_64bitmode(ctx);
6672         {
6673             TCGv_i32 fp32 = tcg_temp_new_i32();
6674             TCGv_i64 fp64 = tcg_temp_new_i64();
6675
6676             gen_load_fpr32(fp32, fs);
6677             gen_helper_float_ceill_s(fp64, fp32);
6678             tcg_temp_free_i32(fp32);
6679             gen_store_fpr64(ctx, fp64, fd);
6680             tcg_temp_free_i64(fp64);
6681         }
6682         opn = "ceil.l.s";
6683         break;
6684     case OPC_FLOOR_L_S:
6685         check_cp1_64bitmode(ctx);
6686         {
6687             TCGv_i32 fp32 = tcg_temp_new_i32();
6688             TCGv_i64 fp64 = tcg_temp_new_i64();
6689
6690             gen_load_fpr32(fp32, fs);
6691             gen_helper_float_floorl_s(fp64, fp32);
6692             tcg_temp_free_i32(fp32);
6693             gen_store_fpr64(ctx, fp64, fd);
6694             tcg_temp_free_i64(fp64);
6695         }
6696         opn = "floor.l.s";
6697         break;
6698     case OPC_ROUND_W_S:
6699         {
6700             TCGv_i32 fp0 = tcg_temp_new_i32();
6701
6702             gen_load_fpr32(fp0, fs);
6703             gen_helper_float_roundw_s(fp0, fp0);
6704             gen_store_fpr32(fp0, fd);
6705             tcg_temp_free_i32(fp0);
6706         }
6707         opn = "round.w.s";
6708         break;
6709     case OPC_TRUNC_W_S:
6710         {
6711             TCGv_i32 fp0 = tcg_temp_new_i32();
6712
6713             gen_load_fpr32(fp0, fs);
6714             gen_helper_float_truncw_s(fp0, fp0);
6715             gen_store_fpr32(fp0, fd);
6716             tcg_temp_free_i32(fp0);
6717         }
6718         opn = "trunc.w.s";
6719         break;
6720     case OPC_CEIL_W_S:
6721         {
6722             TCGv_i32 fp0 = tcg_temp_new_i32();
6723
6724             gen_load_fpr32(fp0, fs);
6725             gen_helper_float_ceilw_s(fp0, fp0);
6726             gen_store_fpr32(fp0, fd);
6727             tcg_temp_free_i32(fp0);
6728         }
6729         opn = "ceil.w.s";
6730         break;
6731     case OPC_FLOOR_W_S:
6732         {
6733             TCGv_i32 fp0 = tcg_temp_new_i32();
6734
6735             gen_load_fpr32(fp0, fs);
6736             gen_helper_float_floorw_s(fp0, fp0);
6737             gen_store_fpr32(fp0, fd);
6738             tcg_temp_free_i32(fp0);
6739         }
6740         opn = "floor.w.s";
6741         break;
6742     case OPC_MOVCF_S:
6743         gen_movcf_s(fs, fd, (ft >> 2) & 0x7, ft & 0x1);
6744         opn = "movcf.s";
6745         break;
6746     case OPC_MOVZ_S:
6747         {
6748             int l1 = gen_new_label();
6749             TCGv_i32 fp0;
6750
6751             if (ft != 0) {
6752                 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
6753             }
6754             fp0 = tcg_temp_new_i32();
6755             gen_load_fpr32(fp0, fs);
6756             gen_store_fpr32(fp0, fd);
6757             tcg_temp_free_i32(fp0);
6758             gen_set_label(l1);
6759         }
6760         opn = "movz.s";
6761         break;
6762     case OPC_MOVN_S:
6763         {
6764             int l1 = gen_new_label();
6765             TCGv_i32 fp0;
6766
6767             if (ft != 0) {
6768                 tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
6769                 fp0 = tcg_temp_new_i32();
6770                 gen_load_fpr32(fp0, fs);
6771                 gen_store_fpr32(fp0, fd);
6772                 tcg_temp_free_i32(fp0);
6773                 gen_set_label(l1);
6774             }
6775         }
6776         opn = "movn.s";
6777         break;
6778     case OPC_RECIP_S:
6779         check_cop1x(ctx);
6780         {
6781             TCGv_i32 fp0 = tcg_temp_new_i32();
6782
6783             gen_load_fpr32(fp0, fs);
6784             gen_helper_float_recip_s(fp0, fp0);
6785             gen_store_fpr32(fp0, fd);
6786             tcg_temp_free_i32(fp0);
6787         }
6788         opn = "recip.s";
6789         break;
6790     case OPC_RSQRT_S:
6791         check_cop1x(ctx);
6792         {
6793             TCGv_i32 fp0 = tcg_temp_new_i32();
6794
6795             gen_load_fpr32(fp0, fs);
6796             gen_helper_float_rsqrt_s(fp0, fp0);
6797             gen_store_fpr32(fp0, fd);
6798             tcg_temp_free_i32(fp0);
6799         }
6800         opn = "rsqrt.s";
6801         break;
6802     case OPC_RECIP2_S:
6803         check_cp1_64bitmode(ctx);
6804         {
6805             TCGv_i32 fp0 = tcg_temp_new_i32();
6806             TCGv_i32 fp1 = tcg_temp_new_i32();
6807
6808             gen_load_fpr32(fp0, fs);
6809             gen_load_fpr32(fp1, ft);
6810             gen_helper_float_recip2_s(fp0, fp0, fp1);
6811             tcg_temp_free_i32(fp1);
6812             gen_store_fpr32(fp0, fd);
6813             tcg_temp_free_i32(fp0);
6814         }
6815         opn = "recip2.s";
6816         break;
6817     case OPC_RECIP1_S:
6818         check_cp1_64bitmode(ctx);
6819         {
6820             TCGv_i32 fp0 = tcg_temp_new_i32();
6821
6822             gen_load_fpr32(fp0, fs);
6823             gen_helper_float_recip1_s(fp0, fp0);
6824             gen_store_fpr32(fp0, fd);
6825             tcg_temp_free_i32(fp0);
6826         }
6827         opn = "recip1.s";
6828         break;
6829     case OPC_RSQRT1_S:
6830         check_cp1_64bitmode(ctx);
6831         {
6832             TCGv_i32 fp0 = tcg_temp_new_i32();
6833
6834             gen_load_fpr32(fp0, fs);
6835             gen_helper_float_rsqrt1_s(fp0, fp0);
6836             gen_store_fpr32(fp0, fd);
6837             tcg_temp_free_i32(fp0);
6838         }
6839         opn = "rsqrt1.s";
6840         break;
6841     case OPC_RSQRT2_S:
6842         check_cp1_64bitmode(ctx);
6843         {
6844             TCGv_i32 fp0 = tcg_temp_new_i32();
6845             TCGv_i32 fp1 = tcg_temp_new_i32();
6846
6847             gen_load_fpr32(fp0, fs);
6848             gen_load_fpr32(fp1, ft);
6849             gen_helper_float_rsqrt2_s(fp0, fp0, fp1);
6850             tcg_temp_free_i32(fp1);
6851             gen_store_fpr32(fp0, fd);
6852             tcg_temp_free_i32(fp0);
6853         }
6854         opn = "rsqrt2.s";
6855         break;
6856     case OPC_CVT_D_S:
6857         check_cp1_registers(ctx, fd);
6858         {
6859             TCGv_i32 fp32 = tcg_temp_new_i32();
6860             TCGv_i64 fp64 = tcg_temp_new_i64();
6861
6862             gen_load_fpr32(fp32, fs);
6863             gen_helper_float_cvtd_s(fp64, fp32);
6864             tcg_temp_free_i32(fp32);
6865             gen_store_fpr64(ctx, fp64, fd);
6866             tcg_temp_free_i64(fp64);
6867         }
6868         opn = "cvt.d.s";
6869         break;
6870     case OPC_CVT_W_S:
6871         {
6872             TCGv_i32 fp0 = tcg_temp_new_i32();
6873
6874             gen_load_fpr32(fp0, fs);
6875             gen_helper_float_cvtw_s(fp0, fp0);
6876             gen_store_fpr32(fp0, fd);
6877             tcg_temp_free_i32(fp0);
6878         }
6879         opn = "cvt.w.s";
6880         break;
6881     case OPC_CVT_L_S:
6882         check_cp1_64bitmode(ctx);
6883         {
6884             TCGv_i32 fp32 = tcg_temp_new_i32();
6885             TCGv_i64 fp64 = tcg_temp_new_i64();
6886
6887             gen_load_fpr32(fp32, fs);
6888             gen_helper_float_cvtl_s(fp64, fp32);
6889             tcg_temp_free_i32(fp32);
6890             gen_store_fpr64(ctx, fp64, fd);
6891             tcg_temp_free_i64(fp64);
6892         }
6893         opn = "cvt.l.s";
6894         break;
6895     case OPC_CVT_PS_S:
6896         check_cp1_64bitmode(ctx);
6897         {
6898             TCGv_i64 fp64 = tcg_temp_new_i64();
6899             TCGv_i32 fp32_0 = tcg_temp_new_i32();
6900             TCGv_i32 fp32_1 = tcg_temp_new_i32();
6901
6902             gen_load_fpr32(fp32_0, fs);
6903             gen_load_fpr32(fp32_1, ft);
6904             tcg_gen_concat_i32_i64(fp64, fp32_1, fp32_0);
6905             tcg_temp_free_i32(fp32_1);
6906             tcg_temp_free_i32(fp32_0);
6907             gen_store_fpr64(ctx, fp64, fd);
6908             tcg_temp_free_i64(fp64);
6909         }
6910         opn = "cvt.ps.s";
6911         break;
6912     case OPC_CMP_F_S:
6913     case OPC_CMP_UN_S:
6914     case OPC_CMP_EQ_S:
6915     case OPC_CMP_UEQ_S:
6916     case OPC_CMP_OLT_S:
6917     case OPC_CMP_ULT_S:
6918     case OPC_CMP_OLE_S:
6919     case OPC_CMP_ULE_S:
6920     case OPC_CMP_SF_S:
6921     case OPC_CMP_NGLE_S:
6922     case OPC_CMP_SEQ_S:
6923     case OPC_CMP_NGL_S:
6924     case OPC_CMP_LT_S:
6925     case OPC_CMP_NGE_S:
6926     case OPC_CMP_LE_S:
6927     case OPC_CMP_NGT_S:
6928         if (ctx->opcode & (1 << 6)) {
6929             gen_cmpabs_s(ctx, func-48, ft, fs, cc);
6930             opn = condnames_abs[func-48];
6931         } else {
6932             gen_cmp_s(ctx, func-48, ft, fs, cc);
6933             opn = condnames[func-48];
6934         }
6935         break;
6936     case OPC_ADD_D:
6937         check_cp1_registers(ctx, fs | ft | fd);
6938         {
6939             TCGv_i64 fp0 = tcg_temp_new_i64();
6940             TCGv_i64 fp1 = tcg_temp_new_i64();
6941
6942             gen_load_fpr64(ctx, fp0, fs);
6943             gen_load_fpr64(ctx, fp1, ft);
6944             gen_helper_float_add_d(fp0, fp0, fp1);
6945             tcg_temp_free_i64(fp1);
6946             gen_store_fpr64(ctx, fp0, fd);
6947             tcg_temp_free_i64(fp0);
6948         }
6949         opn = "add.d";
6950         optype = BINOP;
6951         break;
6952     case OPC_SUB_D:
6953         check_cp1_registers(ctx, fs | ft | fd);
6954         {
6955             TCGv_i64 fp0 = tcg_temp_new_i64();
6956             TCGv_i64 fp1 = tcg_temp_new_i64();
6957
6958             gen_load_fpr64(ctx, fp0, fs);
6959             gen_load_fpr64(ctx, fp1, ft);
6960             gen_helper_float_sub_d(fp0, fp0, fp1);
6961             tcg_temp_free_i64(fp1);
6962             gen_store_fpr64(ctx, fp0, fd);
6963             tcg_temp_free_i64(fp0);
6964         }
6965         opn = "sub.d";
6966         optype = BINOP;
6967         break;
6968     case OPC_MUL_D:
6969         check_cp1_registers(ctx, fs | ft | fd);
6970         {
6971             TCGv_i64 fp0 = tcg_temp_new_i64();
6972             TCGv_i64 fp1 = tcg_temp_new_i64();
6973
6974             gen_load_fpr64(ctx, fp0, fs);
6975             gen_load_fpr64(ctx, fp1, ft);
6976             gen_helper_float_mul_d(fp0, fp0, fp1);
6977             tcg_temp_free_i64(fp1);
6978             gen_store_fpr64(ctx, fp0, fd);
6979             tcg_temp_free_i64(fp0);
6980         }
6981         opn = "mul.d";
6982         optype = BINOP;
6983         break;
6984     case OPC_DIV_D:
6985         check_cp1_registers(ctx, fs | ft | fd);
6986         {
6987             TCGv_i64 fp0 = tcg_temp_new_i64();
6988             TCGv_i64 fp1 = tcg_temp_new_i64();
6989
6990             gen_load_fpr64(ctx, fp0, fs);
6991             gen_load_fpr64(ctx, fp1, ft);
6992             gen_helper_float_div_d(fp0, fp0, fp1);
6993             tcg_temp_free_i64(fp1);
6994             gen_store_fpr64(ctx, fp0, fd);
6995             tcg_temp_free_i64(fp0);
6996         }
6997         opn = "div.d";
6998         optype = BINOP;
6999         break;
7000     case OPC_SQRT_D:
7001         check_cp1_registers(ctx, fs | fd);
7002         {
7003             TCGv_i64 fp0 = tcg_temp_new_i64();
7004
7005             gen_load_fpr64(ctx, fp0, fs);
7006             gen_helper_float_sqrt_d(fp0, fp0);
7007             gen_store_fpr64(ctx, fp0, fd);
7008             tcg_temp_free_i64(fp0);
7009         }
7010         opn = "sqrt.d";
7011         break;
7012     case OPC_ABS_D:
7013         check_cp1_registers(ctx, fs | fd);
7014         {
7015             TCGv_i64 fp0 = tcg_temp_new_i64();
7016
7017             gen_load_fpr64(ctx, fp0, fs);
7018             gen_helper_float_abs_d(fp0, fp0);
7019             gen_store_fpr64(ctx, fp0, fd);
7020             tcg_temp_free_i64(fp0);
7021         }
7022         opn = "abs.d";
7023         break;
7024     case OPC_MOV_D:
7025         check_cp1_registers(ctx, fs | fd);
7026         {
7027             TCGv_i64 fp0 = tcg_temp_new_i64();
7028
7029             gen_load_fpr64(ctx, fp0, fs);
7030             gen_store_fpr64(ctx, fp0, fd);
7031             tcg_temp_free_i64(fp0);
7032         }
7033         opn = "mov.d";
7034         break;
7035     case OPC_NEG_D:
7036         check_cp1_registers(ctx, fs | fd);
7037         {
7038             TCGv_i64 fp0 = tcg_temp_new_i64();
7039
7040             gen_load_fpr64(ctx, fp0, fs);
7041             gen_helper_float_chs_d(fp0, fp0);
7042             gen_store_fpr64(ctx, fp0, fd);
7043             tcg_temp_free_i64(fp0);
7044         }
7045         opn = "neg.d";
7046         break;
7047     case OPC_ROUND_L_D:
7048         check_cp1_64bitmode(ctx);
7049         {
7050             TCGv_i64 fp0 = tcg_temp_new_i64();
7051
7052             gen_load_fpr64(ctx, fp0, fs);
7053             gen_helper_float_roundl_d(fp0, fp0);
7054             gen_store_fpr64(ctx, fp0, fd);
7055             tcg_temp_free_i64(fp0);
7056         }
7057         opn = "round.l.d";
7058         break;
7059     case OPC_TRUNC_L_D:
7060         check_cp1_64bitmode(ctx);
7061         {
7062             TCGv_i64 fp0 = tcg_temp_new_i64();
7063
7064             gen_load_fpr64(ctx, fp0, fs);
7065             gen_helper_float_truncl_d(fp0, fp0);
7066             gen_store_fpr64(ctx, fp0, fd);
7067             tcg_temp_free_i64(fp0);
7068         }
7069         opn = "trunc.l.d";
7070         break;
7071     case OPC_CEIL_L_D:
7072         check_cp1_64bitmode(ctx);
7073         {
7074             TCGv_i64 fp0 = tcg_temp_new_i64();
7075
7076             gen_load_fpr64(ctx, fp0, fs);
7077             gen_helper_float_ceill_d(fp0, fp0);
7078             gen_store_fpr64(ctx, fp0, fd);
7079             tcg_temp_free_i64(fp0);
7080         }
7081         opn = "ceil.l.d";
7082         break;
7083     case OPC_FLOOR_L_D:
7084         check_cp1_64bitmode(ctx);
7085         {
7086             TCGv_i64 fp0 = tcg_temp_new_i64();
7087
7088             gen_load_fpr64(ctx, fp0, fs);
7089             gen_helper_float_floorl_d(fp0, fp0);
7090             gen_store_fpr64(ctx, fp0, fd);
7091             tcg_temp_free_i64(fp0);
7092         }
7093         opn = "floor.l.d";
7094         break;
7095     case OPC_ROUND_W_D:
7096         check_cp1_registers(ctx, fs);
7097         {
7098             TCGv_i32 fp32 = tcg_temp_new_i32();
7099             TCGv_i64 fp64 = tcg_temp_new_i64();
7100
7101             gen_load_fpr64(ctx, fp64, fs);
7102             gen_helper_float_roundw_d(fp32, fp64);
7103             tcg_temp_free_i64(fp64);
7104             gen_store_fpr32(fp32, fd);
7105             tcg_temp_free_i32(fp32);
7106         }
7107         opn = "round.w.d";
7108         break;
7109     case OPC_TRUNC_W_D:
7110         check_cp1_registers(ctx, fs);
7111         {
7112             TCGv_i32 fp32 = tcg_temp_new_i32();
7113             TCGv_i64 fp64 = tcg_temp_new_i64();
7114
7115             gen_load_fpr64(ctx, fp64, fs);
7116             gen_helper_float_truncw_d(fp32, fp64);
7117             tcg_temp_free_i64(fp64);
7118             gen_store_fpr32(fp32, fd);
7119             tcg_temp_free_i32(fp32);
7120         }
7121         opn = "trunc.w.d";
7122         break;
7123     case OPC_CEIL_W_D:
7124         check_cp1_registers(ctx, fs);
7125         {
7126             TCGv_i32 fp32 = tcg_temp_new_i32();
7127             TCGv_i64 fp64 = tcg_temp_new_i64();
7128
7129             gen_load_fpr64(ctx, fp64, fs);
7130             gen_helper_float_ceilw_d(fp32, fp64);
7131             tcg_temp_free_i64(fp64);
7132             gen_store_fpr32(fp32, fd);
7133             tcg_temp_free_i32(fp32);
7134         }
7135         opn = "ceil.w.d";
7136         break;
7137     case OPC_FLOOR_W_D:
7138         check_cp1_registers(ctx, fs);
7139         {
7140             TCGv_i32 fp32 = tcg_temp_new_i32();
7141             TCGv_i64 fp64 = tcg_temp_new_i64();
7142
7143             gen_load_fpr64(ctx, fp64, fs);
7144             gen_helper_float_floorw_d(fp32, fp64);
7145             tcg_temp_free_i64(fp64);
7146             gen_store_fpr32(fp32, fd);
7147             tcg_temp_free_i32(fp32);
7148         }
7149         opn = "floor.w.d";
7150         break;
7151     case OPC_MOVCF_D:
7152         gen_movcf_d(ctx, fs, fd, (ft >> 2) & 0x7, ft & 0x1);
7153         opn = "movcf.d";
7154         break;
7155     case OPC_MOVZ_D:
7156         {
7157             int l1 = gen_new_label();
7158             TCGv_i64 fp0;
7159
7160             if (ft != 0) {
7161                 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
7162             }
7163             fp0 = tcg_temp_new_i64();
7164             gen_load_fpr64(ctx, fp0, fs);
7165             gen_store_fpr64(ctx, fp0, fd);
7166             tcg_temp_free_i64(fp0);
7167             gen_set_label(l1);
7168         }
7169         opn = "movz.d";
7170         break;
7171     case OPC_MOVN_D:
7172         {
7173             int l1 = gen_new_label();
7174             TCGv_i64 fp0;
7175
7176             if (ft != 0) {
7177                 tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
7178                 fp0 = tcg_temp_new_i64();
7179                 gen_load_fpr64(ctx, fp0, fs);
7180                 gen_store_fpr64(ctx, fp0, fd);
7181                 tcg_temp_free_i64(fp0);
7182                 gen_set_label(l1);
7183             }
7184         }
7185         opn = "movn.d";
7186         break;
7187     case OPC_RECIP_D:
7188         check_cp1_64bitmode(ctx);
7189         {
7190             TCGv_i64 fp0 = tcg_temp_new_i64();
7191
7192             gen_load_fpr64(ctx, fp0, fs);
7193             gen_helper_float_recip_d(fp0, fp0);
7194             gen_store_fpr64(ctx, fp0, fd);
7195             tcg_temp_free_i64(fp0);
7196         }
7197         opn = "recip.d";
7198         break;
7199     case OPC_RSQRT_D:
7200         check_cp1_64bitmode(ctx);
7201         {
7202             TCGv_i64 fp0 = tcg_temp_new_i64();
7203
7204             gen_load_fpr64(ctx, fp0, fs);
7205             gen_helper_float_rsqrt_d(fp0, fp0);
7206             gen_store_fpr64(ctx, fp0, fd);
7207             tcg_temp_free_i64(fp0);
7208         }
7209         opn = "rsqrt.d";
7210         break;
7211     case OPC_RECIP2_D:
7212         check_cp1_64bitmode(ctx);
7213         {
7214             TCGv_i64 fp0 = tcg_temp_new_i64();
7215             TCGv_i64 fp1 = tcg_temp_new_i64();
7216
7217             gen_load_fpr64(ctx, fp0, fs);
7218             gen_load_fpr64(ctx, fp1, ft);
7219             gen_helper_float_recip2_d(fp0, fp0, fp1);
7220             tcg_temp_free_i64(fp1);
7221             gen_store_fpr64(ctx, fp0, fd);
7222             tcg_temp_free_i64(fp0);
7223         }
7224         opn = "recip2.d";
7225         break;
7226     case OPC_RECIP1_D:
7227         check_cp1_64bitmode(ctx);
7228         {
7229             TCGv_i64 fp0 = tcg_temp_new_i64();
7230
7231             gen_load_fpr64(ctx, fp0, fs);
7232             gen_helper_float_recip1_d(fp0, fp0);
7233             gen_store_fpr64(ctx, fp0, fd);
7234             tcg_temp_free_i64(fp0);
7235         }
7236         opn = "recip1.d";
7237         break;
7238     case OPC_RSQRT1_D:
7239         check_cp1_64bitmode(ctx);
7240         {
7241             TCGv_i64 fp0 = tcg_temp_new_i64();
7242
7243             gen_load_fpr64(ctx, fp0, fs);
7244             gen_helper_float_rsqrt1_d(fp0, fp0);
7245             gen_store_fpr64(ctx, fp0, fd);
7246             tcg_temp_free_i64(fp0);
7247         }
7248         opn = "rsqrt1.d";
7249         break;
7250     case OPC_RSQRT2_D:
7251         check_cp1_64bitmode(ctx);
7252         {
7253             TCGv_i64 fp0 = tcg_temp_new_i64();
7254             TCGv_i64 fp1 = tcg_temp_new_i64();
7255
7256             gen_load_fpr64(ctx, fp0, fs);
7257             gen_load_fpr64(ctx, fp1, ft);
7258             gen_helper_float_rsqrt2_d(fp0, fp0, fp1);
7259             tcg_temp_free_i64(fp1);
7260             gen_store_fpr64(ctx, fp0, fd);
7261             tcg_temp_free_i64(fp0);
7262         }
7263         opn = "rsqrt2.d";
7264         break;
7265     case OPC_CMP_F_D:
7266     case OPC_CMP_UN_D:
7267     case OPC_CMP_EQ_D:
7268     case OPC_CMP_UEQ_D:
7269     case OPC_CMP_OLT_D:
7270     case OPC_CMP_ULT_D:
7271     case OPC_CMP_OLE_D:
7272     case OPC_CMP_ULE_D:
7273     case OPC_CMP_SF_D:
7274     case OPC_CMP_NGLE_D:
7275     case OPC_CMP_SEQ_D:
7276     case OPC_CMP_NGL_D:
7277     case OPC_CMP_LT_D:
7278     case OPC_CMP_NGE_D:
7279     case OPC_CMP_LE_D:
7280     case OPC_CMP_NGT_D:
7281         if (ctx->opcode & (1 << 6)) {
7282             gen_cmpabs_d(ctx, func-48, ft, fs, cc);
7283             opn = condnames_abs[func-48];
7284         } else {
7285             gen_cmp_d(ctx, func-48, ft, fs, cc);
7286             opn = condnames[func-48];
7287         }
7288         break;
7289     case OPC_CVT_S_D:
7290         check_cp1_registers(ctx, fs);
7291         {
7292             TCGv_i32 fp32 = tcg_temp_new_i32();
7293             TCGv_i64 fp64 = tcg_temp_new_i64();
7294
7295             gen_load_fpr64(ctx, fp64, fs);
7296             gen_helper_float_cvts_d(fp32, fp64);
7297             tcg_temp_free_i64(fp64);
7298             gen_store_fpr32(fp32, fd);
7299             tcg_temp_free_i32(fp32);
7300         }
7301         opn = "cvt.s.d";
7302         break;
7303     case OPC_CVT_W_D:
7304         check_cp1_registers(ctx, fs);
7305         {
7306             TCGv_i32 fp32 = tcg_temp_new_i32();
7307             TCGv_i64 fp64 = tcg_temp_new_i64();
7308
7309             gen_load_fpr64(ctx, fp64, fs);
7310             gen_helper_float_cvtw_d(fp32, fp64);
7311             tcg_temp_free_i64(fp64);
7312             gen_store_fpr32(fp32, fd);
7313             tcg_temp_free_i32(fp32);
7314         }
7315         opn = "cvt.w.d";
7316         break;
7317     case OPC_CVT_L_D:
7318         check_cp1_64bitmode(ctx);
7319         {
7320             TCGv_i64 fp0 = tcg_temp_new_i64();
7321
7322             gen_load_fpr64(ctx, fp0, fs);
7323             gen_helper_float_cvtl_d(fp0, fp0);
7324             gen_store_fpr64(ctx, fp0, fd);
7325             tcg_temp_free_i64(fp0);
7326         }
7327         opn = "cvt.l.d";
7328         break;
7329     case OPC_CVT_S_W:
7330         {
7331             TCGv_i32 fp0 = tcg_temp_new_i32();
7332
7333             gen_load_fpr32(fp0, fs);
7334             gen_helper_float_cvts_w(fp0, fp0);
7335             gen_store_fpr32(fp0, fd);
7336             tcg_temp_free_i32(fp0);
7337         }
7338         opn = "cvt.s.w";
7339         break;
7340     case OPC_CVT_D_W:
7341         check_cp1_registers(ctx, fd);
7342         {
7343             TCGv_i32 fp32 = tcg_temp_new_i32();
7344             TCGv_i64 fp64 = tcg_temp_new_i64();
7345
7346             gen_load_fpr32(fp32, fs);
7347             gen_helper_float_cvtd_w(fp64, fp32);
7348             tcg_temp_free_i32(fp32);
7349             gen_store_fpr64(ctx, fp64, fd);
7350             tcg_temp_free_i64(fp64);
7351         }
7352         opn = "cvt.d.w";
7353         break;
7354     case OPC_CVT_S_L:
7355         check_cp1_64bitmode(ctx);
7356         {
7357             TCGv_i32 fp32 = tcg_temp_new_i32();
7358             TCGv_i64 fp64 = tcg_temp_new_i64();
7359
7360             gen_load_fpr64(ctx, fp64, fs);
7361             gen_helper_float_cvts_l(fp32, fp64);
7362             tcg_temp_free_i64(fp64);
7363             gen_store_fpr32(fp32, fd);
7364             tcg_temp_free_i32(fp32);
7365         }
7366         opn = "cvt.s.l";
7367         break;
7368     case OPC_CVT_D_L:
7369         check_cp1_64bitmode(ctx);
7370         {
7371             TCGv_i64 fp0 = tcg_temp_new_i64();
7372
7373             gen_load_fpr64(ctx, fp0, fs);
7374             gen_helper_float_cvtd_l(fp0, fp0);
7375             gen_store_fpr64(ctx, fp0, fd);
7376             tcg_temp_free_i64(fp0);
7377         }
7378         opn = "cvt.d.l";
7379         break;
7380     case OPC_CVT_PS_PW:
7381         check_cp1_64bitmode(ctx);
7382         {
7383             TCGv_i64 fp0 = tcg_temp_new_i64();
7384
7385             gen_load_fpr64(ctx, fp0, fs);
7386             gen_helper_float_cvtps_pw(fp0, fp0);
7387             gen_store_fpr64(ctx, fp0, fd);
7388             tcg_temp_free_i64(fp0);
7389         }
7390         opn = "cvt.ps.pw";
7391         break;
7392     case OPC_ADD_PS:
7393         check_cp1_64bitmode(ctx);
7394         {
7395             TCGv_i64 fp0 = tcg_temp_new_i64();
7396             TCGv_i64 fp1 = tcg_temp_new_i64();
7397
7398             gen_load_fpr64(ctx, fp0, fs);
7399             gen_load_fpr64(ctx, fp1, ft);
7400             gen_helper_float_add_ps(fp0, fp0, fp1);
7401             tcg_temp_free_i64(fp1);
7402             gen_store_fpr64(ctx, fp0, fd);
7403             tcg_temp_free_i64(fp0);
7404         }
7405         opn = "add.ps";
7406         break;
7407     case OPC_SUB_PS:
7408         check_cp1_64bitmode(ctx);
7409         {
7410             TCGv_i64 fp0 = tcg_temp_new_i64();
7411             TCGv_i64 fp1 = tcg_temp_new_i64();
7412
7413             gen_load_fpr64(ctx, fp0, fs);
7414             gen_load_fpr64(ctx, fp1, ft);
7415             gen_helper_float_sub_ps(fp0, fp0, fp1);
7416             tcg_temp_free_i64(fp1);
7417             gen_store_fpr64(ctx, fp0, fd);
7418             tcg_temp_free_i64(fp0);
7419         }
7420         opn = "sub.ps";
7421         break;
7422     case OPC_MUL_PS:
7423         check_cp1_64bitmode(ctx);
7424         {
7425             TCGv_i64 fp0 = tcg_temp_new_i64();
7426             TCGv_i64 fp1 = tcg_temp_new_i64();
7427
7428             gen_load_fpr64(ctx, fp0, fs);
7429             gen_load_fpr64(ctx, fp1, ft);
7430             gen_helper_float_mul_ps(fp0, fp0, fp1);
7431             tcg_temp_free_i64(fp1);
7432             gen_store_fpr64(ctx, fp0, fd);
7433             tcg_temp_free_i64(fp0);
7434         }
7435         opn = "mul.ps";
7436         break;
7437     case OPC_ABS_PS:
7438         check_cp1_64bitmode(ctx);
7439         {
7440             TCGv_i64 fp0 = tcg_temp_new_i64();
7441
7442             gen_load_fpr64(ctx, fp0, fs);
7443             gen_helper_float_abs_ps(fp0, fp0);
7444             gen_store_fpr64(ctx, fp0, fd);
7445             tcg_temp_free_i64(fp0);
7446         }
7447         opn = "abs.ps";
7448         break;
7449     case OPC_MOV_PS:
7450         check_cp1_64bitmode(ctx);
7451         {
7452             TCGv_i64 fp0 = tcg_temp_new_i64();
7453
7454             gen_load_fpr64(ctx, fp0, fs);
7455             gen_store_fpr64(ctx, fp0, fd);
7456             tcg_temp_free_i64(fp0);
7457         }
7458         opn = "mov.ps";
7459         break;
7460     case OPC_NEG_PS:
7461         check_cp1_64bitmode(ctx);
7462         {
7463             TCGv_i64 fp0 = tcg_temp_new_i64();
7464
7465             gen_load_fpr64(ctx, fp0, fs);
7466             gen_helper_float_chs_ps(fp0, fp0);
7467             gen_store_fpr64(ctx, fp0, fd);
7468             tcg_temp_free_i64(fp0);
7469         }
7470         opn = "neg.ps";
7471         break;
7472     case OPC_MOVCF_PS:
7473         check_cp1_64bitmode(ctx);
7474         gen_movcf_ps(fs, fd, (ft >> 2) & 0x7, ft & 0x1);
7475         opn = "movcf.ps";
7476         break;
7477     case OPC_MOVZ_PS:
7478         check_cp1_64bitmode(ctx);
7479         {
7480             int l1 = gen_new_label();
7481             TCGv_i64 fp0;
7482
7483             if (ft != 0)
7484                 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
7485             fp0 = tcg_temp_new_i64();
7486             gen_load_fpr64(ctx, fp0, fs);
7487             gen_store_fpr64(ctx, fp0, fd);
7488             tcg_temp_free_i64(fp0);
7489             gen_set_label(l1);
7490         }
7491         opn = "movz.ps";
7492         break;
7493     case OPC_MOVN_PS:
7494         check_cp1_64bitmode(ctx);
7495         {
7496             int l1 = gen_new_label();
7497             TCGv_i64 fp0;
7498
7499             if (ft != 0) {
7500                 tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
7501                 fp0 = tcg_temp_new_i64();
7502                 gen_load_fpr64(ctx, fp0, fs);
7503                 gen_store_fpr64(ctx, fp0, fd);
7504                 tcg_temp_free_i64(fp0);
7505                 gen_set_label(l1);
7506             }
7507         }
7508         opn = "movn.ps";
7509         break;
7510     case OPC_ADDR_PS:
7511         check_cp1_64bitmode(ctx);
7512         {
7513             TCGv_i64 fp0 = tcg_temp_new_i64();
7514             TCGv_i64 fp1 = tcg_temp_new_i64();
7515
7516             gen_load_fpr64(ctx, fp0, ft);
7517             gen_load_fpr64(ctx, fp1, fs);
7518             gen_helper_float_addr_ps(fp0, fp0, fp1);
7519             tcg_temp_free_i64(fp1);
7520             gen_store_fpr64(ctx, fp0, fd);
7521             tcg_temp_free_i64(fp0);
7522         }
7523         opn = "addr.ps";
7524         break;
7525     case OPC_MULR_PS:
7526         check_cp1_64bitmode(ctx);
7527         {
7528             TCGv_i64 fp0 = tcg_temp_new_i64();
7529             TCGv_i64 fp1 = tcg_temp_new_i64();
7530
7531             gen_load_fpr64(ctx, fp0, ft);
7532             gen_load_fpr64(ctx, fp1, fs);
7533             gen_helper_float_mulr_ps(fp0, fp0, fp1);
7534             tcg_temp_free_i64(fp1);
7535             gen_store_fpr64(ctx, fp0, fd);
7536             tcg_temp_free_i64(fp0);
7537         }
7538         opn = "mulr.ps";
7539         break;
7540     case OPC_RECIP2_PS:
7541         check_cp1_64bitmode(ctx);
7542         {
7543             TCGv_i64 fp0 = tcg_temp_new_i64();
7544             TCGv_i64 fp1 = tcg_temp_new_i64();
7545
7546             gen_load_fpr64(ctx, fp0, fs);
7547             gen_load_fpr64(ctx, fp1, ft);
7548             gen_helper_float_recip2_ps(fp0, fp0, fp1);
7549             tcg_temp_free_i64(fp1);
7550             gen_store_fpr64(ctx, fp0, fd);
7551             tcg_temp_free_i64(fp0);
7552         }
7553         opn = "recip2.ps";
7554         break;
7555     case OPC_RECIP1_PS:
7556         check_cp1_64bitmode(ctx);
7557         {
7558             TCGv_i64 fp0 = tcg_temp_new_i64();
7559
7560             gen_load_fpr64(ctx, fp0, fs);
7561             gen_helper_float_recip1_ps(fp0, fp0);
7562             gen_store_fpr64(ctx, fp0, fd);
7563             tcg_temp_free_i64(fp0);
7564         }
7565         opn = "recip1.ps";
7566         break;
7567     case OPC_RSQRT1_PS:
7568         check_cp1_64bitmode(ctx);
7569         {
7570             TCGv_i64 fp0 = tcg_temp_new_i64();
7571
7572             gen_load_fpr64(ctx, fp0, fs);
7573             gen_helper_float_rsqrt1_ps(fp0, fp0);
7574             gen_store_fpr64(ctx, fp0, fd);
7575             tcg_temp_free_i64(fp0);
7576         }
7577         opn = "rsqrt1.ps";
7578         break;
7579     case OPC_RSQRT2_PS:
7580         check_cp1_64bitmode(ctx);
7581         {
7582             TCGv_i64 fp0 = tcg_temp_new_i64();
7583             TCGv_i64 fp1 = tcg_temp_new_i64();
7584
7585             gen_load_fpr64(ctx, fp0, fs);
7586             gen_load_fpr64(ctx, fp1, ft);
7587             gen_helper_float_rsqrt2_ps(fp0, fp0, fp1);
7588             tcg_temp_free_i64(fp1);
7589             gen_store_fpr64(ctx, fp0, fd);
7590             tcg_temp_free_i64(fp0);
7591         }
7592         opn = "rsqrt2.ps";
7593         break;
7594     case OPC_CVT_S_PU:
7595         check_cp1_64bitmode(ctx);
7596         {
7597             TCGv_i32 fp0 = tcg_temp_new_i32();
7598
7599             gen_load_fpr32h(fp0, fs);
7600             gen_helper_float_cvts_pu(fp0, fp0);
7601             gen_store_fpr32(fp0, fd);
7602             tcg_temp_free_i32(fp0);
7603         }
7604         opn = "cvt.s.pu";
7605         break;
7606     case OPC_CVT_PW_PS:
7607         check_cp1_64bitmode(ctx);
7608         {
7609             TCGv_i64 fp0 = tcg_temp_new_i64();
7610
7611             gen_load_fpr64(ctx, fp0, fs);
7612             gen_helper_float_cvtpw_ps(fp0, fp0);
7613             gen_store_fpr64(ctx, fp0, fd);
7614             tcg_temp_free_i64(fp0);
7615         }
7616         opn = "cvt.pw.ps";
7617         break;
7618     case OPC_CVT_S_PL:
7619         check_cp1_64bitmode(ctx);
7620         {
7621             TCGv_i32 fp0 = tcg_temp_new_i32();
7622
7623             gen_load_fpr32(fp0, fs);
7624             gen_helper_float_cvts_pl(fp0, fp0);
7625             gen_store_fpr32(fp0, fd);
7626             tcg_temp_free_i32(fp0);
7627         }
7628         opn = "cvt.s.pl";
7629         break;
7630     case OPC_PLL_PS:
7631         check_cp1_64bitmode(ctx);
7632         {
7633             TCGv_i32 fp0 = tcg_temp_new_i32();
7634             TCGv_i32 fp1 = tcg_temp_new_i32();
7635
7636             gen_load_fpr32(fp0, fs);
7637             gen_load_fpr32(fp1, ft);
7638             gen_store_fpr32h(fp0, fd);
7639             gen_store_fpr32(fp1, fd);
7640             tcg_temp_free_i32(fp0);
7641             tcg_temp_free_i32(fp1);
7642         }
7643         opn = "pll.ps";
7644         break;
7645     case OPC_PLU_PS:
7646         check_cp1_64bitmode(ctx);
7647         {
7648             TCGv_i32 fp0 = tcg_temp_new_i32();
7649             TCGv_i32 fp1 = tcg_temp_new_i32();
7650
7651             gen_load_fpr32(fp0, fs);
7652             gen_load_fpr32h(fp1, ft);
7653             gen_store_fpr32(fp1, fd);
7654             gen_store_fpr32h(fp0, fd);
7655             tcg_temp_free_i32(fp0);
7656             tcg_temp_free_i32(fp1);
7657         }
7658         opn = "plu.ps";
7659         break;
7660     case OPC_PUL_PS:
7661         check_cp1_64bitmode(ctx);
7662         {
7663             TCGv_i32 fp0 = tcg_temp_new_i32();
7664             TCGv_i32 fp1 = tcg_temp_new_i32();
7665
7666             gen_load_fpr32h(fp0, fs);
7667             gen_load_fpr32(fp1, ft);
7668             gen_store_fpr32(fp1, fd);
7669             gen_store_fpr32h(fp0, fd);
7670             tcg_temp_free_i32(fp0);
7671             tcg_temp_free_i32(fp1);
7672         }
7673         opn = "pul.ps";
7674         break;
7675     case OPC_PUU_PS:
7676         check_cp1_64bitmode(ctx);
7677         {
7678             TCGv_i32 fp0 = tcg_temp_new_i32();
7679             TCGv_i32 fp1 = tcg_temp_new_i32();
7680
7681             gen_load_fpr32h(fp0, fs);
7682             gen_load_fpr32h(fp1, ft);
7683             gen_store_fpr32(fp1, fd);
7684             gen_store_fpr32h(fp0, fd);
7685             tcg_temp_free_i32(fp0);
7686             tcg_temp_free_i32(fp1);
7687         }
7688         opn = "puu.ps";
7689         break;
7690     case OPC_CMP_F_PS:
7691     case OPC_CMP_UN_PS:
7692     case OPC_CMP_EQ_PS:
7693     case OPC_CMP_UEQ_PS:
7694     case OPC_CMP_OLT_PS:
7695     case OPC_CMP_ULT_PS:
7696     case OPC_CMP_OLE_PS:
7697     case OPC_CMP_ULE_PS:
7698     case OPC_CMP_SF_PS:
7699     case OPC_CMP_NGLE_PS:
7700     case OPC_CMP_SEQ_PS:
7701     case OPC_CMP_NGL_PS:
7702     case OPC_CMP_LT_PS:
7703     case OPC_CMP_NGE_PS:
7704     case OPC_CMP_LE_PS:
7705     case OPC_CMP_NGT_PS:
7706         if (ctx->opcode & (1 << 6)) {
7707             gen_cmpabs_ps(ctx, func-48, ft, fs, cc);
7708             opn = condnames_abs[func-48];
7709         } else {
7710             gen_cmp_ps(ctx, func-48, ft, fs, cc);
7711             opn = condnames[func-48];
7712         }
7713         break;
7714     default:
7715         MIPS_INVAL(opn);
7716         generate_exception (ctx, EXCP_RI);
7717         return;
7718     }
7719     (void)opn; /* avoid a compiler warning */
7720     switch (optype) {
7721     case BINOP:
7722         MIPS_DEBUG("%s %s, %s, %s", opn, fregnames[fd], fregnames[fs], fregnames[ft]);
7723         break;
7724     case CMPOP:
7725         MIPS_DEBUG("%s %s,%s", opn, fregnames[fs], fregnames[ft]);
7726         break;
7727     default:
7728         MIPS_DEBUG("%s %s,%s", opn, fregnames[fd], fregnames[fs]);
7729         break;
7730     }
7731 }
7732
7733 /* Coprocessor 3 (FPU) */
7734 static void gen_flt3_ldst (DisasContext *ctx, uint32_t opc,
7735                            int fd, int fs, int base, int index)
7736 {
7737     const char *opn = "extended float load/store";
7738     int store = 0;
7739     TCGv t0 = tcg_temp_new();
7740
7741     if (base == 0) {
7742         gen_load_gpr(t0, index);
7743     } else if (index == 0) {
7744         gen_load_gpr(t0, base);
7745     } else {
7746         gen_op_addr_add(ctx, t0, cpu_gpr[base], cpu_gpr[index]);
7747     }
7748     /* Don't do NOP if destination is zero: we must perform the actual
7749        memory access. */
7750     save_cpu_state(ctx, 0);
7751     switch (opc) {
7752     case OPC_LWXC1:
7753         check_cop1x(ctx);
7754         {
7755             TCGv_i32 fp0 = tcg_temp_new_i32();
7756
7757             tcg_gen_qemu_ld32s(t0, t0, ctx->mem_idx);
7758             tcg_gen_trunc_tl_i32(fp0, t0);
7759             gen_store_fpr32(fp0, fd);
7760             tcg_temp_free_i32(fp0);
7761         }
7762         opn = "lwxc1";
7763         break;
7764     case OPC_LDXC1:
7765         check_cop1x(ctx);
7766         check_cp1_registers(ctx, fd);
7767         {
7768             TCGv_i64 fp0 = tcg_temp_new_i64();
7769
7770             tcg_gen_qemu_ld64(fp0, t0, ctx->mem_idx);
7771             gen_store_fpr64(ctx, fp0, fd);
7772             tcg_temp_free_i64(fp0);
7773         }
7774         opn = "ldxc1";
7775         break;
7776     case OPC_LUXC1:
7777         check_cp1_64bitmode(ctx);
7778         tcg_gen_andi_tl(t0, t0, ~0x7);
7779         {
7780             TCGv_i64 fp0 = tcg_temp_new_i64();
7781
7782             tcg_gen_qemu_ld64(fp0, t0, ctx->mem_idx);
7783             gen_store_fpr64(ctx, fp0, fd);
7784             tcg_temp_free_i64(fp0);
7785         }
7786         opn = "luxc1";
7787         break;
7788     case OPC_SWXC1:
7789         check_cop1x(ctx);
7790         {
7791             TCGv_i32 fp0 = tcg_temp_new_i32();
7792             TCGv t1 = tcg_temp_new();
7793
7794             gen_load_fpr32(fp0, fs);
7795             tcg_gen_extu_i32_tl(t1, fp0);
7796             tcg_gen_qemu_st32(t1, t0, ctx->mem_idx);
7797             tcg_temp_free_i32(fp0);
7798             tcg_temp_free(t1);
7799         }
7800         opn = "swxc1";
7801         store = 1;
7802         break;
7803     case OPC_SDXC1:
7804         check_cop1x(ctx);
7805         check_cp1_registers(ctx, fs);
7806         {
7807             TCGv_i64 fp0 = tcg_temp_new_i64();
7808
7809             gen_load_fpr64(ctx, fp0, fs);
7810             tcg_gen_qemu_st64(fp0, t0, ctx->mem_idx);
7811             tcg_temp_free_i64(fp0);
7812         }
7813         opn = "sdxc1";
7814         store = 1;
7815         break;
7816     case OPC_SUXC1:
7817         check_cp1_64bitmode(ctx);
7818         tcg_gen_andi_tl(t0, t0, ~0x7);
7819         {
7820             TCGv_i64 fp0 = tcg_temp_new_i64();
7821
7822             gen_load_fpr64(ctx, fp0, fs);
7823             tcg_gen_qemu_st64(fp0, t0, ctx->mem_idx);
7824             tcg_temp_free_i64(fp0);
7825         }
7826         opn = "suxc1";
7827         store = 1;
7828         break;
7829     }
7830     tcg_temp_free(t0);
7831     (void)opn; (void)store; /* avoid compiler warnings */
7832     MIPS_DEBUG("%s %s, %s(%s)", opn, fregnames[store ? fs : fd],
7833                regnames[index], regnames[base]);
7834 }
7835
7836 static void gen_flt3_arith (DisasContext *ctx, uint32_t opc,
7837                             int fd, int fr, int fs, int ft)
7838 {
7839     const char *opn = "flt3_arith";
7840
7841     switch (opc) {
7842     case OPC_ALNV_PS:
7843         check_cp1_64bitmode(ctx);
7844         {
7845             TCGv t0 = tcg_temp_local_new();
7846             TCGv_i32 fp = tcg_temp_new_i32();
7847             TCGv_i32 fph = tcg_temp_new_i32();
7848             int l1 = gen_new_label();
7849             int l2 = gen_new_label();
7850
7851             gen_load_gpr(t0, fr);
7852             tcg_gen_andi_tl(t0, t0, 0x7);
7853
7854             tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
7855             gen_load_fpr32(fp, fs);
7856             gen_load_fpr32h(fph, fs);
7857             gen_store_fpr32(fp, fd);
7858             gen_store_fpr32h(fph, fd);
7859             tcg_gen_br(l2);
7860             gen_set_label(l1);
7861             tcg_gen_brcondi_tl(TCG_COND_NE, t0, 4, l2);
7862             tcg_temp_free(t0);
7863 #ifdef TARGET_WORDS_BIGENDIAN
7864             gen_load_fpr32(fp, fs);
7865             gen_load_fpr32h(fph, ft);
7866             gen_store_fpr32h(fp, fd);
7867             gen_store_fpr32(fph, fd);
7868 #else
7869             gen_load_fpr32h(fph, fs);
7870             gen_load_fpr32(fp, ft);
7871             gen_store_fpr32(fph, fd);
7872             gen_store_fpr32h(fp, fd);
7873 #endif
7874             gen_set_label(l2);
7875             tcg_temp_free_i32(fp);
7876             tcg_temp_free_i32(fph);
7877         }
7878         opn = "alnv.ps";
7879         break;
7880     case OPC_MADD_S:
7881         check_cop1x(ctx);
7882         {
7883             TCGv_i32 fp0 = tcg_temp_new_i32();
7884             TCGv_i32 fp1 = tcg_temp_new_i32();
7885             TCGv_i32 fp2 = tcg_temp_new_i32();
7886
7887             gen_load_fpr32(fp0, fs);
7888             gen_load_fpr32(fp1, ft);
7889             gen_load_fpr32(fp2, fr);
7890             gen_helper_float_muladd_s(fp2, fp0, fp1, fp2);
7891             tcg_temp_free_i32(fp0);
7892             tcg_temp_free_i32(fp1);
7893             gen_store_fpr32(fp2, fd);
7894             tcg_temp_free_i32(fp2);
7895         }
7896         opn = "madd.s";
7897         break;
7898     case OPC_MADD_D:
7899         check_cop1x(ctx);
7900         check_cp1_registers(ctx, fd | fs | ft | fr);
7901         {
7902             TCGv_i64 fp0 = tcg_temp_new_i64();
7903             TCGv_i64 fp1 = tcg_temp_new_i64();
7904             TCGv_i64 fp2 = tcg_temp_new_i64();
7905
7906             gen_load_fpr64(ctx, fp0, fs);
7907             gen_load_fpr64(ctx, fp1, ft);
7908             gen_load_fpr64(ctx, fp2, fr);
7909             gen_helper_float_muladd_d(fp2, fp0, fp1, fp2);
7910             tcg_temp_free_i64(fp0);
7911             tcg_temp_free_i64(fp1);
7912             gen_store_fpr64(ctx, fp2, fd);
7913             tcg_temp_free_i64(fp2);
7914         }
7915         opn = "madd.d";
7916         break;
7917     case OPC_MADD_PS:
7918         check_cp1_64bitmode(ctx);
7919         {
7920             TCGv_i64 fp0 = tcg_temp_new_i64();
7921             TCGv_i64 fp1 = tcg_temp_new_i64();
7922             TCGv_i64 fp2 = tcg_temp_new_i64();
7923
7924             gen_load_fpr64(ctx, fp0, fs);
7925             gen_load_fpr64(ctx, fp1, ft);
7926             gen_load_fpr64(ctx, fp2, fr);
7927             gen_helper_float_muladd_ps(fp2, fp0, fp1, fp2);
7928             tcg_temp_free_i64(fp0);
7929             tcg_temp_free_i64(fp1);
7930             gen_store_fpr64(ctx, fp2, fd);
7931             tcg_temp_free_i64(fp2);
7932         }
7933         opn = "madd.ps";
7934         break;
7935     case OPC_MSUB_S:
7936         check_cop1x(ctx);
7937         {
7938             TCGv_i32 fp0 = tcg_temp_new_i32();
7939             TCGv_i32 fp1 = tcg_temp_new_i32();
7940             TCGv_i32 fp2 = tcg_temp_new_i32();
7941
7942             gen_load_fpr32(fp0, fs);
7943             gen_load_fpr32(fp1, ft);
7944             gen_load_fpr32(fp2, fr);
7945             gen_helper_float_mulsub_s(fp2, fp0, fp1, fp2);
7946             tcg_temp_free_i32(fp0);
7947             tcg_temp_free_i32(fp1);
7948             gen_store_fpr32(fp2, fd);
7949             tcg_temp_free_i32(fp2);
7950         }
7951         opn = "msub.s";
7952         break;
7953     case OPC_MSUB_D:
7954         check_cop1x(ctx);
7955         check_cp1_registers(ctx, fd | fs | ft | fr);
7956         {
7957             TCGv_i64 fp0 = tcg_temp_new_i64();
7958             TCGv_i64 fp1 = tcg_temp_new_i64();
7959             TCGv_i64 fp2 = tcg_temp_new_i64();
7960
7961             gen_load_fpr64(ctx, fp0, fs);
7962             gen_load_fpr64(ctx, fp1, ft);
7963             gen_load_fpr64(ctx, fp2, fr);
7964             gen_helper_float_mulsub_d(fp2, fp0, fp1, fp2);
7965             tcg_temp_free_i64(fp0);
7966             tcg_temp_free_i64(fp1);
7967             gen_store_fpr64(ctx, fp2, fd);
7968             tcg_temp_free_i64(fp2);
7969         }
7970         opn = "msub.d";
7971         break;
7972     case OPC_MSUB_PS:
7973         check_cp1_64bitmode(ctx);
7974         {
7975             TCGv_i64 fp0 = tcg_temp_new_i64();
7976             TCGv_i64 fp1 = tcg_temp_new_i64();
7977             TCGv_i64 fp2 = tcg_temp_new_i64();
7978
7979             gen_load_fpr64(ctx, fp0, fs);
7980             gen_load_fpr64(ctx, fp1, ft);
7981             gen_load_fpr64(ctx, fp2, fr);
7982             gen_helper_float_mulsub_ps(fp2, fp0, fp1, fp2);
7983             tcg_temp_free_i64(fp0);
7984             tcg_temp_free_i64(fp1);
7985             gen_store_fpr64(ctx, fp2, fd);
7986             tcg_temp_free_i64(fp2);
7987         }
7988         opn = "msub.ps";
7989         break;
7990     case OPC_NMADD_S:
7991         check_cop1x(ctx);
7992         {
7993             TCGv_i32 fp0 = tcg_temp_new_i32();
7994             TCGv_i32 fp1 = tcg_temp_new_i32();
7995             TCGv_i32 fp2 = tcg_temp_new_i32();
7996
7997             gen_load_fpr32(fp0, fs);
7998             gen_load_fpr32(fp1, ft);
7999             gen_load_fpr32(fp2, fr);
8000             gen_helper_float_nmuladd_s(fp2, fp0, fp1, fp2);
8001             tcg_temp_free_i32(fp0);
8002             tcg_temp_free_i32(fp1);
8003             gen_store_fpr32(fp2, fd);
8004             tcg_temp_free_i32(fp2);
8005         }
8006         opn = "nmadd.s";
8007         break;
8008     case OPC_NMADD_D:
8009         check_cop1x(ctx);
8010         check_cp1_registers(ctx, fd | fs | ft | fr);
8011         {
8012             TCGv_i64 fp0 = tcg_temp_new_i64();
8013             TCGv_i64 fp1 = tcg_temp_new_i64();
8014             TCGv_i64 fp2 = tcg_temp_new_i64();
8015
8016             gen_load_fpr64(ctx, fp0, fs);
8017             gen_load_fpr64(ctx, fp1, ft);
8018             gen_load_fpr64(ctx, fp2, fr);
8019             gen_helper_float_nmuladd_d(fp2, fp0, fp1, fp2);
8020             tcg_temp_free_i64(fp0);
8021             tcg_temp_free_i64(fp1);
8022             gen_store_fpr64(ctx, fp2, fd);
8023             tcg_temp_free_i64(fp2);
8024         }
8025         opn = "nmadd.d";
8026         break;
8027     case OPC_NMADD_PS:
8028         check_cp1_64bitmode(ctx);
8029         {
8030             TCGv_i64 fp0 = tcg_temp_new_i64();
8031             TCGv_i64 fp1 = tcg_temp_new_i64();
8032             TCGv_i64 fp2 = tcg_temp_new_i64();
8033
8034             gen_load_fpr64(ctx, fp0, fs);
8035             gen_load_fpr64(ctx, fp1, ft);
8036             gen_load_fpr64(ctx, fp2, fr);
8037             gen_helper_float_nmuladd_ps(fp2, fp0, fp1, fp2);
8038             tcg_temp_free_i64(fp0);
8039             tcg_temp_free_i64(fp1);
8040             gen_store_fpr64(ctx, fp2, fd);
8041             tcg_temp_free_i64(fp2);
8042         }
8043         opn = "nmadd.ps";
8044         break;
8045     case OPC_NMSUB_S:
8046         check_cop1x(ctx);
8047         {
8048             TCGv_i32 fp0 = tcg_temp_new_i32();
8049             TCGv_i32 fp1 = tcg_temp_new_i32();
8050             TCGv_i32 fp2 = tcg_temp_new_i32();
8051
8052             gen_load_fpr32(fp0, fs);
8053             gen_load_fpr32(fp1, ft);
8054             gen_load_fpr32(fp2, fr);
8055             gen_helper_float_nmulsub_s(fp2, fp0, fp1, fp2);
8056             tcg_temp_free_i32(fp0);
8057             tcg_temp_free_i32(fp1);
8058             gen_store_fpr32(fp2, fd);
8059             tcg_temp_free_i32(fp2);
8060         }
8061         opn = "nmsub.s";
8062         break;
8063     case OPC_NMSUB_D:
8064         check_cop1x(ctx);
8065         check_cp1_registers(ctx, fd | fs | ft | fr);
8066         {
8067             TCGv_i64 fp0 = tcg_temp_new_i64();
8068             TCGv_i64 fp1 = tcg_temp_new_i64();
8069             TCGv_i64 fp2 = tcg_temp_new_i64();
8070
8071             gen_load_fpr64(ctx, fp0, fs);
8072             gen_load_fpr64(ctx, fp1, ft);
8073             gen_load_fpr64(ctx, fp2, fr);
8074             gen_helper_float_nmulsub_d(fp2, fp0, fp1, fp2);
8075             tcg_temp_free_i64(fp0);
8076             tcg_temp_free_i64(fp1);
8077             gen_store_fpr64(ctx, fp2, fd);
8078             tcg_temp_free_i64(fp2);
8079         }
8080         opn = "nmsub.d";
8081         break;
8082     case OPC_NMSUB_PS:
8083         check_cp1_64bitmode(ctx);
8084         {
8085             TCGv_i64 fp0 = tcg_temp_new_i64();
8086             TCGv_i64 fp1 = tcg_temp_new_i64();
8087             TCGv_i64 fp2 = tcg_temp_new_i64();
8088
8089             gen_load_fpr64(ctx, fp0, fs);
8090             gen_load_fpr64(ctx, fp1, ft);
8091             gen_load_fpr64(ctx, fp2, fr);
8092             gen_helper_float_nmulsub_ps(fp2, fp0, fp1, fp2);
8093             tcg_temp_free_i64(fp0);
8094             tcg_temp_free_i64(fp1);
8095             gen_store_fpr64(ctx, fp2, fd);
8096             tcg_temp_free_i64(fp2);
8097         }
8098         opn = "nmsub.ps";
8099         break;
8100     default:
8101         MIPS_INVAL(opn);
8102         generate_exception (ctx, EXCP_RI);
8103         return;
8104     }
8105     (void)opn; /* avoid a compiler warning */
8106     MIPS_DEBUG("%s %s, %s, %s, %s", opn, fregnames[fd], fregnames[fr],
8107                fregnames[fs], fregnames[ft]);
8108 }
8109
8110 static void
8111 gen_rdhwr (CPUMIPSState *env, DisasContext *ctx, int rt, int rd)
8112 {
8113     TCGv t0;
8114
8115 #if !defined(CONFIG_USER_ONLY)
8116     /* The Linux kernel will emulate rdhwr if it's not supported natively.
8117        Therefore only check the ISA in system mode.  */
8118     check_insn(env, ctx, ISA_MIPS32R2);
8119 #endif
8120     t0 = tcg_temp_new();
8121
8122     switch (rd) {
8123     case 0:
8124         save_cpu_state(ctx, 1);
8125         gen_helper_rdhwr_cpunum(t0);
8126         gen_store_gpr(t0, rt);
8127         break;
8128     case 1:
8129         save_cpu_state(ctx, 1);
8130         gen_helper_rdhwr_synci_step(t0);
8131         gen_store_gpr(t0, rt);
8132         break;
8133     case 2:
8134         save_cpu_state(ctx, 1);
8135         gen_helper_rdhwr_cc(t0);
8136         gen_store_gpr(t0, rt);
8137         break;
8138     case 3:
8139         save_cpu_state(ctx, 1);
8140         gen_helper_rdhwr_ccres(t0);
8141         gen_store_gpr(t0, rt);
8142         break;
8143     case 29:
8144 #if defined(CONFIG_USER_ONLY)
8145         tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUMIPSState, tls_value));
8146         gen_store_gpr(t0, rt);
8147         break;
8148 #else
8149         /* XXX: Some CPUs implement this in hardware.
8150            Not supported yet. */
8151 #endif
8152     default:            /* Invalid */
8153         MIPS_INVAL("rdhwr");
8154         generate_exception(ctx, EXCP_RI);
8155         break;
8156     }
8157     tcg_temp_free(t0);
8158 }
8159
8160 static void handle_delay_slot (CPUMIPSState *env, DisasContext *ctx,
8161                                int insn_bytes)
8162 {
8163     if (ctx->hflags & MIPS_HFLAG_BMASK) {
8164         int proc_hflags = ctx->hflags & MIPS_HFLAG_BMASK;
8165         /* Branches completion */
8166         ctx->hflags &= ~MIPS_HFLAG_BMASK;
8167         ctx->bstate = BS_BRANCH;
8168         save_cpu_state(ctx, 0);
8169         /* FIXME: Need to clear can_do_io.  */
8170         switch (proc_hflags & MIPS_HFLAG_BMASK_BASE) {
8171         case MIPS_HFLAG_B:
8172             /* unconditional branch */
8173             MIPS_DEBUG("unconditional branch");
8174             if (proc_hflags & MIPS_HFLAG_BX) {
8175                 tcg_gen_xori_i32(hflags, hflags, MIPS_HFLAG_M16);
8176             }
8177             gen_goto_tb(ctx, 0, ctx->btarget);
8178             break;
8179         case MIPS_HFLAG_BL:
8180             /* blikely taken case */
8181             MIPS_DEBUG("blikely branch taken");
8182             gen_goto_tb(ctx, 0, ctx->btarget);
8183             break;
8184         case MIPS_HFLAG_BC:
8185             /* Conditional branch */
8186             MIPS_DEBUG("conditional branch");
8187             {
8188                 int l1 = gen_new_label();
8189
8190                 tcg_gen_brcondi_tl(TCG_COND_NE, bcond, 0, l1);
8191                 gen_goto_tb(ctx, 1, ctx->pc + insn_bytes);
8192                 gen_set_label(l1);
8193                 gen_goto_tb(ctx, 0, ctx->btarget);
8194             }
8195             break;
8196         case MIPS_HFLAG_BR:
8197             /* unconditional branch to register */
8198             MIPS_DEBUG("branch to register");
8199             if (env->insn_flags & (ASE_MIPS16 | ASE_MICROMIPS)) {
8200                 TCGv t0 = tcg_temp_new();
8201                 TCGv_i32 t1 = tcg_temp_new_i32();
8202
8203                 tcg_gen_andi_tl(t0, btarget, 0x1);
8204                 tcg_gen_trunc_tl_i32(t1, t0);
8205                 tcg_temp_free(t0);
8206                 tcg_gen_andi_i32(hflags, hflags, ~(uint32_t)MIPS_HFLAG_M16);
8207                 tcg_gen_shli_i32(t1, t1, MIPS_HFLAG_M16_SHIFT);
8208                 tcg_gen_or_i32(hflags, hflags, t1);
8209                 tcg_temp_free_i32(t1);
8210
8211                 tcg_gen_andi_tl(cpu_PC, btarget, ~(target_ulong)0x1);
8212             } else {
8213                 tcg_gen_mov_tl(cpu_PC, btarget);
8214             }
8215             if (ctx->singlestep_enabled) {
8216                 save_cpu_state(ctx, 0);
8217                 gen_helper_0i(raise_exception, EXCP_DEBUG);
8218             }
8219             tcg_gen_exit_tb(0);
8220             break;
8221         default:
8222             MIPS_DEBUG("unknown branch");
8223             break;
8224         }
8225     }
8226 }
8227
8228 /* ISA extensions (ASEs) */
8229 /* MIPS16 extension to MIPS32 */
8230
8231 /* MIPS16 major opcodes */
8232 enum {
8233   M16_OPC_ADDIUSP = 0x00,
8234   M16_OPC_ADDIUPC = 0x01,
8235   M16_OPC_B = 0x02,
8236   M16_OPC_JAL = 0x03,
8237   M16_OPC_BEQZ = 0x04,
8238   M16_OPC_BNEQZ = 0x05,
8239   M16_OPC_SHIFT = 0x06,
8240   M16_OPC_LD = 0x07,
8241   M16_OPC_RRIA = 0x08,
8242   M16_OPC_ADDIU8 = 0x09,
8243   M16_OPC_SLTI = 0x0a,
8244   M16_OPC_SLTIU = 0x0b,
8245   M16_OPC_I8 = 0x0c,
8246   M16_OPC_LI = 0x0d,
8247   M16_OPC_CMPI = 0x0e,
8248   M16_OPC_SD = 0x0f,
8249   M16_OPC_LB = 0x10,
8250   M16_OPC_LH = 0x11,
8251   M16_OPC_LWSP = 0x12,
8252   M16_OPC_LW = 0x13,
8253   M16_OPC_LBU = 0x14,
8254   M16_OPC_LHU = 0x15,
8255   M16_OPC_LWPC = 0x16,
8256   M16_OPC_LWU = 0x17,
8257   M16_OPC_SB = 0x18,
8258   M16_OPC_SH = 0x19,
8259   M16_OPC_SWSP = 0x1a,
8260   M16_OPC_SW = 0x1b,
8261   M16_OPC_RRR = 0x1c,
8262   M16_OPC_RR = 0x1d,
8263   M16_OPC_EXTEND = 0x1e,
8264   M16_OPC_I64 = 0x1f
8265 };
8266
8267 /* I8 funct field */
8268 enum {
8269   I8_BTEQZ = 0x0,
8270   I8_BTNEZ = 0x1,
8271   I8_SWRASP = 0x2,
8272   I8_ADJSP = 0x3,
8273   I8_SVRS = 0x4,
8274   I8_MOV32R = 0x5,
8275   I8_MOVR32 = 0x7
8276 };
8277
8278 /* RRR f field */
8279 enum {
8280   RRR_DADDU = 0x0,
8281   RRR_ADDU = 0x1,
8282   RRR_DSUBU = 0x2,
8283   RRR_SUBU = 0x3
8284 };
8285
8286 /* RR funct field */
8287 enum {
8288   RR_JR = 0x00,
8289   RR_SDBBP = 0x01,
8290   RR_SLT = 0x02,
8291   RR_SLTU = 0x03,
8292   RR_SLLV = 0x04,
8293   RR_BREAK = 0x05,
8294   RR_SRLV = 0x06,
8295   RR_SRAV = 0x07,
8296   RR_DSRL = 0x08,
8297   RR_CMP = 0x0a,
8298   RR_NEG = 0x0b,
8299   RR_AND = 0x0c,
8300   RR_OR = 0x0d,
8301   RR_XOR = 0x0e,
8302   RR_NOT = 0x0f,
8303   RR_MFHI = 0x10,
8304   RR_CNVT = 0x11,
8305   RR_MFLO = 0x12,
8306   RR_DSRA = 0x13,
8307   RR_DSLLV = 0x14,
8308   RR_DSRLV = 0x16,
8309   RR_DSRAV = 0x17,
8310   RR_MULT = 0x18,
8311   RR_MULTU = 0x19,
8312   RR_DIV = 0x1a,
8313   RR_DIVU = 0x1b,
8314   RR_DMULT = 0x1c,
8315   RR_DMULTU = 0x1d,
8316   RR_DDIV = 0x1e,
8317   RR_DDIVU = 0x1f
8318 };
8319
8320 /* I64 funct field */
8321 enum {
8322   I64_LDSP = 0x0,
8323   I64_SDSP = 0x1,
8324   I64_SDRASP = 0x2,
8325   I64_DADJSP = 0x3,
8326   I64_LDPC = 0x4,
8327   I64_DADDIU5 = 0x5,
8328   I64_DADDIUPC = 0x6,
8329   I64_DADDIUSP = 0x7
8330 };
8331
8332 /* RR ry field for CNVT */
8333 enum {
8334   RR_RY_CNVT_ZEB = 0x0,
8335   RR_RY_CNVT_ZEH = 0x1,
8336   RR_RY_CNVT_ZEW = 0x2,
8337   RR_RY_CNVT_SEB = 0x4,
8338   RR_RY_CNVT_SEH = 0x5,
8339   RR_RY_CNVT_SEW = 0x6,
8340 };
8341
8342 static int xlat (int r)
8343 {
8344   static int map[] = { 16, 17, 2, 3, 4, 5, 6, 7 };
8345
8346   return map[r];
8347 }
8348
8349 static void gen_mips16_save (DisasContext *ctx,
8350                              int xsregs, int aregs,
8351                              int do_ra, int do_s0, int do_s1,
8352                              int framesize)
8353 {
8354     TCGv t0 = tcg_temp_new();
8355     TCGv t1 = tcg_temp_new();
8356     int args, astatic;
8357
8358     switch (aregs) {
8359     case 0:
8360     case 1:
8361     case 2:
8362     case 3:
8363     case 11:
8364         args = 0;
8365         break;
8366     case 4:
8367     case 5:
8368     case 6:
8369     case 7:
8370         args = 1;
8371         break;
8372     case 8:
8373     case 9:
8374     case 10:
8375         args = 2;
8376         break;
8377     case 12:
8378     case 13:
8379         args = 3;
8380         break;
8381     case 14:
8382         args = 4;
8383         break;
8384     default:
8385         generate_exception(ctx, EXCP_RI);
8386         return;
8387     }
8388
8389     switch (args) {
8390     case 4:
8391         gen_base_offset_addr(ctx, t0, 29, 12);
8392         gen_load_gpr(t1, 7);
8393         op_st_sw(t1, t0, ctx);
8394         /* Fall through */
8395     case 3:
8396         gen_base_offset_addr(ctx, t0, 29, 8);
8397         gen_load_gpr(t1, 6);
8398         op_st_sw(t1, t0, ctx);
8399         /* Fall through */
8400     case 2:
8401         gen_base_offset_addr(ctx, t0, 29, 4);
8402         gen_load_gpr(t1, 5);
8403         op_st_sw(t1, t0, ctx);
8404         /* Fall through */
8405     case 1:
8406         gen_base_offset_addr(ctx, t0, 29, 0);
8407         gen_load_gpr(t1, 4);
8408         op_st_sw(t1, t0, ctx);
8409     }
8410
8411     gen_load_gpr(t0, 29);
8412
8413 #define DECR_AND_STORE(reg) do {                \
8414         tcg_gen_subi_tl(t0, t0, 4);             \
8415         gen_load_gpr(t1, reg);                  \
8416         op_st_sw(t1, t0, ctx);                  \
8417     } while (0)
8418
8419     if (do_ra) {
8420         DECR_AND_STORE(31);
8421     }
8422
8423     switch (xsregs) {
8424     case 7:
8425         DECR_AND_STORE(30);
8426         /* Fall through */
8427     case 6:
8428         DECR_AND_STORE(23);
8429         /* Fall through */
8430     case 5:
8431         DECR_AND_STORE(22);
8432         /* Fall through */
8433     case 4:
8434         DECR_AND_STORE(21);
8435         /* Fall through */
8436     case 3:
8437         DECR_AND_STORE(20);
8438         /* Fall through */
8439     case 2:
8440         DECR_AND_STORE(19);
8441         /* Fall through */
8442     case 1:
8443         DECR_AND_STORE(18);
8444     }
8445
8446     if (do_s1) {
8447         DECR_AND_STORE(17);
8448     }
8449     if (do_s0) {
8450         DECR_AND_STORE(16);
8451     }
8452
8453     switch (aregs) {
8454     case 0:
8455     case 4:
8456     case 8:
8457     case 12:
8458     case 14:
8459         astatic = 0;
8460         break;
8461     case 1:
8462     case 5:
8463     case 9:
8464     case 13:
8465         astatic = 1;
8466         break;
8467     case 2:
8468     case 6:
8469     case 10:
8470         astatic = 2;
8471         break;
8472     case 3:
8473     case 7:
8474         astatic = 3;
8475         break;
8476     case 11:
8477         astatic = 4;
8478         break;
8479     default:
8480         generate_exception(ctx, EXCP_RI);
8481         return;
8482     }
8483
8484     if (astatic > 0) {
8485         DECR_AND_STORE(7);
8486         if (astatic > 1) {
8487             DECR_AND_STORE(6);
8488             if (astatic > 2) {
8489                 DECR_AND_STORE(5);
8490                 if (astatic > 3) {
8491                     DECR_AND_STORE(4);
8492                 }
8493             }
8494         }
8495     }
8496 #undef DECR_AND_STORE
8497
8498     tcg_gen_subi_tl(cpu_gpr[29], cpu_gpr[29], framesize);
8499     tcg_temp_free(t0);
8500     tcg_temp_free(t1);
8501 }
8502
8503 static void gen_mips16_restore (DisasContext *ctx,
8504                                 int xsregs, int aregs,
8505                                 int do_ra, int do_s0, int do_s1,
8506                                 int framesize)
8507 {
8508     int astatic;
8509     TCGv t0 = tcg_temp_new();
8510     TCGv t1 = tcg_temp_new();
8511
8512     tcg_gen_addi_tl(t0, cpu_gpr[29], framesize);
8513
8514 #define DECR_AND_LOAD(reg) do {                 \
8515         tcg_gen_subi_tl(t0, t0, 4);             \
8516         op_ld_lw(t1, t0, ctx);                  \
8517         gen_store_gpr(t1, reg);                 \
8518     } while (0)
8519
8520     if (do_ra) {
8521         DECR_AND_LOAD(31);
8522     }
8523
8524     switch (xsregs) {
8525     case 7:
8526         DECR_AND_LOAD(30);
8527         /* Fall through */
8528     case 6:
8529         DECR_AND_LOAD(23);
8530         /* Fall through */
8531     case 5:
8532         DECR_AND_LOAD(22);
8533         /* Fall through */
8534     case 4:
8535         DECR_AND_LOAD(21);
8536         /* Fall through */
8537     case 3:
8538         DECR_AND_LOAD(20);
8539         /* Fall through */
8540     case 2:
8541         DECR_AND_LOAD(19);
8542         /* Fall through */
8543     case 1:
8544         DECR_AND_LOAD(18);
8545     }
8546
8547     if (do_s1) {
8548         DECR_AND_LOAD(17);
8549     }
8550     if (do_s0) {
8551         DECR_AND_LOAD(16);
8552     }
8553
8554     switch (aregs) {
8555     case 0:
8556     case 4:
8557     case 8:
8558     case 12:
8559     case 14:
8560         astatic = 0;
8561         break;
8562     case 1:
8563     case 5:
8564     case 9:
8565     case 13:
8566         astatic = 1;
8567         break;
8568     case 2:
8569     case 6:
8570     case 10:
8571         astatic = 2;
8572         break;
8573     case 3:
8574     case 7:
8575         astatic = 3;
8576         break;
8577     case 11:
8578         astatic = 4;
8579         break;
8580     default:
8581         generate_exception(ctx, EXCP_RI);
8582         return;
8583     }
8584
8585     if (astatic > 0) {
8586         DECR_AND_LOAD(7);
8587         if (astatic > 1) {
8588             DECR_AND_LOAD(6);
8589             if (astatic > 2) {
8590                 DECR_AND_LOAD(5);
8591                 if (astatic > 3) {
8592                     DECR_AND_LOAD(4);
8593                 }
8594             }
8595         }
8596     }
8597 #undef DECR_AND_LOAD
8598
8599     tcg_gen_addi_tl(cpu_gpr[29], cpu_gpr[29], framesize);
8600     tcg_temp_free(t0);
8601     tcg_temp_free(t1);
8602 }
8603
8604 static void gen_addiupc (DisasContext *ctx, int rx, int imm,
8605                          int is_64_bit, int extended)
8606 {
8607     TCGv t0;
8608
8609     if (extended && (ctx->hflags & MIPS_HFLAG_BMASK)) {
8610         generate_exception(ctx, EXCP_RI);
8611         return;
8612     }
8613
8614     t0 = tcg_temp_new();
8615
8616     tcg_gen_movi_tl(t0, pc_relative_pc(ctx));
8617     tcg_gen_addi_tl(cpu_gpr[rx], t0, imm);
8618     if (!is_64_bit) {
8619         tcg_gen_ext32s_tl(cpu_gpr[rx], cpu_gpr[rx]);
8620     }
8621
8622     tcg_temp_free(t0);
8623 }
8624
8625 #if defined(TARGET_MIPS64)
8626 static void decode_i64_mips16 (CPUMIPSState *env, DisasContext *ctx,
8627                                int ry, int funct, int16_t offset,
8628                                int extended)
8629 {
8630     switch (funct) {
8631     case I64_LDSP:
8632         check_mips_64(ctx);
8633         offset = extended ? offset : offset << 3;
8634         gen_ld(env, ctx, OPC_LD, ry, 29, offset);
8635         break;
8636     case I64_SDSP:
8637         check_mips_64(ctx);
8638         offset = extended ? offset : offset << 3;
8639         gen_st(ctx, OPC_SD, ry, 29, offset);
8640         break;
8641     case I64_SDRASP:
8642         check_mips_64(ctx);
8643         offset = extended ? offset : (ctx->opcode & 0xff) << 3;
8644         gen_st(ctx, OPC_SD, 31, 29, offset);
8645         break;
8646     case I64_DADJSP:
8647         check_mips_64(ctx);
8648         offset = extended ? offset : ((int8_t)ctx->opcode) << 3;
8649         gen_arith_imm(env, ctx, OPC_DADDIU, 29, 29, offset);
8650         break;
8651     case I64_LDPC:
8652         if (extended && (ctx->hflags & MIPS_HFLAG_BMASK)) {
8653             generate_exception(ctx, EXCP_RI);
8654         } else {
8655             offset = extended ? offset : offset << 3;
8656             gen_ld(env, ctx, OPC_LDPC, ry, 0, offset);
8657         }
8658         break;
8659     case I64_DADDIU5:
8660         check_mips_64(ctx);
8661         offset = extended ? offset : ((int8_t)(offset << 3)) >> 3;
8662         gen_arith_imm(env, ctx, OPC_DADDIU, ry, ry, offset);
8663         break;
8664     case I64_DADDIUPC:
8665         check_mips_64(ctx);
8666         offset = extended ? offset : offset << 2;
8667         gen_addiupc(ctx, ry, offset, 1, extended);
8668         break;
8669     case I64_DADDIUSP:
8670         check_mips_64(ctx);
8671         offset = extended ? offset : offset << 2;
8672         gen_arith_imm(env, ctx, OPC_DADDIU, ry, 29, offset);
8673         break;
8674     }
8675 }
8676 #endif
8677
8678 static int decode_extended_mips16_opc (CPUMIPSState *env, DisasContext *ctx,
8679                                        int *is_branch)
8680 {
8681     int extend = lduw_code(ctx->pc + 2);
8682     int op, rx, ry, funct, sa;
8683     int16_t imm, offset;
8684
8685     ctx->opcode = (ctx->opcode << 16) | extend;
8686     op = (ctx->opcode >> 11) & 0x1f;
8687     sa = (ctx->opcode >> 22) & 0x1f;
8688     funct = (ctx->opcode >> 8) & 0x7;
8689     rx = xlat((ctx->opcode >> 8) & 0x7);
8690     ry = xlat((ctx->opcode >> 5) & 0x7);
8691     offset = imm = (int16_t) (((ctx->opcode >> 16) & 0x1f) << 11
8692                               | ((ctx->opcode >> 21) & 0x3f) << 5
8693                               | (ctx->opcode & 0x1f));
8694
8695     /* The extended opcodes cleverly reuse the opcodes from their 16-bit
8696        counterparts.  */
8697     switch (op) {
8698     case M16_OPC_ADDIUSP:
8699         gen_arith_imm(env, ctx, OPC_ADDIU, rx, 29, imm);
8700         break;
8701     case M16_OPC_ADDIUPC:
8702         gen_addiupc(ctx, rx, imm, 0, 1);
8703         break;
8704     case M16_OPC_B:
8705         gen_compute_branch(ctx, OPC_BEQ, 4, 0, 0, offset << 1);
8706         /* No delay slot, so just process as a normal instruction */
8707         break;
8708     case M16_OPC_BEQZ:
8709         gen_compute_branch(ctx, OPC_BEQ, 4, rx, 0, offset << 1);
8710         /* No delay slot, so just process as a normal instruction */
8711         break;
8712     case M16_OPC_BNEQZ:
8713         gen_compute_branch(ctx, OPC_BNE, 4, rx, 0, offset << 1);
8714         /* No delay slot, so just process as a normal instruction */
8715         break;
8716     case M16_OPC_SHIFT:
8717         switch (ctx->opcode & 0x3) {
8718         case 0x0:
8719             gen_shift_imm(env, ctx, OPC_SLL, rx, ry, sa);
8720             break;
8721         case 0x1:
8722 #if defined(TARGET_MIPS64)
8723             check_mips_64(ctx);
8724             gen_shift_imm(env, ctx, OPC_DSLL, rx, ry, sa);
8725 #else
8726             generate_exception(ctx, EXCP_RI);
8727 #endif
8728             break;
8729         case 0x2:
8730             gen_shift_imm(env, ctx, OPC_SRL, rx, ry, sa);
8731             break;
8732         case 0x3:
8733             gen_shift_imm(env, ctx, OPC_SRA, rx, ry, sa);
8734             break;
8735         }
8736         break;
8737 #if defined(TARGET_MIPS64)
8738     case M16_OPC_LD:
8739             check_mips_64(ctx);
8740         gen_ld(env, ctx, OPC_LD, ry, rx, offset);
8741         break;
8742 #endif
8743     case M16_OPC_RRIA:
8744         imm = ctx->opcode & 0xf;
8745         imm = imm | ((ctx->opcode >> 20) & 0x7f) << 4;
8746         imm = imm | ((ctx->opcode >> 16) & 0xf) << 11;
8747         imm = (int16_t) (imm << 1) >> 1;
8748         if ((ctx->opcode >> 4) & 0x1) {
8749 #if defined(TARGET_MIPS64)
8750             check_mips_64(ctx);
8751             gen_arith_imm(env, ctx, OPC_DADDIU, ry, rx, imm);
8752 #else
8753             generate_exception(ctx, EXCP_RI);
8754 #endif
8755         } else {
8756             gen_arith_imm(env, ctx, OPC_ADDIU, ry, rx, imm);
8757         }
8758         break;
8759     case M16_OPC_ADDIU8:
8760         gen_arith_imm(env, ctx, OPC_ADDIU, rx, rx, imm);
8761         break;
8762     case M16_OPC_SLTI:
8763         gen_slt_imm(env, OPC_SLTI, 24, rx, imm);
8764         break;
8765     case M16_OPC_SLTIU:
8766         gen_slt_imm(env, OPC_SLTIU, 24, rx, imm);
8767         break;
8768     case M16_OPC_I8:
8769         switch (funct) {
8770         case I8_BTEQZ:
8771             gen_compute_branch(ctx, OPC_BEQ, 4, 24, 0, offset << 1);
8772             break;
8773         case I8_BTNEZ:
8774             gen_compute_branch(ctx, OPC_BNE, 4, 24, 0, offset << 1);
8775             break;
8776         case I8_SWRASP:
8777             gen_st(ctx, OPC_SW, 31, 29, imm);
8778             break;
8779         case I8_ADJSP:
8780             gen_arith_imm(env, ctx, OPC_ADDIU, 29, 29, imm);
8781             break;
8782         case I8_SVRS:
8783             {
8784                 int xsregs = (ctx->opcode >> 24) & 0x7;
8785                 int aregs = (ctx->opcode >> 16) & 0xf;
8786                 int do_ra = (ctx->opcode >> 6) & 0x1;
8787                 int do_s0 = (ctx->opcode >> 5) & 0x1;
8788                 int do_s1 = (ctx->opcode >> 4) & 0x1;
8789                 int framesize = (((ctx->opcode >> 20) & 0xf) << 4
8790                                  | (ctx->opcode & 0xf)) << 3;
8791
8792                 if (ctx->opcode & (1 << 7)) {
8793                     gen_mips16_save(ctx, xsregs, aregs,
8794                                     do_ra, do_s0, do_s1,
8795                                     framesize);
8796                 } else {
8797                     gen_mips16_restore(ctx, xsregs, aregs,
8798                                        do_ra, do_s0, do_s1,
8799                                        framesize);
8800                 }
8801             }
8802             break;
8803         default:
8804             generate_exception(ctx, EXCP_RI);
8805             break;
8806         }
8807         break;
8808     case M16_OPC_LI:
8809         tcg_gen_movi_tl(cpu_gpr[rx], (uint16_t) imm);
8810         break;
8811     case M16_OPC_CMPI:
8812         tcg_gen_xori_tl(cpu_gpr[24], cpu_gpr[rx], (uint16_t) imm);
8813         break;
8814 #if defined(TARGET_MIPS64)
8815     case M16_OPC_SD:
8816         gen_st(ctx, OPC_SD, ry, rx, offset);
8817         break;
8818 #endif
8819     case M16_OPC_LB:
8820         gen_ld(env, ctx, OPC_LB, ry, rx, offset);
8821         break;
8822     case M16_OPC_LH:
8823         gen_ld(env, ctx, OPC_LH, ry, rx, offset);
8824         break;
8825     case M16_OPC_LWSP:
8826         gen_ld(env, ctx, OPC_LW, rx, 29, offset);
8827         break;
8828     case M16_OPC_LW:
8829         gen_ld(env, ctx, OPC_LW, ry, rx, offset);
8830         break;
8831     case M16_OPC_LBU:
8832         gen_ld(env, ctx, OPC_LBU, ry, rx, offset);
8833         break;
8834     case M16_OPC_LHU:
8835         gen_ld(env, ctx, OPC_LHU, ry, rx, offset);
8836         break;
8837     case M16_OPC_LWPC:
8838         gen_ld(env, ctx, OPC_LWPC, rx, 0, offset);
8839         break;
8840 #if defined(TARGET_MIPS64)
8841     case M16_OPC_LWU:
8842         gen_ld(env, ctx, OPC_LWU, ry, rx, offset);
8843         break;
8844 #endif
8845     case M16_OPC_SB:
8846         gen_st(ctx, OPC_SB, ry, rx, offset);
8847         break;
8848     case M16_OPC_SH:
8849         gen_st(ctx, OPC_SH, ry, rx, offset);
8850         break;
8851     case M16_OPC_SWSP:
8852         gen_st(ctx, OPC_SW, rx, 29, offset);
8853         break;
8854     case M16_OPC_SW:
8855         gen_st(ctx, OPC_SW, ry, rx, offset);
8856         break;
8857 #if defined(TARGET_MIPS64)
8858     case M16_OPC_I64:
8859         decode_i64_mips16(env, ctx, ry, funct, offset, 1);
8860         break;
8861 #endif
8862     default:
8863         generate_exception(ctx, EXCP_RI);
8864         break;
8865     }
8866
8867     return 4;
8868 }
8869
8870 static int decode_mips16_opc (CPUMIPSState *env, DisasContext *ctx,
8871                               int *is_branch)
8872 {
8873     int rx, ry;
8874     int sa;
8875     int op, cnvt_op, op1, offset;
8876     int funct;
8877     int n_bytes;
8878
8879     op = (ctx->opcode >> 11) & 0x1f;
8880     sa = (ctx->opcode >> 2) & 0x7;
8881     sa = sa == 0 ? 8 : sa;
8882     rx = xlat((ctx->opcode >> 8) & 0x7);
8883     cnvt_op = (ctx->opcode >> 5) & 0x7;
8884     ry = xlat((ctx->opcode >> 5) & 0x7);
8885     op1 = offset = ctx->opcode & 0x1f;
8886
8887     n_bytes = 2;
8888
8889     switch (op) {
8890     case M16_OPC_ADDIUSP:
8891         {
8892             int16_t imm = ((uint8_t) ctx->opcode) << 2;
8893
8894             gen_arith_imm(env, ctx, OPC_ADDIU, rx, 29, imm);
8895         }
8896         break;
8897     case M16_OPC_ADDIUPC:
8898         gen_addiupc(ctx, rx, ((uint8_t) ctx->opcode) << 2, 0, 0);
8899         break;
8900     case M16_OPC_B:
8901         offset = (ctx->opcode & 0x7ff) << 1;
8902         offset = (int16_t)(offset << 4) >> 4;
8903         gen_compute_branch(ctx, OPC_BEQ, 2, 0, 0, offset);
8904         /* No delay slot, so just process as a normal instruction */
8905         break;
8906     case M16_OPC_JAL:
8907         offset = lduw_code(ctx->pc + 2);
8908         offset = (((ctx->opcode & 0x1f) << 21)
8909                   | ((ctx->opcode >> 5) & 0x1f) << 16
8910                   | offset) << 2;
8911         op = ((ctx->opcode >> 10) & 0x1) ? OPC_JALXS : OPC_JALS;
8912         gen_compute_branch(ctx, op, 4, rx, ry, offset);
8913         n_bytes = 4;
8914         *is_branch = 1;
8915         break;
8916     case M16_OPC_BEQZ:
8917         gen_compute_branch(ctx, OPC_BEQ, 2, rx, 0, ((int8_t)ctx->opcode) << 1);
8918         /* No delay slot, so just process as a normal instruction */
8919         break;
8920     case M16_OPC_BNEQZ:
8921         gen_compute_branch(ctx, OPC_BNE, 2, rx, 0, ((int8_t)ctx->opcode) << 1);
8922         /* No delay slot, so just process as a normal instruction */
8923         break;
8924     case M16_OPC_SHIFT:
8925         switch (ctx->opcode & 0x3) {
8926         case 0x0:
8927             gen_shift_imm(env, ctx, OPC_SLL, rx, ry, sa);
8928             break;
8929         case 0x1:
8930 #if defined(TARGET_MIPS64)
8931             check_mips_64(ctx);
8932             gen_shift_imm(env, ctx, OPC_DSLL, rx, ry, sa);
8933 #else
8934             generate_exception(ctx, EXCP_RI);
8935 #endif
8936             break;
8937         case 0x2:
8938             gen_shift_imm(env, ctx, OPC_SRL, rx, ry, sa);
8939             break;
8940         case 0x3:
8941             gen_shift_imm(env, ctx, OPC_SRA, rx, ry, sa);
8942             break;
8943         }
8944         break;
8945 #if defined(TARGET_MIPS64)
8946     case M16_OPC_LD:
8947         check_mips_64(ctx);
8948         gen_ld(env, ctx, OPC_LD, ry, rx, offset << 3);
8949         break;
8950 #endif
8951     case M16_OPC_RRIA:
8952         {
8953             int16_t imm = (int8_t)((ctx->opcode & 0xf) << 4) >> 4;
8954
8955             if ((ctx->opcode >> 4) & 1) {
8956 #if defined(TARGET_MIPS64)
8957                 check_mips_64(ctx);
8958                 gen_arith_imm(env, ctx, OPC_DADDIU, ry, rx, imm);
8959 #else
8960                 generate_exception(ctx, EXCP_RI);
8961 #endif
8962             } else {
8963                 gen_arith_imm(env, ctx, OPC_ADDIU, ry, rx, imm);
8964             }
8965         }
8966         break;
8967     case M16_OPC_ADDIU8:
8968         {
8969             int16_t imm = (int8_t) ctx->opcode;
8970
8971             gen_arith_imm(env, ctx, OPC_ADDIU, rx, rx, imm);
8972         }
8973         break;
8974     case M16_OPC_SLTI:
8975         {
8976             int16_t imm = (uint8_t) ctx->opcode;
8977
8978             gen_slt_imm(env, OPC_SLTI, 24, rx, imm);
8979         }
8980         break;
8981     case M16_OPC_SLTIU:
8982         {
8983             int16_t imm = (uint8_t) ctx->opcode;
8984
8985             gen_slt_imm(env, OPC_SLTIU, 24, rx, imm);
8986         }
8987         break;
8988     case M16_OPC_I8:
8989         {
8990             int reg32;
8991
8992             funct = (ctx->opcode >> 8) & 0x7;
8993             switch (funct) {
8994             case I8_BTEQZ:
8995                 gen_compute_branch(ctx, OPC_BEQ, 2, 24, 0,
8996                                    ((int8_t)ctx->opcode) << 1);
8997                 break;
8998             case I8_BTNEZ:
8999                 gen_compute_branch(ctx, OPC_BNE, 2, 24, 0,
9000                                    ((int8_t)ctx->opcode) << 1);
9001                 break;
9002             case I8_SWRASP:
9003                 gen_st(ctx, OPC_SW, 31, 29, (ctx->opcode & 0xff) << 2);
9004                 break;
9005             case I8_ADJSP:
9006                 gen_arith_imm(env, ctx, OPC_ADDIU, 29, 29,
9007                               ((int8_t)ctx->opcode) << 3);
9008                 break;
9009             case I8_SVRS:
9010                 {
9011                     int do_ra = ctx->opcode & (1 << 6);
9012                     int do_s0 = ctx->opcode & (1 << 5);
9013                     int do_s1 = ctx->opcode & (1 << 4);
9014                     int framesize = ctx->opcode & 0xf;
9015
9016                     if (framesize == 0) {
9017                         framesize = 128;
9018                     } else {
9019                         framesize = framesize << 3;
9020                     }
9021
9022                     if (ctx->opcode & (1 << 7)) {
9023                         gen_mips16_save(ctx, 0, 0,
9024                                         do_ra, do_s0, do_s1, framesize);
9025                     } else {
9026                         gen_mips16_restore(ctx, 0, 0,
9027                                            do_ra, do_s0, do_s1, framesize);
9028                     }
9029                 }
9030                 break;
9031             case I8_MOV32R:
9032                 {
9033                     int rz = xlat(ctx->opcode & 0x7);
9034
9035                     reg32 = (((ctx->opcode >> 3) & 0x3) << 3) |
9036                         ((ctx->opcode >> 5) & 0x7);
9037                     gen_arith(env, ctx, OPC_ADDU, reg32, rz, 0);
9038                 }
9039                 break;
9040             case I8_MOVR32:
9041                 reg32 = ctx->opcode & 0x1f;
9042                 gen_arith(env, ctx, OPC_ADDU, ry, reg32, 0);
9043                 break;
9044             default:
9045                 generate_exception(ctx, EXCP_RI);
9046                 break;
9047             }
9048         }
9049         break;
9050     case M16_OPC_LI:
9051         {
9052             int16_t imm = (uint8_t) ctx->opcode;
9053
9054             gen_arith_imm(env, ctx, OPC_ADDIU, rx, 0, imm);
9055         }
9056         break;
9057     case M16_OPC_CMPI:
9058         {
9059             int16_t imm = (uint8_t) ctx->opcode;
9060
9061             gen_logic_imm(env, OPC_XORI, 24, rx, imm);
9062         }
9063         break;
9064 #if defined(TARGET_MIPS64)
9065     case M16_OPC_SD:
9066         check_mips_64(ctx);
9067         gen_st(ctx, OPC_SD, ry, rx, offset << 3);
9068         break;
9069 #endif
9070     case M16_OPC_LB:
9071         gen_ld(env, ctx, OPC_LB, ry, rx, offset);
9072         break;
9073     case M16_OPC_LH:
9074         gen_ld(env, ctx, OPC_LH, ry, rx, offset << 1);
9075         break;
9076     case M16_OPC_LWSP:
9077         gen_ld(env, ctx, OPC_LW, rx, 29, ((uint8_t)ctx->opcode) << 2);
9078         break;
9079     case M16_OPC_LW:
9080         gen_ld(env, ctx, OPC_LW, ry, rx, offset << 2);
9081         break;
9082     case M16_OPC_LBU:
9083         gen_ld(env, ctx, OPC_LBU, ry, rx, offset);
9084         break;
9085     case M16_OPC_LHU:
9086         gen_ld(env, ctx, OPC_LHU, ry, rx, offset << 1);
9087         break;
9088     case M16_OPC_LWPC:
9089         gen_ld(env, ctx, OPC_LWPC, rx, 0, ((uint8_t)ctx->opcode) << 2);
9090         break;
9091 #if defined (TARGET_MIPS64)
9092     case M16_OPC_LWU:
9093         check_mips_64(ctx);
9094         gen_ld(env, ctx, OPC_LWU, ry, rx, offset << 2);
9095         break;
9096 #endif
9097     case M16_OPC_SB:
9098         gen_st(ctx, OPC_SB, ry, rx, offset);
9099         break;
9100     case M16_OPC_SH:
9101         gen_st(ctx, OPC_SH, ry, rx, offset << 1);
9102         break;
9103     case M16_OPC_SWSP:
9104         gen_st(ctx, OPC_SW, rx, 29, ((uint8_t)ctx->opcode) << 2);
9105         break;
9106     case M16_OPC_SW:
9107         gen_st(ctx, OPC_SW, ry, rx, offset << 2);
9108         break;
9109     case M16_OPC_RRR:
9110         {
9111             int rz = xlat((ctx->opcode >> 2) & 0x7);
9112             int mips32_op;
9113
9114             switch (ctx->opcode & 0x3) {
9115             case RRR_ADDU:
9116                 mips32_op = OPC_ADDU;
9117                 break;
9118             case RRR_SUBU:
9119                 mips32_op = OPC_SUBU;
9120                 break;
9121 #if defined(TARGET_MIPS64)
9122             case RRR_DADDU:
9123                 mips32_op = OPC_DADDU;
9124                 check_mips_64(ctx);
9125                 break;
9126             case RRR_DSUBU:
9127                 mips32_op = OPC_DSUBU;
9128                 check_mips_64(ctx);
9129                 break;
9130 #endif
9131             default:
9132                 generate_exception(ctx, EXCP_RI);
9133                 goto done;
9134             }
9135
9136             gen_arith(env, ctx, mips32_op, rz, rx, ry);
9137         done:
9138             ;
9139         }
9140         break;
9141     case M16_OPC_RR:
9142         switch (op1) {
9143         case RR_JR:
9144             {
9145                 int nd = (ctx->opcode >> 7) & 0x1;
9146                 int link = (ctx->opcode >> 6) & 0x1;
9147                 int ra = (ctx->opcode >> 5) & 0x1;
9148
9149                 if (link) {
9150                     op = nd ? OPC_JALRC : OPC_JALRS;
9151                 } else {
9152                     op = OPC_JR;
9153                 }
9154
9155                 gen_compute_branch(ctx, op, 2, ra ? 31 : rx, 31, 0);
9156                 if (!nd) {
9157                     *is_branch = 1;
9158                 }
9159             }
9160             break;
9161         case RR_SDBBP:
9162             /* XXX: not clear which exception should be raised
9163              *      when in debug mode...
9164              */
9165             check_insn(env, ctx, ISA_MIPS32);
9166             if (!(ctx->hflags & MIPS_HFLAG_DM)) {
9167                 generate_exception(ctx, EXCP_DBp);
9168             } else {
9169                 generate_exception(ctx, EXCP_DBp);
9170             }
9171             break;
9172         case RR_SLT:
9173             gen_slt(env, OPC_SLT, 24, rx, ry);
9174             break;
9175         case RR_SLTU:
9176             gen_slt(env, OPC_SLTU, 24, rx, ry);
9177             break;
9178         case RR_BREAK:
9179             generate_exception(ctx, EXCP_BREAK);
9180             break;
9181         case RR_SLLV:
9182             gen_shift(env, ctx, OPC_SLLV, ry, rx, ry);
9183             break;
9184         case RR_SRLV:
9185             gen_shift(env, ctx, OPC_SRLV, ry, rx, ry);
9186             break;
9187         case RR_SRAV:
9188             gen_shift(env, ctx, OPC_SRAV, ry, rx, ry);
9189             break;
9190 #if defined (TARGET_MIPS64)
9191         case RR_DSRL:
9192             check_mips_64(ctx);
9193             gen_shift_imm(env, ctx, OPC_DSRL, ry, ry, sa);
9194             break;
9195 #endif
9196         case RR_CMP:
9197             gen_logic(env, OPC_XOR, 24, rx, ry);
9198             break;
9199         case RR_NEG:
9200             gen_arith(env, ctx, OPC_SUBU, rx, 0, ry);
9201             break;
9202         case RR_AND:
9203             gen_logic(env, OPC_AND, rx, rx, ry);
9204             break;
9205         case RR_OR:
9206             gen_logic(env, OPC_OR, rx, rx, ry);
9207             break;
9208         case RR_XOR:
9209             gen_logic(env, OPC_XOR, rx, rx, ry);
9210             break;
9211         case RR_NOT:
9212             gen_logic(env, OPC_NOR, rx, ry, 0);
9213             break;
9214         case RR_MFHI:
9215             gen_HILO(ctx, OPC_MFHI, rx);
9216             break;
9217         case RR_CNVT:
9218             switch (cnvt_op) {
9219             case RR_RY_CNVT_ZEB:
9220                 tcg_gen_ext8u_tl(cpu_gpr[rx], cpu_gpr[rx]);
9221                 break;
9222             case RR_RY_CNVT_ZEH:
9223                 tcg_gen_ext16u_tl(cpu_gpr[rx], cpu_gpr[rx]);
9224                 break;
9225             case RR_RY_CNVT_SEB:
9226                 tcg_gen_ext8s_tl(cpu_gpr[rx], cpu_gpr[rx]);
9227                 break;
9228             case RR_RY_CNVT_SEH:
9229                 tcg_gen_ext16s_tl(cpu_gpr[rx], cpu_gpr[rx]);
9230                 break;
9231 #if defined (TARGET_MIPS64)
9232             case RR_RY_CNVT_ZEW:
9233                 check_mips_64(ctx);
9234                 tcg_gen_ext32u_tl(cpu_gpr[rx], cpu_gpr[rx]);
9235                 break;
9236             case RR_RY_CNVT_SEW:
9237                 check_mips_64(ctx);
9238                 tcg_gen_ext32s_tl(cpu_gpr[rx], cpu_gpr[rx]);
9239                 break;
9240 #endif
9241             default:
9242                 generate_exception(ctx, EXCP_RI);
9243                 break;
9244             }
9245             break;
9246         case RR_MFLO:
9247             gen_HILO(ctx, OPC_MFLO, rx);
9248             break;
9249 #if defined (TARGET_MIPS64)
9250         case RR_DSRA:
9251             check_mips_64(ctx);
9252             gen_shift_imm(env, ctx, OPC_DSRA, ry, ry, sa);
9253             break;
9254         case RR_DSLLV:
9255             check_mips_64(ctx);
9256             gen_shift(env, ctx, OPC_DSLLV, ry, rx, ry);
9257             break;
9258         case RR_DSRLV:
9259             check_mips_64(ctx);
9260             gen_shift(env, ctx, OPC_DSRLV, ry, rx, ry);
9261             break;
9262         case RR_DSRAV:
9263             check_mips_64(ctx);
9264             gen_shift(env, ctx, OPC_DSRAV, ry, rx, ry);
9265             break;
9266 #endif
9267         case RR_MULT:
9268             gen_muldiv(ctx, OPC_MULT, rx, ry);
9269             break;
9270         case RR_MULTU:
9271             gen_muldiv(ctx, OPC_MULTU, rx, ry);
9272             break;
9273         case RR_DIV:
9274             gen_muldiv(ctx, OPC_DIV, rx, ry);
9275             break;
9276         case RR_DIVU:
9277             gen_muldiv(ctx, OPC_DIVU, rx, ry);
9278             break;
9279 #if defined (TARGET_MIPS64)
9280         case RR_DMULT:
9281             check_mips_64(ctx);
9282             gen_muldiv(ctx, OPC_DMULT, rx, ry);
9283             break;
9284         case RR_DMULTU:
9285             check_mips_64(ctx);
9286             gen_muldiv(ctx, OPC_DMULTU, rx, ry);
9287             break;
9288         case RR_DDIV:
9289             check_mips_64(ctx);
9290             gen_muldiv(ctx, OPC_DDIV, rx, ry);
9291             break;
9292         case RR_DDIVU:
9293             check_mips_64(ctx);
9294             gen_muldiv(ctx, OPC_DDIVU, rx, ry);
9295             break;
9296 #endif
9297         default:
9298             generate_exception(ctx, EXCP_RI);
9299             break;
9300         }
9301         break;
9302     case M16_OPC_EXTEND:
9303         decode_extended_mips16_opc(env, ctx, is_branch);
9304         n_bytes = 4;
9305         break;
9306 #if defined(TARGET_MIPS64)
9307     case M16_OPC_I64:
9308         funct = (ctx->opcode >> 8) & 0x7;
9309         decode_i64_mips16(env, ctx, ry, funct, offset, 0);
9310         break;
9311 #endif
9312     default:
9313         generate_exception(ctx, EXCP_RI);
9314         break;
9315     }
9316
9317     return n_bytes;
9318 }
9319
9320 /* microMIPS extension to MIPS32 */
9321
9322 /* microMIPS32 major opcodes */
9323
9324 enum {
9325     POOL32A = 0x00,
9326     POOL16A = 0x01,
9327     LBU16 = 0x02,
9328     MOVE16 = 0x03,
9329     ADDI32 = 0x04,
9330     LBU32 = 0x05,
9331     SB32 = 0x06,
9332     LB32 = 0x07,
9333
9334     POOL32B = 0x08,
9335     POOL16B = 0x09,
9336     LHU16 = 0x0a,
9337     ANDI16 = 0x0b,
9338     ADDIU32 = 0x0c,
9339     LHU32 = 0x0d,
9340     SH32 = 0x0e,
9341     LH32 = 0x0f,
9342
9343     POOL32I = 0x10,
9344     POOL16C = 0x11,
9345     LWSP16 = 0x12,
9346     POOL16D = 0x13,
9347     ORI32 = 0x14,
9348     POOL32F = 0x15,
9349     POOL32S = 0x16,
9350     DADDIU32 = 0x17,
9351
9352     POOL32C = 0x18,
9353     LWGP16 = 0x19,
9354     LW16 = 0x1a,
9355     POOL16E = 0x1b,
9356     XORI32 = 0x1c,
9357     JALS32 = 0x1d,
9358     ADDIUPC = 0x1e,
9359     POOL48A = 0x1f,
9360
9361     /* 0x20 is reserved */
9362     RES_20 = 0x20,
9363     POOL16F = 0x21,
9364     SB16 = 0x22,
9365     BEQZ16 = 0x23,
9366     SLTI32 = 0x24,
9367     BEQ32 = 0x25,
9368     SWC132 = 0x26,
9369     LWC132 = 0x27,
9370
9371     /* 0x28 and 0x29 are reserved */
9372     RES_28 = 0x28,
9373     RES_29 = 0x29,
9374     SH16 = 0x2a,
9375     BNEZ16 = 0x2b,
9376     SLTIU32 = 0x2c,
9377     BNE32 = 0x2d,
9378     SDC132 = 0x2e,
9379     LDC132 = 0x2f,
9380
9381     /* 0x30 and 0x31 are reserved */
9382     RES_30 = 0x30,
9383     RES_31 = 0x31,
9384     SWSP16 = 0x32,
9385     B16 = 0x33,
9386     ANDI32 = 0x34,
9387     J32 = 0x35,
9388     SD32 = 0x36,
9389     LD32 = 0x37,
9390
9391     /* 0x38 and 0x39 are reserved */
9392     RES_38 = 0x38,
9393     RES_39 = 0x39,
9394     SW16 = 0x3a,
9395     LI16 = 0x3b,
9396     JALX32 = 0x3c,
9397     JAL32 = 0x3d,
9398     SW32 = 0x3e,
9399     LW32 = 0x3f
9400 };
9401
9402 /* POOL32A encoding of minor opcode field */
9403
9404 enum {
9405     /* These opcodes are distinguished only by bits 9..6; those bits are
9406      * what are recorded below. */
9407     SLL32 = 0x0,
9408     SRL32 = 0x1,
9409     SRA = 0x2,
9410     ROTR = 0x3,
9411
9412     SLLV = 0x0,
9413     SRLV = 0x1,
9414     SRAV = 0x2,
9415     ROTRV = 0x3,
9416     ADD = 0x4,
9417     ADDU32 = 0x5,
9418     SUB = 0x6,
9419     SUBU32 = 0x7,
9420     MUL = 0x8,
9421     AND = 0x9,
9422     OR32 = 0xa,
9423     NOR = 0xb,
9424     XOR32 = 0xc,
9425     SLT = 0xd,
9426     SLTU = 0xe,
9427
9428     MOVN = 0x0,
9429     MOVZ = 0x1,
9430     LWXS = 0x4,
9431
9432     /* The following can be distinguished by their lower 6 bits. */
9433     INS = 0x0c,
9434     EXT = 0x2c,
9435     POOL32AXF = 0x3c
9436 };
9437
9438 /* POOL32AXF encoding of minor opcode field extension */
9439
9440 enum {
9441     /* bits 11..6 */
9442     TEQ = 0x00,
9443     TGE = 0x08,
9444     TGEU = 0x10,
9445     TLT = 0x20,
9446     TLTU = 0x28,
9447     TNE = 0x30,
9448
9449     MFC0 = 0x03,
9450     MTC0 = 0x0b,
9451
9452     /* bits 13..12 for 0x01 */
9453     MFHI_ACC = 0x0,
9454     MFLO_ACC = 0x1,
9455     MTHI_ACC = 0x2,
9456     MTLO_ACC = 0x3,
9457
9458     /* bits 13..12 for 0x2a */
9459     MADD_ACC = 0x0,
9460     MADDU_ACC = 0x1,
9461     MSUB_ACC = 0x2,
9462     MSUBU_ACC = 0x3,
9463
9464     /* bits 13..12 for 0x32 */
9465     MULT_ACC = 0x0,
9466     MULTU_ACC = 0x0,
9467
9468     /* bits 15..12 for 0x2c */
9469     SEB = 0x2,
9470     SEH = 0x3,
9471     CLO = 0x4,
9472     CLZ = 0x5,
9473     RDHWR = 0x6,
9474     WSBH = 0x7,
9475     MULT = 0x8,
9476     MULTU = 0x9,
9477     DIV = 0xa,
9478     DIVU = 0xb,
9479     MADD = 0xc,
9480     MADDU = 0xd,
9481     MSUB = 0xe,
9482     MSUBU = 0xf,
9483
9484     /* bits 15..12 for 0x34 */
9485     MFC2 = 0x4,
9486     MTC2 = 0x5,
9487     MFHC2 = 0x8,
9488     MTHC2 = 0x9,
9489     CFC2 = 0xc,
9490     CTC2 = 0xd,
9491
9492     /* bits 15..12 for 0x3c */
9493     JALR = 0x0,
9494     JR = 0x0,                   /* alias */
9495     JALR_HB = 0x1,
9496     JALRS = 0x4,
9497     JALRS_HB = 0x5,
9498
9499     /* bits 15..12 for 0x05 */
9500     RDPGPR = 0xe,
9501     WRPGPR = 0xf,
9502
9503     /* bits 15..12 for 0x0d */
9504     TLBP = 0x0,
9505     TLBR = 0x1,
9506     TLBWI = 0x2,
9507     TLBWR = 0x3,
9508     WAIT = 0x9,
9509     IRET = 0xd,
9510     DERET = 0xe,
9511     ERET = 0xf,
9512
9513     /* bits 15..12 for 0x15 */
9514     DMT = 0x0,
9515     DVPE = 0x1,
9516     EMT = 0x2,
9517     EVPE = 0x3,
9518
9519     /* bits 15..12 for 0x1d */
9520     DI = 0x4,
9521     EI = 0x5,
9522
9523     /* bits 15..12 for 0x2d */
9524     SYNC = 0x6,
9525     SYSCALL = 0x8,
9526     SDBBP = 0xd,
9527
9528     /* bits 15..12 for 0x35 */
9529     MFHI32 = 0x0,
9530     MFLO32 = 0x1,
9531     MTHI32 = 0x2,
9532     MTLO32 = 0x3,
9533 };
9534
9535 /* POOL32B encoding of minor opcode field (bits 15..12) */
9536
9537 enum {
9538     LWC2 = 0x0,
9539     LWP = 0x1,
9540     LDP = 0x4,
9541     LWM32 = 0x5,
9542     CACHE = 0x6,
9543     LDM = 0x7,
9544     SWC2 = 0x8,
9545     SWP = 0x9,
9546     SDP = 0xc,
9547     SWM32 = 0xd,
9548     SDM = 0xf
9549 };
9550
9551 /* POOL32C encoding of minor opcode field (bits 15..12) */
9552
9553 enum {
9554     LWL = 0x0,
9555     SWL = 0x8,
9556     LWR = 0x1,
9557     SWR = 0x9,
9558     PREF = 0x2,
9559     /* 0xa is reserved */
9560     LL = 0x3,
9561     SC = 0xb,
9562     LDL = 0x4,
9563     SDL = 0xc,
9564     LDR = 0x5,
9565     SDR = 0xd,
9566     /* 0x6 is reserved */
9567     LWU = 0xe,
9568     LLD = 0x7,
9569     SCD = 0xf
9570 };
9571
9572 /* POOL32F encoding of minor opcode field (bits 5..0) */
9573
9574 enum {
9575     /* These are the bit 7..6 values */
9576     ADD_FMT = 0x0,
9577     MOVN_FMT = 0x0,
9578
9579     SUB_FMT = 0x1,
9580     MOVZ_FMT = 0x1,
9581
9582     MUL_FMT = 0x2,
9583
9584     DIV_FMT = 0x3,
9585
9586     /* These are the bit 8..6 values */
9587     RSQRT2_FMT = 0x0,
9588     MOVF_FMT = 0x0,
9589
9590     LWXC1 = 0x1,
9591     MOVT_FMT = 0x1,
9592
9593     PLL_PS = 0x2,
9594     SWXC1 = 0x2,
9595
9596     PLU_PS = 0x3,
9597     LDXC1 = 0x3,
9598
9599     PUL_PS = 0x4,
9600     SDXC1 = 0x4,
9601     RECIP2_FMT = 0x4,
9602
9603     PUU_PS = 0x5,
9604     LUXC1 = 0x5,
9605
9606     CVT_PS_S = 0x6,
9607     SUXC1 = 0x6,
9608     ADDR_PS = 0x6,
9609     PREFX = 0x6,
9610
9611     MULR_PS = 0x7,
9612
9613     MADD_S = 0x01,
9614     MADD_D = 0x09,
9615     MADD_PS = 0x11,
9616     ALNV_PS = 0x19,
9617     MSUB_S = 0x21,
9618     MSUB_D = 0x29,
9619     MSUB_PS = 0x31,
9620
9621     NMADD_S = 0x02,
9622     NMADD_D = 0x0a,
9623     NMADD_PS = 0x12,
9624     NMSUB_S = 0x22,
9625     NMSUB_D = 0x2a,
9626     NMSUB_PS = 0x32,
9627
9628     POOL32FXF = 0x3b,
9629
9630     CABS_COND_FMT = 0x1c,              /* MIPS3D */
9631     C_COND_FMT = 0x3c
9632 };
9633
9634 /* POOL32Fxf encoding of minor opcode extension field */
9635
9636 enum {
9637     CVT_L = 0x04,
9638     RSQRT_FMT = 0x08,
9639     FLOOR_L = 0x0c,
9640     CVT_PW_PS = 0x1c,
9641     CVT_W = 0x24,
9642     SQRT_FMT = 0x28,
9643     FLOOR_W = 0x2c,
9644     CVT_PS_PW = 0x3c,
9645     CFC1 = 0x40,
9646     RECIP_FMT = 0x48,
9647     CEIL_L = 0x4c,
9648     CTC1 = 0x60,
9649     CEIL_W = 0x6c,
9650     MFC1 = 0x80,
9651     CVT_S_PL = 0x84,
9652     TRUNC_L = 0x8c,
9653     MTC1 = 0xa0,
9654     CVT_S_PU = 0xa4,
9655     TRUNC_W = 0xac,
9656     MFHC1 = 0xc0,
9657     ROUND_L = 0xcc,
9658     MTHC1 = 0xe0,
9659     ROUND_W = 0xec,
9660
9661     MOV_FMT = 0x01,
9662     MOVF = 0x05,
9663     ABS_FMT = 0x0d,
9664     RSQRT1_FMT = 0x1d,
9665     MOVT = 0x25,
9666     NEG_FMT = 0x2d,
9667     CVT_D = 0x4d,
9668     RECIP1_FMT = 0x5d,
9669     CVT_S = 0x6d
9670 };
9671
9672 /* POOL32I encoding of minor opcode field (bits 25..21) */
9673
9674 enum {
9675     BLTZ = 0x00,
9676     BLTZAL = 0x01,
9677     BGEZ = 0x02,
9678     BGEZAL = 0x03,
9679     BLEZ = 0x04,
9680     BNEZC = 0x05,
9681     BGTZ = 0x06,
9682     BEQZC = 0x07,
9683     TLTI = 0x08,
9684     TGEI = 0x09,
9685     TLTIU = 0x0a,
9686     TGEIU = 0x0b,
9687     TNEI = 0x0c,
9688     LUI = 0x0d,
9689     TEQI = 0x0e,
9690     SYNCI = 0x10,
9691     BLTZALS = 0x11,
9692     BGEZALS = 0x13,
9693     BC2F = 0x14,
9694     BC2T = 0x15,
9695     BPOSGE64 = 0x1a,
9696     BPOSGE32 = 0x1b,
9697     /* These overlap and are distinguished by bit16 of the instruction */
9698     BC1F = 0x1c,
9699     BC1T = 0x1d,
9700     BC1ANY2F = 0x1c,
9701     BC1ANY2T = 0x1d,
9702     BC1ANY4F = 0x1e,
9703     BC1ANY4T = 0x1f
9704 };
9705
9706 /* POOL16A encoding of minor opcode field */
9707
9708 enum {
9709     ADDU16 = 0x0,
9710     SUBU16 = 0x1
9711 };
9712
9713 /* POOL16B encoding of minor opcode field */
9714
9715 enum {
9716     SLL16 = 0x0,
9717     SRL16 = 0x1
9718 };
9719
9720 /* POOL16C encoding of minor opcode field */
9721
9722 enum {
9723     NOT16 = 0x00,
9724     XOR16 = 0x04,
9725     AND16 = 0x08,
9726     OR16 = 0x0c,
9727     LWM16 = 0x10,
9728     SWM16 = 0x14,
9729     JR16 = 0x18,
9730     JRC16 = 0x1a,
9731     JALR16 = 0x1c,
9732     JALR16S = 0x1e,
9733     MFHI16 = 0x20,
9734     MFLO16 = 0x24,
9735     BREAK16 = 0x28,
9736     SDBBP16 = 0x2c,
9737     JRADDIUSP = 0x30
9738 };
9739
9740 /* POOL16D encoding of minor opcode field */
9741
9742 enum {
9743     ADDIUS5 = 0x0,
9744     ADDIUSP = 0x1
9745 };
9746
9747 /* POOL16E encoding of minor opcode field */
9748
9749 enum {
9750     ADDIUR2 = 0x0,
9751     ADDIUR1SP = 0x1
9752 };
9753
9754 static int mmreg (int r)
9755 {
9756     static const int map[] = { 16, 17, 2, 3, 4, 5, 6, 7 };
9757
9758     return map[r];
9759 }
9760
9761 /* Used for 16-bit store instructions.  */
9762 static int mmreg2 (int r)
9763 {
9764     static const int map[] = { 0, 17, 2, 3, 4, 5, 6, 7 };
9765
9766     return map[r];
9767 }
9768
9769 #define uMIPS_RD(op) ((op >> 7) & 0x7)
9770 #define uMIPS_RS(op) ((op >> 4) & 0x7)
9771 #define uMIPS_RS2(op) uMIPS_RS(op)
9772 #define uMIPS_RS1(op) ((op >> 1) & 0x7)
9773 #define uMIPS_RD5(op) ((op >> 5) & 0x1f)
9774 #define uMIPS_RS5(op) (op & 0x1f)
9775
9776 /* Signed immediate */
9777 #define SIMM(op, start, width)                                          \
9778     ((int32_t)(((op >> start) & ((~0U) >> (32-width)))                 \
9779                << (32-width))                                           \
9780      >> (32-width))
9781 /* Zero-extended immediate */
9782 #define ZIMM(op, start, width) ((op >> start) & ((~0U) >> (32-width)))
9783
9784 static void gen_addiur1sp (CPUMIPSState *env, DisasContext *ctx)
9785 {
9786     int rd = mmreg(uMIPS_RD(ctx->opcode));
9787
9788     gen_arith_imm(env, ctx, OPC_ADDIU, rd, 29, ((ctx->opcode >> 1) & 0x3f) << 2);
9789 }
9790
9791 static void gen_addiur2 (CPUMIPSState *env, DisasContext *ctx)
9792 {
9793     static const int decoded_imm[] = { 1, 4, 8, 12, 16, 20, 24, -1 };
9794     int rd = mmreg(uMIPS_RD(ctx->opcode));
9795     int rs = mmreg(uMIPS_RS(ctx->opcode));
9796
9797     gen_arith_imm(env, ctx, OPC_ADDIU, rd, rs, decoded_imm[ZIMM(ctx->opcode, 1, 3)]);
9798 }
9799
9800 static void gen_addiusp (CPUMIPSState *env, DisasContext *ctx)
9801 {
9802     int encoded = ZIMM(ctx->opcode, 1, 9);
9803     int decoded;
9804
9805     if (encoded <= 1) {
9806         decoded = 256 + encoded;
9807     } else if (encoded <= 255) {
9808         decoded = encoded;
9809     } else if (encoded <= 509) {
9810         decoded = encoded - 512;
9811     } else {
9812         decoded = encoded - 768;
9813     }
9814
9815     gen_arith_imm(env, ctx, OPC_ADDIU, 29, 29, decoded << 2);
9816 }
9817
9818 static void gen_addius5 (CPUMIPSState *env, DisasContext *ctx)
9819 {
9820     int imm = SIMM(ctx->opcode, 1, 4);
9821     int rd = (ctx->opcode >> 5) & 0x1f;
9822
9823     gen_arith_imm(env, ctx, OPC_ADDIU, rd, rd, imm);
9824 }
9825
9826 static void gen_andi16 (CPUMIPSState *env, DisasContext *ctx)
9827 {
9828     static const int decoded_imm[] = { 128, 1, 2, 3, 4, 7, 8, 15, 16,
9829                                  31, 32, 63, 64, 255, 32768, 65535 };
9830     int rd = mmreg(uMIPS_RD(ctx->opcode));
9831     int rs = mmreg(uMIPS_RS(ctx->opcode));
9832     int encoded = ZIMM(ctx->opcode, 0, 4);
9833
9834     gen_logic_imm(env, OPC_ANDI, rd, rs, decoded_imm[encoded]);
9835 }
9836
9837 static void gen_ldst_multiple (DisasContext *ctx, uint32_t opc, int reglist,
9838                                int base, int16_t offset)
9839 {
9840     TCGv t0, t1;
9841     TCGv_i32 t2;
9842
9843     if (ctx->hflags & MIPS_HFLAG_BMASK) {
9844         generate_exception(ctx, EXCP_RI);
9845         return;
9846     }
9847
9848     t0 = tcg_temp_new();
9849
9850     gen_base_offset_addr(ctx, t0, base, offset);
9851
9852     t1 = tcg_const_tl(reglist);
9853     t2 = tcg_const_i32(ctx->mem_idx);
9854
9855     save_cpu_state(ctx, 1);
9856     switch (opc) {
9857     case LWM32:
9858         gen_helper_lwm(t0, t1, t2);
9859         break;
9860     case SWM32:
9861         gen_helper_swm(t0, t1, t2);
9862         break;
9863 #ifdef TARGET_MIPS64
9864     case LDM:
9865         gen_helper_ldm(t0, t1, t2);
9866         break;
9867     case SDM:
9868         gen_helper_sdm(t0, t1, t2);
9869         break;
9870 #endif
9871     }
9872     MIPS_DEBUG("%s, %x, %d(%s)", opn, reglist, offset, regnames[base]);
9873     tcg_temp_free(t0);
9874     tcg_temp_free(t1);
9875     tcg_temp_free_i32(t2);
9876 }
9877
9878
9879 static void gen_pool16c_insn (CPUMIPSState *env, DisasContext *ctx, int *is_branch)
9880 {
9881     int rd = mmreg((ctx->opcode >> 3) & 0x7);
9882     int rs = mmreg(ctx->opcode & 0x7);
9883     int opc;
9884
9885     switch (((ctx->opcode) >> 4) & 0x3f) {
9886     case NOT16 + 0:
9887     case NOT16 + 1:
9888     case NOT16 + 2:
9889     case NOT16 + 3:
9890         gen_logic(env, OPC_NOR, rd, rs, 0);
9891         break;
9892     case XOR16 + 0:
9893     case XOR16 + 1:
9894     case XOR16 + 2:
9895     case XOR16 + 3:
9896         gen_logic(env, OPC_XOR, rd, rd, rs);
9897         break;
9898     case AND16 + 0:
9899     case AND16 + 1:
9900     case AND16 + 2:
9901     case AND16 + 3:
9902         gen_logic(env, OPC_AND, rd, rd, rs);
9903         break;
9904     case OR16 + 0:
9905     case OR16 + 1:
9906     case OR16 + 2:
9907     case OR16 + 3:
9908         gen_logic(env, OPC_OR, rd, rd, rs);
9909         break;
9910     case LWM16 + 0:
9911     case LWM16 + 1:
9912     case LWM16 + 2:
9913     case LWM16 + 3:
9914         {
9915             static const int lwm_convert[] = { 0x11, 0x12, 0x13, 0x14 };
9916             int offset = ZIMM(ctx->opcode, 0, 4);
9917
9918             gen_ldst_multiple(ctx, LWM32, lwm_convert[(ctx->opcode >> 4) & 0x3],
9919                               29, offset << 2);
9920         }
9921         break;
9922     case SWM16 + 0:
9923     case SWM16 + 1:
9924     case SWM16 + 2:
9925     case SWM16 + 3:
9926         {
9927             static const int swm_convert[] = { 0x11, 0x12, 0x13, 0x14 };
9928             int offset = ZIMM(ctx->opcode, 0, 4);
9929
9930             gen_ldst_multiple(ctx, SWM32, swm_convert[(ctx->opcode >> 4) & 0x3],
9931                               29, offset << 2);
9932         }
9933         break;
9934     case JR16 + 0:
9935     case JR16 + 1:
9936         {
9937             int reg = ctx->opcode & 0x1f;
9938
9939             gen_compute_branch(ctx, OPC_JR, 2, reg, 0, 0);
9940         }
9941         *is_branch = 1;
9942         break;
9943     case JRC16 + 0:
9944     case JRC16 + 1:
9945         {
9946             int reg = ctx->opcode & 0x1f;
9947
9948             gen_compute_branch(ctx, OPC_JR, 2, reg, 0, 0);
9949             /* Let normal delay slot handling in our caller take us
9950                to the branch target.  */
9951         }
9952         break;
9953     case JALR16 + 0:
9954     case JALR16 + 1:
9955         opc = OPC_JALR;
9956         goto do_jalr;
9957     case JALR16S + 0:
9958     case JALR16S + 1:
9959         opc = OPC_JALRS;
9960     do_jalr:
9961         {
9962             int reg = ctx->opcode & 0x1f;
9963
9964             gen_compute_branch(ctx, opc, 2, reg, 31, 0);
9965         }
9966         *is_branch = 1;
9967         break;
9968     case MFHI16 + 0:
9969     case MFHI16 + 1:
9970         gen_HILO(ctx, OPC_MFHI, uMIPS_RS5(ctx->opcode));
9971         break;
9972     case MFLO16 + 0:
9973     case MFLO16 + 1:
9974         gen_HILO(ctx, OPC_MFLO, uMIPS_RS5(ctx->opcode));
9975         break;
9976     case BREAK16:
9977         generate_exception(ctx, EXCP_BREAK);
9978         break;
9979     case SDBBP16:
9980         /* XXX: not clear which exception should be raised
9981          *      when in debug mode...
9982          */
9983         check_insn(env, ctx, ISA_MIPS32);
9984         if (!(ctx->hflags & MIPS_HFLAG_DM)) {
9985             generate_exception(ctx, EXCP_DBp);
9986         } else {
9987             generate_exception(ctx, EXCP_DBp);
9988         }
9989         break;
9990     case JRADDIUSP + 0:
9991     case JRADDIUSP + 1:
9992         {
9993             int imm = ZIMM(ctx->opcode, 0, 5);
9994
9995             gen_compute_branch(ctx, OPC_JR, 2, 31, 0, 0);
9996             gen_arith_imm(env, ctx, OPC_ADDIU, 29, 29, imm << 2);
9997             /* Let normal delay slot handling in our caller take us
9998                to the branch target.  */
9999         }
10000         break;
10001     default:
10002         generate_exception(ctx, EXCP_RI);
10003         break;
10004     }
10005 }
10006
10007 static void gen_ldxs (DisasContext *ctx, int base, int index, int rd)
10008 {
10009     TCGv t0 = tcg_temp_new();
10010     TCGv t1 = tcg_temp_new();
10011
10012     gen_load_gpr(t0, base);
10013
10014     if (index != 0) {
10015         gen_load_gpr(t1, index);
10016         tcg_gen_shli_tl(t1, t1, 2);
10017         gen_op_addr_add(ctx, t0, t1, t0);
10018     }
10019
10020     save_cpu_state(ctx, 0);
10021     op_ld_lw(t1, t0, ctx);
10022     gen_store_gpr(t1, rd);
10023
10024     tcg_temp_free(t0);
10025     tcg_temp_free(t1);
10026 }
10027
10028 static void gen_ldst_pair (DisasContext *ctx, uint32_t opc, int rd,
10029                            int base, int16_t offset)
10030 {
10031     const char *opn = "ldst_pair";
10032     TCGv t0, t1;
10033
10034     if (ctx->hflags & MIPS_HFLAG_BMASK || rd == 31) {
10035         generate_exception(ctx, EXCP_RI);
10036         return;
10037     }
10038
10039     t0 = tcg_temp_new();
10040     t1 = tcg_temp_new();
10041
10042     gen_base_offset_addr(ctx, t0, base, offset);
10043
10044     switch (opc) {
10045     case LWP:
10046         if (rd == base) {
10047             generate_exception(ctx, EXCP_RI);
10048             return;
10049         }
10050         save_cpu_state(ctx, 0);
10051         op_ld_lw(t1, t0, ctx);
10052         gen_store_gpr(t1, rd);
10053         tcg_gen_movi_tl(t1, 4);
10054         gen_op_addr_add(ctx, t0, t0, t1);
10055         op_ld_lw(t1, t0, ctx);
10056         gen_store_gpr(t1, rd+1);
10057         opn = "lwp";
10058         break;
10059     case SWP:
10060         save_cpu_state(ctx, 0);
10061         gen_load_gpr(t1, rd);
10062         op_st_sw(t1, t0, ctx);
10063         tcg_gen_movi_tl(t1, 4);
10064         gen_op_addr_add(ctx, t0, t0, t1);
10065         gen_load_gpr(t1, rd+1);
10066         op_st_sw(t1, t0, ctx);
10067         opn = "swp";
10068         break;
10069 #ifdef TARGET_MIPS64
10070     case LDP:
10071         if (rd == base) {
10072             generate_exception(ctx, EXCP_RI);
10073             return;
10074         }
10075         save_cpu_state(ctx, 0);
10076         op_ld_ld(t1, t0, ctx);
10077         gen_store_gpr(t1, rd);
10078         tcg_gen_movi_tl(t1, 8);
10079         gen_op_addr_add(ctx, t0, t0, t1);
10080         op_ld_ld(t1, t0, ctx);
10081         gen_store_gpr(t1, rd+1);
10082         opn = "ldp";
10083         break;
10084     case SDP:
10085         save_cpu_state(ctx, 0);
10086         gen_load_gpr(t1, rd);
10087         op_st_sd(t1, t0, ctx);
10088         tcg_gen_movi_tl(t1, 8);
10089         gen_op_addr_add(ctx, t0, t0, t1);
10090         gen_load_gpr(t1, rd+1);
10091         op_st_sd(t1, t0, ctx);
10092         opn = "sdp";
10093         break;
10094 #endif
10095     }
10096     (void)opn; /* avoid a compiler warning */
10097     MIPS_DEBUG("%s, %s, %d(%s)", opn, regnames[rd], offset, regnames[base]);
10098     tcg_temp_free(t0);
10099     tcg_temp_free(t1);
10100 }
10101
10102 static void gen_pool32axf (CPUMIPSState *env, DisasContext *ctx, int rt, int rs,
10103                            int *is_branch)
10104 {
10105     int extension = (ctx->opcode >> 6) & 0x3f;
10106     int minor = (ctx->opcode >> 12) & 0xf;
10107     uint32_t mips32_op;
10108
10109     switch (extension) {
10110     case TEQ:
10111         mips32_op = OPC_TEQ;
10112         goto do_trap;
10113     case TGE:
10114         mips32_op = OPC_TGE;
10115         goto do_trap;
10116     case TGEU:
10117         mips32_op = OPC_TGEU;
10118         goto do_trap;
10119     case TLT:
10120         mips32_op = OPC_TLT;
10121         goto do_trap;
10122     case TLTU:
10123         mips32_op = OPC_TLTU;
10124         goto do_trap;
10125     case TNE:
10126         mips32_op = OPC_TNE;
10127     do_trap:
10128         gen_trap(ctx, mips32_op, rs, rt, -1);
10129         break;
10130 #ifndef CONFIG_USER_ONLY
10131     case MFC0:
10132     case MFC0 + 32:
10133         check_cp0_enabled(ctx);
10134         if (rt == 0) {
10135             /* Treat as NOP. */
10136             break;
10137         }
10138         gen_mfc0(env, ctx, cpu_gpr[rt], rs, (ctx->opcode >> 11) & 0x7);
10139         break;
10140     case MTC0:
10141     case MTC0 + 32:
10142         check_cp0_enabled(ctx);
10143         {
10144             TCGv t0 = tcg_temp_new();
10145
10146             gen_load_gpr(t0, rt);
10147             gen_mtc0(env, ctx, t0, rs, (ctx->opcode >> 11) & 0x7);
10148             tcg_temp_free(t0);
10149         }
10150         break;
10151 #endif
10152     case 0x2c:
10153         switch (minor) {
10154         case SEB:
10155             gen_bshfl(ctx, OPC_SEB, rs, rt);
10156             break;
10157         case SEH:
10158             gen_bshfl(ctx, OPC_SEH, rs, rt);
10159             break;
10160         case CLO:
10161             mips32_op = OPC_CLO;
10162             goto do_cl;
10163         case CLZ:
10164             mips32_op = OPC_CLZ;
10165         do_cl:
10166             check_insn(env, ctx, ISA_MIPS32);
10167             gen_cl(ctx, mips32_op, rt, rs);
10168             break;
10169         case RDHWR:
10170             gen_rdhwr(env, ctx, rt, rs);
10171             break;
10172         case WSBH:
10173             gen_bshfl(ctx, OPC_WSBH, rs, rt);
10174             break;
10175         case MULT:
10176             mips32_op = OPC_MULT;
10177             goto do_muldiv;
10178         case MULTU:
10179             mips32_op = OPC_MULTU;
10180             goto do_muldiv;
10181         case DIV:
10182             mips32_op = OPC_DIV;
10183             goto do_muldiv;
10184         case DIVU:
10185             mips32_op = OPC_DIVU;
10186             goto do_muldiv;
10187         case MADD:
10188             mips32_op = OPC_MADD;
10189             goto do_muldiv;
10190         case MADDU:
10191             mips32_op = OPC_MADDU;
10192             goto do_muldiv;
10193         case MSUB:
10194             mips32_op = OPC_MSUB;
10195             goto do_muldiv;
10196         case MSUBU:
10197             mips32_op = OPC_MSUBU;
10198         do_muldiv:
10199             check_insn(env, ctx, ISA_MIPS32);
10200             gen_muldiv(ctx, mips32_op, rs, rt);
10201             break;
10202         default:
10203             goto pool32axf_invalid;
10204         }
10205         break;
10206     case 0x34:
10207         switch (minor) {
10208         case MFC2:
10209         case MTC2:
10210         case MFHC2:
10211         case MTHC2:
10212         case CFC2:
10213         case CTC2:
10214             generate_exception_err(ctx, EXCP_CpU, 2);
10215             break;
10216         default:
10217             goto pool32axf_invalid;
10218         }
10219         break;
10220     case 0x3c:
10221         switch (minor) {
10222         case JALR:
10223         case JALR_HB:
10224             gen_compute_branch (ctx, OPC_JALR, 4, rs, rt, 0);
10225             *is_branch = 1;
10226             break;
10227         case JALRS:
10228         case JALRS_HB:
10229             gen_compute_branch (ctx, OPC_JALRS, 4, rs, rt, 0);
10230             *is_branch = 1;
10231             break;
10232         default:
10233             goto pool32axf_invalid;
10234         }
10235         break;
10236     case 0x05:
10237         switch (minor) {
10238         case RDPGPR:
10239             check_cp0_enabled(ctx);
10240             check_insn(env, ctx, ISA_MIPS32R2);
10241             gen_load_srsgpr(rt, rs);
10242             break;
10243         case WRPGPR:
10244             check_cp0_enabled(ctx);
10245             check_insn(env, ctx, ISA_MIPS32R2);
10246             gen_store_srsgpr(rt, rs);
10247             break;
10248         default:
10249             goto pool32axf_invalid;
10250         }
10251         break;
10252 #ifndef CONFIG_USER_ONLY
10253     case 0x0d:
10254         switch (minor) {
10255         case TLBP:
10256             mips32_op = OPC_TLBP;
10257             goto do_cp0;
10258         case TLBR:
10259             mips32_op = OPC_TLBR;
10260             goto do_cp0;
10261         case TLBWI:
10262             mips32_op = OPC_TLBWI;
10263             goto do_cp0;
10264         case TLBWR:
10265             mips32_op = OPC_TLBWR;
10266             goto do_cp0;
10267         case WAIT:
10268             mips32_op = OPC_WAIT;
10269             goto do_cp0;
10270         case DERET:
10271             mips32_op = OPC_DERET;
10272             goto do_cp0;
10273         case ERET:
10274             mips32_op = OPC_ERET;
10275         do_cp0:
10276             gen_cp0(env, ctx, mips32_op, rt, rs);
10277             break;
10278         default:
10279             goto pool32axf_invalid;
10280         }
10281         break;
10282     case 0x1d:
10283         switch (minor) {
10284         case DI:
10285             check_cp0_enabled(ctx);
10286             {
10287                 TCGv t0 = tcg_temp_new();
10288
10289                 save_cpu_state(ctx, 1);
10290                 gen_helper_di(t0);
10291                 gen_store_gpr(t0, rs);
10292                 /* Stop translation as we may have switched the execution mode */
10293                 ctx->bstate = BS_STOP;
10294                 tcg_temp_free(t0);
10295             }
10296             break;
10297         case EI:
10298             check_cp0_enabled(ctx);
10299             {
10300                 TCGv t0 = tcg_temp_new();
10301
10302                 save_cpu_state(ctx, 1);
10303                 gen_helper_ei(t0);
10304                 gen_store_gpr(t0, rs);
10305                 /* Stop translation as we may have switched the execution mode */
10306                 ctx->bstate = BS_STOP;
10307                 tcg_temp_free(t0);
10308             }
10309             break;
10310         default:
10311             goto pool32axf_invalid;
10312         }
10313         break;
10314 #endif
10315     case 0x2d:
10316         switch (minor) {
10317         case SYNC:
10318             /* NOP */
10319             break;
10320         case SYSCALL:
10321             generate_exception(ctx, EXCP_SYSCALL);
10322             ctx->bstate = BS_STOP;
10323             break;
10324         case SDBBP:
10325             check_insn(env, ctx, ISA_MIPS32);
10326             if (!(ctx->hflags & MIPS_HFLAG_DM)) {
10327                 generate_exception(ctx, EXCP_DBp);
10328             } else {
10329                 generate_exception(ctx, EXCP_DBp);
10330             }
10331             break;
10332         default:
10333             goto pool32axf_invalid;
10334         }
10335         break;
10336     case 0x35:
10337         switch (minor) {
10338         case MFHI32:
10339             gen_HILO(ctx, OPC_MFHI, rs);
10340             break;
10341         case MFLO32:
10342             gen_HILO(ctx, OPC_MFLO, rs);
10343             break;
10344         case MTHI32:
10345             gen_HILO(ctx, OPC_MTHI, rs);
10346             break;
10347         case MTLO32:
10348             gen_HILO(ctx, OPC_MTLO, rs);
10349             break;
10350         default:
10351             goto pool32axf_invalid;
10352         }
10353         break;
10354     default:
10355     pool32axf_invalid:
10356         MIPS_INVAL("pool32axf");
10357         generate_exception(ctx, EXCP_RI);
10358         break;
10359     }
10360 }
10361
10362 /* Values for microMIPS fmt field.  Variable-width, depending on which
10363    formats the instruction supports.  */
10364
10365 enum {
10366     FMT_SD_S = 0,
10367     FMT_SD_D = 1,
10368
10369     FMT_SDPS_S = 0,
10370     FMT_SDPS_D = 1,
10371     FMT_SDPS_PS = 2,
10372
10373     FMT_SWL_S = 0,
10374     FMT_SWL_W = 1,
10375     FMT_SWL_L = 2,
10376
10377     FMT_DWL_D = 0,
10378     FMT_DWL_W = 1,
10379     FMT_DWL_L = 2
10380 };
10381
10382 static void gen_pool32fxf (CPUMIPSState *env, DisasContext *ctx, int rt, int rs)
10383 {
10384     int extension = (ctx->opcode >> 6) & 0x3ff;
10385     uint32_t mips32_op;
10386
10387 #define FLOAT_1BIT_FMT(opc, fmt) (fmt << 8) | opc
10388 #define FLOAT_2BIT_FMT(opc, fmt) (fmt << 7) | opc
10389 #define COND_FLOAT_MOV(opc, cond) (cond << 7) | opc
10390
10391     switch (extension) {
10392     case FLOAT_1BIT_FMT(CFC1, 0):
10393         mips32_op = OPC_CFC1;
10394         goto do_cp1;
10395     case FLOAT_1BIT_FMT(CTC1, 0):
10396         mips32_op = OPC_CTC1;
10397         goto do_cp1;
10398     case FLOAT_1BIT_FMT(MFC1, 0):
10399         mips32_op = OPC_MFC1;
10400         goto do_cp1;
10401     case FLOAT_1BIT_FMT(MTC1, 0):
10402         mips32_op = OPC_MTC1;
10403         goto do_cp1;
10404     case FLOAT_1BIT_FMT(MFHC1, 0):
10405         mips32_op = OPC_MFHC1;
10406         goto do_cp1;
10407     case FLOAT_1BIT_FMT(MTHC1, 0):
10408         mips32_op = OPC_MTHC1;
10409     do_cp1:
10410         gen_cp1(ctx, mips32_op, rt, rs);
10411         break;
10412
10413         /* Reciprocal square root */
10414     case FLOAT_1BIT_FMT(RSQRT_FMT, FMT_SD_S):
10415         mips32_op = OPC_RSQRT_S;
10416         goto do_unaryfp;
10417     case FLOAT_1BIT_FMT(RSQRT_FMT, FMT_SD_D):
10418         mips32_op = OPC_RSQRT_D;
10419         goto do_unaryfp;
10420
10421         /* Square root */
10422     case FLOAT_1BIT_FMT(SQRT_FMT, FMT_SD_S):
10423         mips32_op = OPC_SQRT_S;
10424         goto do_unaryfp;
10425     case FLOAT_1BIT_FMT(SQRT_FMT, FMT_SD_D):
10426         mips32_op = OPC_SQRT_D;
10427         goto do_unaryfp;
10428
10429         /* Reciprocal */
10430     case FLOAT_1BIT_FMT(RECIP_FMT, FMT_SD_S):
10431         mips32_op = OPC_RECIP_S;
10432         goto do_unaryfp;
10433     case FLOAT_1BIT_FMT(RECIP_FMT, FMT_SD_D):
10434         mips32_op = OPC_RECIP_D;
10435         goto do_unaryfp;
10436
10437         /* Floor */
10438     case FLOAT_1BIT_FMT(FLOOR_L, FMT_SD_S):
10439         mips32_op = OPC_FLOOR_L_S;
10440         goto do_unaryfp;
10441     case FLOAT_1BIT_FMT(FLOOR_L, FMT_SD_D):
10442         mips32_op = OPC_FLOOR_L_D;
10443         goto do_unaryfp;
10444     case FLOAT_1BIT_FMT(FLOOR_W, FMT_SD_S):
10445         mips32_op = OPC_FLOOR_W_S;
10446         goto do_unaryfp;
10447     case FLOAT_1BIT_FMT(FLOOR_W, FMT_SD_D):
10448         mips32_op = OPC_FLOOR_W_D;
10449         goto do_unaryfp;
10450
10451         /* Ceiling */
10452     case FLOAT_1BIT_FMT(CEIL_L, FMT_SD_S):
10453         mips32_op = OPC_CEIL_L_S;
10454         goto do_unaryfp;
10455     case FLOAT_1BIT_FMT(CEIL_L, FMT_SD_D):
10456         mips32_op = OPC_CEIL_L_D;
10457         goto do_unaryfp;
10458     case FLOAT_1BIT_FMT(CEIL_W, FMT_SD_S):
10459         mips32_op = OPC_CEIL_W_S;
10460         goto do_unaryfp;
10461     case FLOAT_1BIT_FMT(CEIL_W, FMT_SD_D):
10462         mips32_op = OPC_CEIL_W_D;
10463         goto do_unaryfp;
10464
10465         /* Truncation */
10466     case FLOAT_1BIT_FMT(TRUNC_L, FMT_SD_S):
10467         mips32_op = OPC_TRUNC_L_S;
10468         goto do_unaryfp;
10469     case FLOAT_1BIT_FMT(TRUNC_L, FMT_SD_D):
10470         mips32_op = OPC_TRUNC_L_D;
10471         goto do_unaryfp;
10472     case FLOAT_1BIT_FMT(TRUNC_W, FMT_SD_S):
10473         mips32_op = OPC_TRUNC_W_S;
10474         goto do_unaryfp;
10475     case FLOAT_1BIT_FMT(TRUNC_W, FMT_SD_D):
10476         mips32_op = OPC_TRUNC_W_D;
10477         goto do_unaryfp;
10478
10479         /* Round */
10480     case FLOAT_1BIT_FMT(ROUND_L, FMT_SD_S):
10481         mips32_op = OPC_ROUND_L_S;
10482         goto do_unaryfp;
10483     case FLOAT_1BIT_FMT(ROUND_L, FMT_SD_D):
10484         mips32_op = OPC_ROUND_L_D;
10485         goto do_unaryfp;
10486     case FLOAT_1BIT_FMT(ROUND_W, FMT_SD_S):
10487         mips32_op = OPC_ROUND_W_S;
10488         goto do_unaryfp;
10489     case FLOAT_1BIT_FMT(ROUND_W, FMT_SD_D):
10490         mips32_op = OPC_ROUND_W_D;
10491         goto do_unaryfp;
10492
10493         /* Integer to floating-point conversion */
10494     case FLOAT_1BIT_FMT(CVT_L, FMT_SD_S):
10495         mips32_op = OPC_CVT_L_S;
10496         goto do_unaryfp;
10497     case FLOAT_1BIT_FMT(CVT_L, FMT_SD_D):
10498         mips32_op = OPC_CVT_L_D;
10499         goto do_unaryfp;
10500     case FLOAT_1BIT_FMT(CVT_W, FMT_SD_S):
10501         mips32_op = OPC_CVT_W_S;
10502         goto do_unaryfp;
10503     case FLOAT_1BIT_FMT(CVT_W, FMT_SD_D):
10504         mips32_op = OPC_CVT_W_D;
10505         goto do_unaryfp;
10506
10507         /* Paired-foo conversions */
10508     case FLOAT_1BIT_FMT(CVT_S_PL, 0):
10509         mips32_op = OPC_CVT_S_PL;
10510         goto do_unaryfp;
10511     case FLOAT_1BIT_FMT(CVT_S_PU, 0):
10512         mips32_op = OPC_CVT_S_PU;
10513         goto do_unaryfp;
10514     case FLOAT_1BIT_FMT(CVT_PW_PS, 0):
10515         mips32_op = OPC_CVT_PW_PS;
10516         goto do_unaryfp;
10517     case FLOAT_1BIT_FMT(CVT_PS_PW, 0):
10518         mips32_op = OPC_CVT_PS_PW;
10519         goto do_unaryfp;
10520
10521         /* Floating-point moves */
10522     case FLOAT_2BIT_FMT(MOV_FMT, FMT_SDPS_S):
10523         mips32_op = OPC_MOV_S;
10524         goto do_unaryfp;
10525     case FLOAT_2BIT_FMT(MOV_FMT, FMT_SDPS_D):
10526         mips32_op = OPC_MOV_D;
10527         goto do_unaryfp;
10528     case FLOAT_2BIT_FMT(MOV_FMT, FMT_SDPS_PS):
10529         mips32_op = OPC_MOV_PS;
10530         goto do_unaryfp;
10531
10532         /* Absolute value */
10533     case FLOAT_2BIT_FMT(ABS_FMT, FMT_SDPS_S):
10534         mips32_op = OPC_ABS_S;
10535         goto do_unaryfp;
10536     case FLOAT_2BIT_FMT(ABS_FMT, FMT_SDPS_D):
10537         mips32_op = OPC_ABS_D;
10538         goto do_unaryfp;
10539     case FLOAT_2BIT_FMT(ABS_FMT, FMT_SDPS_PS):
10540         mips32_op = OPC_ABS_PS;
10541         goto do_unaryfp;
10542
10543         /* Negation */
10544     case FLOAT_2BIT_FMT(NEG_FMT, FMT_SDPS_S):
10545         mips32_op = OPC_NEG_S;
10546         goto do_unaryfp;
10547     case FLOAT_2BIT_FMT(NEG_FMT, FMT_SDPS_D):
10548         mips32_op = OPC_NEG_D;
10549         goto do_unaryfp;
10550     case FLOAT_2BIT_FMT(NEG_FMT, FMT_SDPS_PS):
10551         mips32_op = OPC_NEG_PS;
10552         goto do_unaryfp;
10553
10554         /* Reciprocal square root step */
10555     case FLOAT_2BIT_FMT(RSQRT1_FMT, FMT_SDPS_S):
10556         mips32_op = OPC_RSQRT1_S;
10557         goto do_unaryfp;
10558     case FLOAT_2BIT_FMT(RSQRT1_FMT, FMT_SDPS_D):
10559         mips32_op = OPC_RSQRT1_D;
10560         goto do_unaryfp;
10561     case FLOAT_2BIT_FMT(RSQRT1_FMT, FMT_SDPS_PS):
10562         mips32_op = OPC_RSQRT1_PS;
10563         goto do_unaryfp;
10564
10565         /* Reciprocal step */
10566     case FLOAT_2BIT_FMT(RECIP1_FMT, FMT_SDPS_S):
10567         mips32_op = OPC_RECIP1_S;
10568         goto do_unaryfp;
10569     case FLOAT_2BIT_FMT(RECIP1_FMT, FMT_SDPS_D):
10570         mips32_op = OPC_RECIP1_S;
10571         goto do_unaryfp;
10572     case FLOAT_2BIT_FMT(RECIP1_FMT, FMT_SDPS_PS):
10573         mips32_op = OPC_RECIP1_PS;
10574         goto do_unaryfp;
10575
10576         /* Conversions from double */
10577     case FLOAT_2BIT_FMT(CVT_D, FMT_SWL_S):
10578         mips32_op = OPC_CVT_D_S;
10579         goto do_unaryfp;
10580     case FLOAT_2BIT_FMT(CVT_D, FMT_SWL_W):
10581         mips32_op = OPC_CVT_D_W;
10582         goto do_unaryfp;
10583     case FLOAT_2BIT_FMT(CVT_D, FMT_SWL_L):
10584         mips32_op = OPC_CVT_D_L;
10585         goto do_unaryfp;
10586
10587         /* Conversions from single */
10588     case FLOAT_2BIT_FMT(CVT_S, FMT_DWL_D):
10589         mips32_op = OPC_CVT_S_D;
10590         goto do_unaryfp;
10591     case FLOAT_2BIT_FMT(CVT_S, FMT_DWL_W):
10592         mips32_op = OPC_CVT_S_W;
10593         goto do_unaryfp;
10594     case FLOAT_2BIT_FMT(CVT_S, FMT_DWL_L):
10595         mips32_op = OPC_CVT_S_L;
10596     do_unaryfp:
10597         gen_farith(ctx, mips32_op, -1, rs, rt, 0);
10598         break;
10599
10600         /* Conditional moves on floating-point codes */
10601     case COND_FLOAT_MOV(MOVT, 0):
10602     case COND_FLOAT_MOV(MOVT, 1):
10603     case COND_FLOAT_MOV(MOVT, 2):
10604     case COND_FLOAT_MOV(MOVT, 3):
10605     case COND_FLOAT_MOV(MOVT, 4):
10606     case COND_FLOAT_MOV(MOVT, 5):
10607     case COND_FLOAT_MOV(MOVT, 6):
10608     case COND_FLOAT_MOV(MOVT, 7):
10609         gen_movci(ctx, rt, rs, (ctx->opcode >> 13) & 0x7, 1);
10610         break;
10611     case COND_FLOAT_MOV(MOVF, 0):
10612     case COND_FLOAT_MOV(MOVF, 1):
10613     case COND_FLOAT_MOV(MOVF, 2):
10614     case COND_FLOAT_MOV(MOVF, 3):
10615     case COND_FLOAT_MOV(MOVF, 4):
10616     case COND_FLOAT_MOV(MOVF, 5):
10617     case COND_FLOAT_MOV(MOVF, 6):
10618     case COND_FLOAT_MOV(MOVF, 7):
10619         gen_movci(ctx, rt, rs, (ctx->opcode >> 13) & 0x7, 0);
10620         break;
10621     default:
10622         MIPS_INVAL("pool32fxf");
10623         generate_exception(ctx, EXCP_RI);
10624         break;
10625     }
10626 }
10627
10628 static void decode_micromips32_opc (CPUMIPSState *env, DisasContext *ctx,
10629                                     uint16_t insn_hw1, int *is_branch)
10630 {
10631     int32_t offset;
10632     uint16_t insn;
10633     int rt, rs, rd, rr;
10634     int16_t imm;
10635     uint32_t op, minor, mips32_op;
10636     uint32_t cond, fmt, cc;
10637
10638     insn = lduw_code(ctx->pc + 2);
10639     ctx->opcode = (ctx->opcode << 16) | insn;
10640
10641     rt = (ctx->opcode >> 21) & 0x1f;
10642     rs = (ctx->opcode >> 16) & 0x1f;
10643     rd = (ctx->opcode >> 11) & 0x1f;
10644     rr = (ctx->opcode >> 6) & 0x1f;
10645     imm = (int16_t) ctx->opcode;
10646
10647     op = (ctx->opcode >> 26) & 0x3f;
10648     switch (op) {
10649     case POOL32A:
10650         minor = ctx->opcode & 0x3f;
10651         switch (minor) {
10652         case 0x00:
10653             minor = (ctx->opcode >> 6) & 0xf;
10654             switch (minor) {
10655             case SLL32:
10656                 mips32_op = OPC_SLL;
10657                 goto do_shifti;
10658             case SRA:
10659                 mips32_op = OPC_SRA;
10660                 goto do_shifti;
10661             case SRL32:
10662                 mips32_op = OPC_SRL;
10663                 goto do_shifti;
10664             case ROTR:
10665                 mips32_op = OPC_ROTR;
10666             do_shifti:
10667                 gen_shift_imm(env, ctx, mips32_op, rt, rs, rd);
10668                 break;
10669             default:
10670                 goto pool32a_invalid;
10671             }
10672             break;
10673         case 0x10:
10674             minor = (ctx->opcode >> 6) & 0xf;
10675             switch (minor) {
10676                 /* Arithmetic */
10677             case ADD:
10678                 mips32_op = OPC_ADD;
10679                 goto do_arith;
10680             case ADDU32:
10681                 mips32_op = OPC_ADDU;
10682                 goto do_arith;
10683             case SUB:
10684                 mips32_op = OPC_SUB;
10685                 goto do_arith;
10686             case SUBU32:
10687                 mips32_op = OPC_SUBU;
10688                 goto do_arith;
10689             case MUL:
10690                 mips32_op = OPC_MUL;
10691             do_arith:
10692                 gen_arith(env, ctx, mips32_op, rd, rs, rt);
10693                 break;
10694                 /* Shifts */
10695             case SLLV:
10696                 mips32_op = OPC_SLLV;
10697                 goto do_shift;
10698             case SRLV:
10699                 mips32_op = OPC_SRLV;
10700                 goto do_shift;
10701             case SRAV:
10702                 mips32_op = OPC_SRAV;
10703                 goto do_shift;
10704             case ROTRV:
10705                 mips32_op = OPC_ROTRV;
10706             do_shift:
10707                 gen_shift(env, ctx, mips32_op, rd, rs, rt);
10708                 break;
10709                 /* Logical operations */
10710             case AND:
10711                 mips32_op = OPC_AND;
10712                 goto do_logic;
10713             case OR32:
10714                 mips32_op = OPC_OR;
10715                 goto do_logic;
10716             case NOR:
10717                 mips32_op = OPC_NOR;
10718                 goto do_logic;
10719             case XOR32:
10720                 mips32_op = OPC_XOR;
10721             do_logic:
10722                 gen_logic(env, mips32_op, rd, rs, rt);
10723                 break;
10724                 /* Set less than */
10725             case SLT:
10726                 mips32_op = OPC_SLT;
10727                 goto do_slt;
10728             case SLTU:
10729                 mips32_op = OPC_SLTU;
10730             do_slt:
10731                 gen_slt(env, mips32_op, rd, rs, rt);
10732                 break;
10733             default:
10734                 goto pool32a_invalid;
10735             }
10736             break;
10737         case 0x18:
10738             minor = (ctx->opcode >> 6) & 0xf;
10739             switch (minor) {
10740                 /* Conditional moves */
10741             case MOVN:
10742                 mips32_op = OPC_MOVN;
10743                 goto do_cmov;
10744             case MOVZ:
10745                 mips32_op = OPC_MOVZ;
10746             do_cmov:
10747                 gen_cond_move(env, mips32_op, rd, rs, rt);
10748                 break;
10749             case LWXS:
10750                 gen_ldxs(ctx, rs, rt, rd);
10751                 break;
10752             default:
10753                 goto pool32a_invalid;
10754             }
10755             break;
10756         case INS:
10757             gen_bitops(ctx, OPC_INS, rt, rs, rr, rd);
10758             return;
10759         case EXT:
10760             gen_bitops(ctx, OPC_EXT, rt, rs, rr, rd);
10761             return;
10762         case POOL32AXF:
10763             gen_pool32axf(env, ctx, rt, rs, is_branch);
10764             break;
10765         case 0x07:
10766             generate_exception(ctx, EXCP_BREAK);
10767             break;
10768         default:
10769         pool32a_invalid:
10770                 MIPS_INVAL("pool32a");
10771                 generate_exception(ctx, EXCP_RI);
10772                 break;
10773         }
10774         break;
10775     case POOL32B:
10776         minor = (ctx->opcode >> 12) & 0xf;
10777         switch (minor) {
10778         case CACHE:
10779             check_cp0_enabled(ctx);
10780             /* Treat as no-op. */
10781             break;
10782         case LWC2:
10783         case SWC2:
10784             /* COP2: Not implemented. */
10785             generate_exception_err(ctx, EXCP_CpU, 2);
10786             break;
10787         case LWP:
10788         case SWP:
10789 #ifdef TARGET_MIPS64
10790         case LDP:
10791         case SDP:
10792 #endif
10793             gen_ldst_pair(ctx, minor, rt, rs, SIMM(ctx->opcode, 0, 12));
10794             break;
10795         case LWM32:
10796         case SWM32:
10797 #ifdef TARGET_MIPS64
10798         case LDM:
10799         case SDM:
10800 #endif
10801             gen_ldst_multiple(ctx, minor, rt, rs, SIMM(ctx->opcode, 0, 12));
10802             break;
10803         default:
10804             MIPS_INVAL("pool32b");
10805             generate_exception(ctx, EXCP_RI);
10806             break;
10807         }
10808         break;
10809     case POOL32F:
10810         if (env->CP0_Config1 & (1 << CP0C1_FP)) {
10811             minor = ctx->opcode & 0x3f;
10812             check_cp1_enabled(ctx);
10813             switch (minor) {
10814             case ALNV_PS:
10815                 mips32_op = OPC_ALNV_PS;
10816                 goto do_madd;
10817             case MADD_S:
10818                 mips32_op = OPC_MADD_S;
10819                 goto do_madd;
10820             case MADD_D:
10821                 mips32_op = OPC_MADD_D;
10822                 goto do_madd;
10823             case MADD_PS:
10824                 mips32_op = OPC_MADD_PS;
10825                 goto do_madd;
10826             case MSUB_S:
10827                 mips32_op = OPC_MSUB_S;
10828                 goto do_madd;
10829             case MSUB_D:
10830                 mips32_op = OPC_MSUB_D;
10831                 goto do_madd;
10832             case MSUB_PS:
10833                 mips32_op = OPC_MSUB_PS;
10834                 goto do_madd;
10835             case NMADD_S:
10836                 mips32_op = OPC_NMADD_S;
10837                 goto do_madd;
10838             case NMADD_D:
10839                 mips32_op = OPC_NMADD_D;
10840                 goto do_madd;
10841             case NMADD_PS:
10842                 mips32_op = OPC_NMADD_PS;
10843                 goto do_madd;
10844             case NMSUB_S:
10845                 mips32_op = OPC_NMSUB_S;
10846                 goto do_madd;
10847             case NMSUB_D:
10848                 mips32_op = OPC_NMSUB_D;
10849                 goto do_madd;
10850             case NMSUB_PS:
10851                 mips32_op = OPC_NMSUB_PS;
10852             do_madd:
10853                 gen_flt3_arith(ctx, mips32_op, rd, rr, rs, rt);
10854                 break;
10855             case CABS_COND_FMT:
10856                 cond = (ctx->opcode >> 6) & 0xf;
10857                 cc = (ctx->opcode >> 13) & 0x7;
10858                 fmt = (ctx->opcode >> 10) & 0x3;
10859                 switch (fmt) {
10860                 case 0x0:
10861                     gen_cmpabs_s(ctx, cond, rt, rs, cc);
10862                     break;
10863                 case 0x1:
10864                     gen_cmpabs_d(ctx, cond, rt, rs, cc);
10865                     break;
10866                 case 0x2:
10867                     gen_cmpabs_ps(ctx, cond, rt, rs, cc);
10868                     break;
10869                 default:
10870                     goto pool32f_invalid;
10871                 }
10872                 break;
10873             case C_COND_FMT:
10874                 cond = (ctx->opcode >> 6) & 0xf;
10875                 cc = (ctx->opcode >> 13) & 0x7;
10876                 fmt = (ctx->opcode >> 10) & 0x3;
10877                 switch (fmt) {
10878                 case 0x0:
10879                     gen_cmp_s(ctx, cond, rt, rs, cc);
10880                     break;
10881                 case 0x1:
10882                     gen_cmp_d(ctx, cond, rt, rs, cc);
10883                     break;
10884                 case 0x2:
10885                     gen_cmp_ps(ctx, cond, rt, rs, cc);
10886                     break;
10887                 default:
10888                     goto pool32f_invalid;
10889                 }
10890                 break;
10891             case POOL32FXF:
10892                 gen_pool32fxf(env, ctx, rt, rs);
10893                 break;
10894             case 0x00:
10895                 /* PLL foo */
10896                 switch ((ctx->opcode >> 6) & 0x7) {
10897                 case PLL_PS:
10898                     mips32_op = OPC_PLL_PS;
10899                     goto do_ps;
10900                 case PLU_PS:
10901                     mips32_op = OPC_PLU_PS;
10902                     goto do_ps;
10903                 case PUL_PS:
10904                     mips32_op = OPC_PUL_PS;
10905                     goto do_ps;
10906                 case PUU_PS:
10907                     mips32_op = OPC_PUU_PS;
10908                     goto do_ps;
10909                 case CVT_PS_S:
10910                     mips32_op = OPC_CVT_PS_S;
10911                 do_ps:
10912                     gen_farith(ctx, mips32_op, rt, rs, rd, 0);
10913                     break;
10914                 default:
10915                     goto pool32f_invalid;
10916                 }
10917                 break;
10918             case 0x08:
10919                 /* [LS][WDU]XC1 */
10920                 switch ((ctx->opcode >> 6) & 0x7) {
10921                 case LWXC1:
10922                     mips32_op = OPC_LWXC1;
10923                     goto do_ldst_cp1;
10924                 case SWXC1:
10925                     mips32_op = OPC_SWXC1;
10926                     goto do_ldst_cp1;
10927                 case LDXC1:
10928                     mips32_op = OPC_LDXC1;
10929                     goto do_ldst_cp1;
10930                 case SDXC1:
10931                     mips32_op = OPC_SDXC1;
10932                     goto do_ldst_cp1;
10933                 case LUXC1:
10934                     mips32_op = OPC_LUXC1;
10935                     goto do_ldst_cp1;
10936                 case SUXC1:
10937                     mips32_op = OPC_SUXC1;
10938                 do_ldst_cp1:
10939                     gen_flt3_ldst(ctx, mips32_op, rd, rd, rt, rs);
10940                     break;
10941                 default:
10942                     goto pool32f_invalid;
10943                 }
10944                 break;
10945             case 0x18:
10946                 /* 3D insns */
10947                 fmt = (ctx->opcode >> 9) & 0x3;
10948                 switch ((ctx->opcode >> 6) & 0x7) {
10949                 case RSQRT2_FMT:
10950                     switch (fmt) {
10951                     case FMT_SDPS_S:
10952                         mips32_op = OPC_RSQRT2_S;
10953                         goto do_3d;
10954                     case FMT_SDPS_D:
10955                         mips32_op = OPC_RSQRT2_D;
10956                         goto do_3d;
10957                     case FMT_SDPS_PS:
10958                         mips32_op = OPC_RSQRT2_PS;
10959                         goto do_3d;
10960                     default:
10961                         goto pool32f_invalid;
10962                     }
10963                     break;
10964                 case RECIP2_FMT:
10965                     switch (fmt) {
10966                     case FMT_SDPS_S:
10967                         mips32_op = OPC_RECIP2_S;
10968                         goto do_3d;
10969                     case FMT_SDPS_D:
10970                         mips32_op = OPC_RECIP2_D;
10971                         goto do_3d;
10972                     case FMT_SDPS_PS:
10973                         mips32_op = OPC_RECIP2_PS;
10974                         goto do_3d;
10975                     default:
10976                         goto pool32f_invalid;
10977                     }
10978                     break;
10979                 case ADDR_PS:
10980                     mips32_op = OPC_ADDR_PS;
10981                     goto do_3d;
10982                 case MULR_PS:
10983                     mips32_op = OPC_MULR_PS;
10984                 do_3d:
10985                     gen_farith(ctx, mips32_op, rt, rs, rd, 0);
10986                     break;
10987                 default:
10988                     goto pool32f_invalid;
10989                 }
10990                 break;
10991             case 0x20:
10992                 /* MOV[FT].fmt and PREFX */
10993                 cc = (ctx->opcode >> 13) & 0x7;
10994                 fmt = (ctx->opcode >> 9) & 0x3;
10995                 switch ((ctx->opcode >> 6) & 0x7) {
10996                 case MOVF_FMT:
10997                     switch (fmt) {
10998                     case FMT_SDPS_S:
10999                         gen_movcf_s(rs, rt, cc, 0);
11000                         break;
11001                     case FMT_SDPS_D:
11002                         gen_movcf_d(ctx, rs, rt, cc, 0);
11003                         break;
11004                     case FMT_SDPS_PS:
11005                         gen_movcf_ps(rs, rt, cc, 0);
11006                         break;
11007                     default:
11008                         goto pool32f_invalid;
11009                     }
11010                     break;
11011                 case MOVT_FMT:
11012                     switch (fmt) {
11013                     case FMT_SDPS_S:
11014                         gen_movcf_s(rs, rt, cc, 1);
11015                         break;
11016                     case FMT_SDPS_D:
11017                         gen_movcf_d(ctx, rs, rt, cc, 1);
11018                         break;
11019                     case FMT_SDPS_PS:
11020                         gen_movcf_ps(rs, rt, cc, 1);
11021                         break;
11022                     default:
11023                         goto pool32f_invalid;
11024                     }
11025                     break;
11026                 case PREFX:
11027                     break;
11028                 default:
11029                     goto pool32f_invalid;
11030                 }
11031                 break;
11032 #define FINSN_3ARG_SDPS(prfx)                           \
11033                 switch ((ctx->opcode >> 8) & 0x3) {     \
11034                 case FMT_SDPS_S:                        \
11035                     mips32_op = OPC_##prfx##_S;         \
11036                     goto do_fpop;                       \
11037                 case FMT_SDPS_D:                        \
11038                     mips32_op = OPC_##prfx##_D;         \
11039                     goto do_fpop;                       \
11040                 case FMT_SDPS_PS:                       \
11041                     mips32_op = OPC_##prfx##_PS;        \
11042                     goto do_fpop;                       \
11043                 default:                                \
11044                     goto pool32f_invalid;               \
11045                 }
11046             case 0x30:
11047                 /* regular FP ops */
11048                 switch ((ctx->opcode >> 6) & 0x3) {
11049                 case ADD_FMT:
11050                     FINSN_3ARG_SDPS(ADD);
11051                     break;
11052                 case SUB_FMT:
11053                     FINSN_3ARG_SDPS(SUB);
11054                     break;
11055                 case MUL_FMT:
11056                     FINSN_3ARG_SDPS(MUL);
11057                     break;
11058                 case DIV_FMT:
11059                     fmt = (ctx->opcode >> 8) & 0x3;
11060                     if (fmt == 1) {
11061                         mips32_op = OPC_DIV_D;
11062                     } else if (fmt == 0) {
11063                         mips32_op = OPC_DIV_S;
11064                     } else {
11065                         goto pool32f_invalid;
11066                     }
11067                     goto do_fpop;
11068                 default:
11069                     goto pool32f_invalid;
11070                 }
11071                 break;
11072             case 0x38:
11073                 /* cmovs */
11074                 switch ((ctx->opcode >> 6) & 0x3) {
11075                 case MOVN_FMT:
11076                     FINSN_3ARG_SDPS(MOVN);
11077                     break;
11078                 case MOVZ_FMT:
11079                     FINSN_3ARG_SDPS(MOVZ);
11080                     break;
11081                 default:
11082                     goto pool32f_invalid;
11083                 }
11084                 break;
11085             do_fpop:
11086                 gen_farith(ctx, mips32_op, rt, rs, rd, 0);
11087                 break;
11088             default:
11089             pool32f_invalid:
11090                 MIPS_INVAL("pool32f");
11091                 generate_exception(ctx, EXCP_RI);
11092                 break;
11093             }
11094         } else {
11095             generate_exception_err(ctx, EXCP_CpU, 1);
11096         }
11097         break;
11098     case POOL32I:
11099         minor = (ctx->opcode >> 21) & 0x1f;
11100         switch (minor) {
11101         case BLTZ:
11102             mips32_op = OPC_BLTZ;
11103             goto do_branch;
11104         case BLTZAL:
11105             mips32_op = OPC_BLTZAL;
11106             goto do_branch;
11107         case BLTZALS:
11108             mips32_op = OPC_BLTZALS;
11109             goto do_branch;
11110         case BGEZ:
11111             mips32_op = OPC_BGEZ;
11112             goto do_branch;
11113         case BGEZAL:
11114             mips32_op = OPC_BGEZAL;
11115             goto do_branch;
11116         case BGEZALS:
11117             mips32_op = OPC_BGEZALS;
11118             goto do_branch;
11119         case BLEZ:
11120             mips32_op = OPC_BLEZ;
11121             goto do_branch;
11122         case BGTZ:
11123             mips32_op = OPC_BGTZ;
11124         do_branch:
11125             gen_compute_branch(ctx, mips32_op, 4, rs, -1, imm << 1);
11126             *is_branch = 1;
11127             break;
11128
11129             /* Traps */
11130         case TLTI:
11131             mips32_op = OPC_TLTI;
11132             goto do_trapi;
11133         case TGEI:
11134             mips32_op = OPC_TGEI;
11135             goto do_trapi;
11136         case TLTIU:
11137             mips32_op = OPC_TLTIU;
11138             goto do_trapi;
11139         case TGEIU:
11140             mips32_op = OPC_TGEIU;
11141             goto do_trapi;
11142         case TNEI:
11143             mips32_op = OPC_TNEI;
11144             goto do_trapi;
11145         case TEQI:
11146             mips32_op = OPC_TEQI;
11147         do_trapi:
11148             gen_trap(ctx, mips32_op, rs, -1, imm);
11149             break;
11150
11151         case BNEZC:
11152         case BEQZC:
11153             gen_compute_branch(ctx, minor == BNEZC ? OPC_BNE : OPC_BEQ,
11154                                4, rs, 0, imm << 1);
11155             /* Compact branches don't have a delay slot, so just let
11156                the normal delay slot handling take us to the branch
11157                target. */
11158             break;
11159         case LUI:
11160             gen_logic_imm(env, OPC_LUI, rs, -1, imm);
11161             break;
11162         case SYNCI:
11163             break;
11164         case BC2F:
11165         case BC2T:
11166             /* COP2: Not implemented. */
11167             generate_exception_err(ctx, EXCP_CpU, 2);
11168             break;
11169         case BC1F:
11170             mips32_op = (ctx->opcode & (1 << 16)) ? OPC_BC1FANY2 : OPC_BC1F;
11171             goto do_cp1branch;
11172         case BC1T:
11173             mips32_op = (ctx->opcode & (1 << 16)) ? OPC_BC1TANY2 : OPC_BC1T;
11174             goto do_cp1branch;
11175         case BC1ANY4F:
11176             mips32_op = OPC_BC1FANY4;
11177             goto do_cp1mips3d;
11178         case BC1ANY4T:
11179             mips32_op = OPC_BC1TANY4;
11180         do_cp1mips3d:
11181             check_cop1x(ctx);
11182             check_insn(env, ctx, ASE_MIPS3D);
11183             /* Fall through */
11184         do_cp1branch:
11185             gen_compute_branch1(env, ctx, mips32_op,
11186                                 (ctx->opcode >> 18) & 0x7, imm << 1);
11187             *is_branch = 1;
11188             break;
11189         case BPOSGE64:
11190         case BPOSGE32:
11191             /* MIPS DSP: not implemented */
11192             /* Fall through */
11193         default:
11194             MIPS_INVAL("pool32i");
11195             generate_exception(ctx, EXCP_RI);
11196             break;
11197         }
11198         break;
11199     case POOL32C:
11200         minor = (ctx->opcode >> 12) & 0xf;
11201         switch (minor) {
11202         case LWL:
11203             mips32_op = OPC_LWL;
11204             goto do_ld_lr;
11205         case SWL:
11206             mips32_op = OPC_SWL;
11207             goto do_st_lr;
11208         case LWR:
11209             mips32_op = OPC_LWR;
11210             goto do_ld_lr;
11211         case SWR:
11212             mips32_op = OPC_SWR;
11213             goto do_st_lr;
11214 #if defined(TARGET_MIPS64)
11215         case LDL:
11216             mips32_op = OPC_LDL;
11217             goto do_ld_lr;
11218         case SDL:
11219             mips32_op = OPC_SDL;
11220             goto do_st_lr;
11221         case LDR:
11222             mips32_op = OPC_LDR;
11223             goto do_ld_lr;
11224         case SDR:
11225             mips32_op = OPC_SDR;
11226             goto do_st_lr;
11227         case LWU:
11228             mips32_op = OPC_LWU;
11229             goto do_ld_lr;
11230         case LLD:
11231             mips32_op = OPC_LLD;
11232             goto do_ld_lr;
11233 #endif
11234         case LL:
11235             mips32_op = OPC_LL;
11236             goto do_ld_lr;
11237         do_ld_lr:
11238             gen_ld(env, ctx, mips32_op, rt, rs, SIMM(ctx->opcode, 0, 12));
11239             break;
11240         do_st_lr:
11241             gen_st(ctx, mips32_op, rt, rs, SIMM(ctx->opcode, 0, 12));
11242             break;
11243         case SC:
11244             gen_st_cond(ctx, OPC_SC, rt, rs, SIMM(ctx->opcode, 0, 12));
11245             break;
11246 #if defined(TARGET_MIPS64)
11247         case SCD:
11248             gen_st_cond(ctx, OPC_SCD, rt, rs, SIMM(ctx->opcode, 0, 12));
11249             break;
11250 #endif
11251         case PREF:
11252             /* Treat as no-op */
11253             break;
11254         default:
11255             MIPS_INVAL("pool32c");
11256             generate_exception(ctx, EXCP_RI);
11257             break;
11258         }
11259         break;
11260     case ADDI32:
11261         mips32_op = OPC_ADDI;
11262         goto do_addi;
11263     case ADDIU32:
11264         mips32_op = OPC_ADDIU;
11265     do_addi:
11266         gen_arith_imm(env, ctx, mips32_op, rt, rs, imm);
11267         break;
11268
11269         /* Logical operations */
11270     case ORI32:
11271         mips32_op = OPC_ORI;
11272         goto do_logici;
11273     case XORI32:
11274         mips32_op = OPC_XORI;
11275         goto do_logici;
11276     case ANDI32:
11277         mips32_op = OPC_ANDI;
11278     do_logici:
11279         gen_logic_imm(env, mips32_op, rt, rs, imm);
11280         break;
11281
11282         /* Set less than immediate */
11283     case SLTI32:
11284         mips32_op = OPC_SLTI;
11285         goto do_slti;
11286     case SLTIU32:
11287         mips32_op = OPC_SLTIU;
11288     do_slti:
11289         gen_slt_imm(env, mips32_op, rt, rs, imm);
11290         break;
11291     case JALX32:
11292         offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
11293         gen_compute_branch(ctx, OPC_JALX, 4, rt, rs, offset);
11294         *is_branch = 1;
11295         break;
11296     case JALS32:
11297         offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 1;
11298         gen_compute_branch(ctx, OPC_JALS, 4, rt, rs, offset);
11299         *is_branch = 1;
11300         break;
11301     case BEQ32:
11302         gen_compute_branch(ctx, OPC_BEQ, 4, rt, rs, imm << 1);
11303         *is_branch = 1;
11304         break;
11305     case BNE32:
11306         gen_compute_branch(ctx, OPC_BNE, 4, rt, rs, imm << 1);
11307         *is_branch = 1;
11308         break;
11309     case J32:
11310         gen_compute_branch(ctx, OPC_J, 4, rt, rs,
11311                            (int32_t)(ctx->opcode & 0x3FFFFFF) << 1);
11312         *is_branch = 1;
11313         break;
11314     case JAL32:
11315         gen_compute_branch(ctx, OPC_JAL, 4, rt, rs,
11316                            (int32_t)(ctx->opcode & 0x3FFFFFF) << 1);
11317         *is_branch = 1;
11318         break;
11319         /* Floating point (COP1) */
11320     case LWC132:
11321         mips32_op = OPC_LWC1;
11322         goto do_cop1;
11323     case LDC132:
11324         mips32_op = OPC_LDC1;
11325         goto do_cop1;
11326     case SWC132:
11327         mips32_op = OPC_SWC1;
11328         goto do_cop1;
11329     case SDC132:
11330         mips32_op = OPC_SDC1;
11331     do_cop1:
11332         gen_cop1_ldst(env, ctx, mips32_op, rt, rs, imm);
11333         break;
11334     case ADDIUPC:
11335         {
11336             int reg = mmreg(ZIMM(ctx->opcode, 23, 3));
11337             int offset = SIMM(ctx->opcode, 0, 23) << 2;
11338
11339             gen_addiupc(ctx, reg, offset, 0, 0);
11340         }
11341         break;
11342         /* Loads and stores */
11343     case LB32:
11344         mips32_op = OPC_LB;
11345         goto do_ld;
11346     case LBU32:
11347         mips32_op = OPC_LBU;
11348         goto do_ld;
11349     case LH32:
11350         mips32_op = OPC_LH;
11351         goto do_ld;
11352     case LHU32:
11353         mips32_op = OPC_LHU;
11354         goto do_ld;
11355     case LW32:
11356         mips32_op = OPC_LW;
11357         goto do_ld;
11358 #ifdef TARGET_MIPS64
11359     case LD32:
11360         mips32_op = OPC_LD;
11361         goto do_ld;
11362     case SD32:
11363         mips32_op = OPC_SD;
11364         goto do_st;
11365 #endif
11366     case SB32:
11367         mips32_op = OPC_SB;
11368         goto do_st;
11369     case SH32:
11370         mips32_op = OPC_SH;
11371         goto do_st;
11372     case SW32:
11373         mips32_op = OPC_SW;
11374         goto do_st;
11375     do_ld:
11376         gen_ld(env, ctx, mips32_op, rt, rs, imm);
11377         break;
11378     do_st:
11379         gen_st(ctx, mips32_op, rt, rs, imm);
11380         break;
11381     default:
11382         generate_exception(ctx, EXCP_RI);
11383         break;
11384     }
11385 }
11386
11387 static int decode_micromips_opc (CPUMIPSState *env, DisasContext *ctx, int *is_branch)
11388 {
11389     uint32_t op;
11390
11391     /* make sure instructions are on a halfword boundary */
11392     if (ctx->pc & 0x1) {
11393         env->CP0_BadVAddr = ctx->pc;
11394         generate_exception(ctx, EXCP_AdEL);
11395         ctx->bstate = BS_STOP;
11396         return 2;
11397     }
11398
11399     op = (ctx->opcode >> 10) & 0x3f;
11400     /* Enforce properly-sized instructions in a delay slot */
11401     if (ctx->hflags & MIPS_HFLAG_BMASK) {
11402         int bits = ctx->hflags & MIPS_HFLAG_BMASK_EXT;
11403
11404         switch (op) {
11405         case POOL32A:
11406         case POOL32B:
11407         case POOL32I:
11408         case POOL32C:
11409         case ADDI32:
11410         case ADDIU32:
11411         case ORI32:
11412         case XORI32:
11413         case SLTI32:
11414         case SLTIU32:
11415         case ANDI32:
11416         case JALX32:
11417         case LBU32:
11418         case LHU32:
11419         case POOL32F:
11420         case JALS32:
11421         case BEQ32:
11422         case BNE32:
11423         case J32:
11424         case JAL32:
11425         case SB32:
11426         case SH32:
11427         case POOL32S:
11428         case ADDIUPC:
11429         case SWC132:
11430         case SDC132:
11431         case SD32:
11432         case SW32:
11433         case LB32:
11434         case LH32:
11435         case DADDIU32:
11436         case POOL48A:           /* ??? */
11437         case LWC132:
11438         case LDC132:
11439         case LD32:
11440         case LW32:
11441             if (bits & MIPS_HFLAG_BDS16) {
11442                 generate_exception(ctx, EXCP_RI);
11443                 /* Just stop translation; the user is confused.  */
11444                 ctx->bstate = BS_STOP;
11445                 return 2;
11446             }
11447             break;
11448         case POOL16A:
11449         case POOL16B:
11450         case POOL16C:
11451         case LWGP16:
11452         case POOL16F:
11453         case LBU16:
11454         case LHU16:
11455         case LWSP16:
11456         case LW16:
11457         case SB16:
11458         case SH16:
11459         case SWSP16:
11460         case SW16:
11461         case MOVE16:
11462         case ANDI16:
11463         case POOL16D:
11464         case POOL16E:
11465         case BEQZ16:
11466         case BNEZ16:
11467         case B16:
11468         case LI16:
11469             if (bits & MIPS_HFLAG_BDS32) {
11470                 generate_exception(ctx, EXCP_RI);
11471                 /* Just stop translation; the user is confused.  */
11472                 ctx->bstate = BS_STOP;
11473                 return 2;
11474             }
11475             break;
11476         default:
11477             break;
11478         }
11479     }
11480     switch (op) {
11481     case POOL16A:
11482         {
11483             int rd = mmreg(uMIPS_RD(ctx->opcode));
11484             int rs1 = mmreg(uMIPS_RS1(ctx->opcode));
11485             int rs2 = mmreg(uMIPS_RS2(ctx->opcode));
11486             uint32_t opc = 0;
11487
11488             switch (ctx->opcode & 0x1) {
11489             case ADDU16:
11490                 opc = OPC_ADDU;
11491                 break;
11492             case SUBU16:
11493                 opc = OPC_SUBU;
11494                 break;
11495             }
11496
11497             gen_arith(env, ctx, opc, rd, rs1, rs2);
11498         }
11499         break;
11500     case POOL16B:
11501         {
11502             int rd = mmreg(uMIPS_RD(ctx->opcode));
11503             int rs = mmreg(uMIPS_RS(ctx->opcode));
11504             int amount = (ctx->opcode >> 1) & 0x7;
11505             uint32_t opc = 0;
11506             amount = amount == 0 ? 8 : amount;
11507
11508             switch (ctx->opcode & 0x1) {
11509             case SLL16:
11510                 opc = OPC_SLL;
11511                 break;
11512             case SRL16:
11513                 opc = OPC_SRL;
11514                 break;
11515             }
11516
11517             gen_shift_imm(env, ctx, opc, rd, rs, amount);
11518         }
11519         break;
11520     case POOL16C:
11521         gen_pool16c_insn(env, ctx, is_branch);
11522         break;
11523     case LWGP16:
11524         {
11525             int rd = mmreg(uMIPS_RD(ctx->opcode));
11526             int rb = 28;            /* GP */
11527             int16_t offset = SIMM(ctx->opcode, 0, 7) << 2;
11528
11529             gen_ld(env, ctx, OPC_LW, rd, rb, offset);
11530         }
11531         break;
11532     case POOL16F:
11533         if (ctx->opcode & 1) {
11534             generate_exception(ctx, EXCP_RI);
11535         } else {
11536             /* MOVEP */
11537             int enc_dest = uMIPS_RD(ctx->opcode);
11538             int enc_rt = uMIPS_RS2(ctx->opcode);
11539             int enc_rs = uMIPS_RS1(ctx->opcode);
11540             int rd, rs, re, rt;
11541             static const int rd_enc[] = { 5, 5, 6, 4, 4, 4, 4, 4 };
11542             static const int re_enc[] = { 6, 7, 7, 21, 22, 5, 6, 7 };
11543             static const int rs_rt_enc[] = { 0, 17, 2, 3, 16, 18, 19, 20 };
11544
11545             rd = rd_enc[enc_dest];
11546             re = re_enc[enc_dest];
11547             rs = rs_rt_enc[enc_rs];
11548             rt = rs_rt_enc[enc_rt];
11549
11550             gen_arith_imm(env, ctx, OPC_ADDIU, rd, rs, 0);
11551             gen_arith_imm(env, ctx, OPC_ADDIU, re, rt, 0);
11552         }
11553         break;
11554     case LBU16:
11555         {
11556             int rd = mmreg(uMIPS_RD(ctx->opcode));
11557             int rb = mmreg(uMIPS_RS(ctx->opcode));
11558             int16_t offset = ZIMM(ctx->opcode, 0, 4);
11559             offset = (offset == 0xf ? -1 : offset);
11560
11561             gen_ld(env, ctx, OPC_LBU, rd, rb, offset);
11562         }
11563         break;
11564     case LHU16:
11565         {
11566             int rd = mmreg(uMIPS_RD(ctx->opcode));
11567             int rb = mmreg(uMIPS_RS(ctx->opcode));
11568             int16_t offset = ZIMM(ctx->opcode, 0, 4) << 1;
11569
11570             gen_ld(env, ctx, OPC_LHU, rd, rb, offset);
11571         }
11572         break;
11573     case LWSP16:
11574         {
11575             int rd = (ctx->opcode >> 5) & 0x1f;
11576             int rb = 29;            /* SP */
11577             int16_t offset = ZIMM(ctx->opcode, 0, 5) << 2;
11578
11579             gen_ld(env, ctx, OPC_LW, rd, rb, offset);
11580         }
11581         break;
11582     case LW16:
11583         {
11584             int rd = mmreg(uMIPS_RD(ctx->opcode));
11585             int rb = mmreg(uMIPS_RS(ctx->opcode));
11586             int16_t offset = ZIMM(ctx->opcode, 0, 4) << 2;
11587
11588             gen_ld(env, ctx, OPC_LW, rd, rb, offset);
11589         }
11590         break;
11591     case SB16:
11592         {
11593             int rd = mmreg2(uMIPS_RD(ctx->opcode));
11594             int rb = mmreg(uMIPS_RS(ctx->opcode));
11595             int16_t offset = ZIMM(ctx->opcode, 0, 4);
11596
11597             gen_st(ctx, OPC_SB, rd, rb, offset);
11598         }
11599         break;
11600     case SH16:
11601         {
11602             int rd = mmreg2(uMIPS_RD(ctx->opcode));
11603             int rb = mmreg(uMIPS_RS(ctx->opcode));
11604             int16_t offset = ZIMM(ctx->opcode, 0, 4) << 1;
11605
11606             gen_st(ctx, OPC_SH, rd, rb, offset);
11607         }
11608         break;
11609     case SWSP16:
11610         {
11611             int rd = (ctx->opcode >> 5) & 0x1f;
11612             int rb = 29;            /* SP */
11613             int16_t offset = ZIMM(ctx->opcode, 0, 5) << 2;
11614
11615             gen_st(ctx, OPC_SW, rd, rb, offset);
11616         }
11617         break;
11618     case SW16:
11619         {
11620             int rd = mmreg2(uMIPS_RD(ctx->opcode));
11621             int rb = mmreg(uMIPS_RS(ctx->opcode));
11622             int16_t offset = ZIMM(ctx->opcode, 0, 4) << 2;
11623
11624             gen_st(ctx, OPC_SW, rd, rb, offset);
11625         }
11626         break;
11627     case MOVE16:
11628         {
11629             int rd = uMIPS_RD5(ctx->opcode);
11630             int rs = uMIPS_RS5(ctx->opcode);
11631
11632             gen_arith_imm(env, ctx, OPC_ADDIU, rd, rs, 0);
11633         }
11634         break;
11635     case ANDI16:
11636         gen_andi16(env, ctx);
11637         break;
11638     case POOL16D:
11639         switch (ctx->opcode & 0x1) {
11640         case ADDIUS5:
11641             gen_addius5(env, ctx);
11642             break;
11643         case ADDIUSP:
11644             gen_addiusp(env, ctx);
11645             break;
11646         }
11647         break;
11648     case POOL16E:
11649         switch (ctx->opcode & 0x1) {
11650         case ADDIUR2:
11651             gen_addiur2(env, ctx);
11652             break;
11653         case ADDIUR1SP:
11654             gen_addiur1sp(env, ctx);
11655             break;
11656         }
11657         break;
11658     case B16:
11659         gen_compute_branch(ctx, OPC_BEQ, 2, 0, 0,
11660                            SIMM(ctx->opcode, 0, 10) << 1);
11661         *is_branch = 1;
11662         break;
11663     case BNEZ16:
11664     case BEQZ16:
11665         gen_compute_branch(ctx, op == BNEZ16 ? OPC_BNE : OPC_BEQ, 2,
11666                            mmreg(uMIPS_RD(ctx->opcode)),
11667                            0, SIMM(ctx->opcode, 0, 7) << 1);
11668         *is_branch = 1;
11669         break;
11670     case LI16:
11671         {
11672             int reg = mmreg(uMIPS_RD(ctx->opcode));
11673             int imm = ZIMM(ctx->opcode, 0, 7);
11674
11675             imm = (imm == 0x7f ? -1 : imm);
11676             tcg_gen_movi_tl(cpu_gpr[reg], imm);
11677         }
11678         break;
11679     case RES_20:
11680     case RES_28:
11681     case RES_29:
11682     case RES_30:
11683     case RES_31:
11684     case RES_38:
11685     case RES_39:
11686         generate_exception(ctx, EXCP_RI);
11687         break;
11688     default:
11689         decode_micromips32_opc (env, ctx, op, is_branch);
11690         return 4;
11691     }
11692
11693     return 2;
11694 }
11695
11696 /* SmartMIPS extension to MIPS32 */
11697
11698 #if defined(TARGET_MIPS64)
11699
11700 /* MDMX extension to MIPS64 */
11701
11702 #endif
11703
11704 static void decode_opc (CPUMIPSState *env, DisasContext *ctx, int *is_branch)
11705 {
11706     int32_t offset;
11707     int rs, rt, rd, sa;
11708     uint32_t op, op1, op2;
11709     int16_t imm;
11710
11711     /* make sure instructions are on a word boundary */
11712     if (ctx->pc & 0x3) {
11713         env->CP0_BadVAddr = ctx->pc;
11714         generate_exception(ctx, EXCP_AdEL);
11715         return;
11716     }
11717
11718     /* Handle blikely not taken case */
11719     if ((ctx->hflags & MIPS_HFLAG_BMASK_BASE) == MIPS_HFLAG_BL) {
11720         int l1 = gen_new_label();
11721
11722         MIPS_DEBUG("blikely condition (" TARGET_FMT_lx ")", ctx->pc + 4);
11723         tcg_gen_brcondi_tl(TCG_COND_NE, bcond, 0, l1);
11724         tcg_gen_movi_i32(hflags, ctx->hflags & ~MIPS_HFLAG_BMASK);
11725         gen_goto_tb(ctx, 1, ctx->pc + 4);
11726         gen_set_label(l1);
11727     }
11728
11729     if (unlikely(qemu_loglevel_mask(CPU_LOG_TB_OP)))
11730         tcg_gen_debug_insn_start(ctx->pc);
11731
11732     op = MASK_OP_MAJOR(ctx->opcode);
11733     rs = (ctx->opcode >> 21) & 0x1f;
11734     rt = (ctx->opcode >> 16) & 0x1f;
11735     rd = (ctx->opcode >> 11) & 0x1f;
11736     sa = (ctx->opcode >> 6) & 0x1f;
11737     imm = (int16_t)ctx->opcode;
11738     switch (op) {
11739     case OPC_SPECIAL:
11740         op1 = MASK_SPECIAL(ctx->opcode);
11741         switch (op1) {
11742         case OPC_SLL:          /* Shift with immediate */
11743         case OPC_SRA:
11744             gen_shift_imm(env, ctx, op1, rd, rt, sa);
11745             break;
11746         case OPC_SRL:
11747             switch ((ctx->opcode >> 21) & 0x1f) {
11748             case 1:
11749                 /* rotr is decoded as srl on non-R2 CPUs */
11750                 if (env->insn_flags & ISA_MIPS32R2) {
11751                     op1 = OPC_ROTR;
11752                 }
11753                 /* Fallthrough */
11754             case 0:
11755                 gen_shift_imm(env, ctx, op1, rd, rt, sa);
11756                 break;
11757             default:
11758                 generate_exception(ctx, EXCP_RI);
11759                 break;
11760             }
11761             break;
11762         case OPC_MOVN:         /* Conditional move */
11763         case OPC_MOVZ:
11764             check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32 |
11765                                  INSN_LOONGSON2E | INSN_LOONGSON2F);
11766             gen_cond_move(env, op1, rd, rs, rt);
11767             break;
11768         case OPC_ADD ... OPC_SUBU:
11769             gen_arith(env, ctx, op1, rd, rs, rt);
11770             break;
11771         case OPC_SLLV:         /* Shifts */
11772         case OPC_SRAV:
11773             gen_shift(env, ctx, op1, rd, rs, rt);
11774             break;
11775         case OPC_SRLV:
11776             switch ((ctx->opcode >> 6) & 0x1f) {
11777             case 1:
11778                 /* rotrv is decoded as srlv on non-R2 CPUs */
11779                 if (env->insn_flags & ISA_MIPS32R2) {
11780                     op1 = OPC_ROTRV;
11781                 }
11782                 /* Fallthrough */
11783             case 0:
11784                 gen_shift(env, ctx, op1, rd, rs, rt);
11785                 break;
11786             default:
11787                 generate_exception(ctx, EXCP_RI);
11788                 break;
11789             }
11790             break;
11791         case OPC_SLT:          /* Set on less than */
11792         case OPC_SLTU:
11793             gen_slt(env, op1, rd, rs, rt);
11794             break;
11795         case OPC_AND:          /* Logic*/
11796         case OPC_OR:
11797         case OPC_NOR:
11798         case OPC_XOR:
11799             gen_logic(env, op1, rd, rs, rt);
11800             break;
11801         case OPC_MULT ... OPC_DIVU:
11802             if (sa) {
11803                 check_insn(env, ctx, INSN_VR54XX);
11804                 op1 = MASK_MUL_VR54XX(ctx->opcode);
11805                 gen_mul_vr54xx(ctx, op1, rd, rs, rt);
11806             } else
11807                 gen_muldiv(ctx, op1, rs, rt);
11808             break;
11809         case OPC_JR ... OPC_JALR:
11810             gen_compute_branch(ctx, op1, 4, rs, rd, sa);
11811             *is_branch = 1;
11812             break;
11813         case OPC_TGE ... OPC_TEQ: /* Traps */
11814         case OPC_TNE:
11815             gen_trap(ctx, op1, rs, rt, -1);
11816             break;
11817         case OPC_MFHI:          /* Move from HI/LO */
11818         case OPC_MFLO:
11819             gen_HILO(ctx, op1, rd);
11820             break;
11821         case OPC_MTHI:
11822         case OPC_MTLO:          /* Move to HI/LO */
11823             gen_HILO(ctx, op1, rs);
11824             break;
11825         case OPC_PMON:          /* Pmon entry point, also R4010 selsl */
11826 #ifdef MIPS_STRICT_STANDARD
11827             MIPS_INVAL("PMON / selsl");
11828             generate_exception(ctx, EXCP_RI);
11829 #else
11830             gen_helper_0i(pmon, sa);
11831 #endif
11832             break;
11833         case OPC_SYSCALL:
11834             generate_exception(ctx, EXCP_SYSCALL);
11835             ctx->bstate = BS_STOP;
11836             break;
11837         case OPC_BREAK:
11838             generate_exception(ctx, EXCP_BREAK);
11839             break;
11840         case OPC_SPIM:
11841 #ifdef MIPS_STRICT_STANDARD
11842             MIPS_INVAL("SPIM");
11843             generate_exception(ctx, EXCP_RI);
11844 #else
11845            /* Implemented as RI exception for now. */
11846             MIPS_INVAL("spim (unofficial)");
11847             generate_exception(ctx, EXCP_RI);
11848 #endif
11849             break;
11850         case OPC_SYNC:
11851             /* Treat as NOP. */
11852             break;
11853
11854         case OPC_MOVCI:
11855             check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
11856             if (env->CP0_Config1 & (1 << CP0C1_FP)) {
11857                 check_cp1_enabled(ctx);
11858                 gen_movci(ctx, rd, rs, (ctx->opcode >> 18) & 0x7,
11859                           (ctx->opcode >> 16) & 1);
11860             } else {
11861                 generate_exception_err(ctx, EXCP_CpU, 1);
11862             }
11863             break;
11864
11865 #if defined(TARGET_MIPS64)
11866        /* MIPS64 specific opcodes */
11867         case OPC_DSLL:
11868         case OPC_DSRA:
11869         case OPC_DSLL32:
11870         case OPC_DSRA32:
11871             check_insn(env, ctx, ISA_MIPS3);
11872             check_mips_64(ctx);
11873             gen_shift_imm(env, ctx, op1, rd, rt, sa);
11874             break;
11875         case OPC_DSRL:
11876             switch ((ctx->opcode >> 21) & 0x1f) {
11877             case 1:
11878                 /* drotr is decoded as dsrl on non-R2 CPUs */
11879                 if (env->insn_flags & ISA_MIPS32R2) {
11880                     op1 = OPC_DROTR;
11881                 }
11882                 /* Fallthrough */
11883             case 0:
11884                 check_insn(env, ctx, ISA_MIPS3);
11885                 check_mips_64(ctx);
11886                 gen_shift_imm(env, ctx, op1, rd, rt, sa);
11887                 break;
11888             default:
11889                 generate_exception(ctx, EXCP_RI);
11890                 break;
11891             }
11892             break;
11893         case OPC_DSRL32:
11894             switch ((ctx->opcode >> 21) & 0x1f) {
11895             case 1:
11896                 /* drotr32 is decoded as dsrl32 on non-R2 CPUs */
11897                 if (env->insn_flags & ISA_MIPS32R2) {
11898                     op1 = OPC_DROTR32;
11899                 }
11900                 /* Fallthrough */
11901             case 0:
11902                 check_insn(env, ctx, ISA_MIPS3);
11903                 check_mips_64(ctx);
11904                 gen_shift_imm(env, ctx, op1, rd, rt, sa);
11905                 break;
11906             default:
11907                 generate_exception(ctx, EXCP_RI);
11908                 break;
11909             }
11910             break;
11911         case OPC_DADD ... OPC_DSUBU:
11912             check_insn(env, ctx, ISA_MIPS3);
11913             check_mips_64(ctx);
11914             gen_arith(env, ctx, op1, rd, rs, rt);
11915             break;
11916         case OPC_DSLLV:
11917         case OPC_DSRAV:
11918             check_insn(env, ctx, ISA_MIPS3);
11919             check_mips_64(ctx);
11920             gen_shift(env, ctx, op1, rd, rs, rt);
11921             break;
11922         case OPC_DSRLV:
11923             switch ((ctx->opcode >> 6) & 0x1f) {
11924             case 1:
11925                 /* drotrv is decoded as dsrlv on non-R2 CPUs */
11926                 if (env->insn_flags & ISA_MIPS32R2) {
11927                     op1 = OPC_DROTRV;
11928                 }
11929                 /* Fallthrough */
11930             case 0:
11931                 check_insn(env, ctx, ISA_MIPS3);
11932                 check_mips_64(ctx);
11933                 gen_shift(env, ctx, op1, rd, rs, rt);
11934                 break;
11935             default:
11936                 generate_exception(ctx, EXCP_RI);
11937                 break;
11938             }
11939             break;
11940         case OPC_DMULT ... OPC_DDIVU:
11941             check_insn(env, ctx, ISA_MIPS3);
11942             check_mips_64(ctx);
11943             gen_muldiv(ctx, op1, rs, rt);
11944             break;
11945 #endif
11946         default:            /* Invalid */
11947             MIPS_INVAL("special");
11948             generate_exception(ctx, EXCP_RI);
11949             break;
11950         }
11951         break;
11952     case OPC_SPECIAL2:
11953         op1 = MASK_SPECIAL2(ctx->opcode);
11954         switch (op1) {
11955         case OPC_MADD ... OPC_MADDU: /* Multiply and add/sub */
11956         case OPC_MSUB ... OPC_MSUBU:
11957             check_insn(env, ctx, ISA_MIPS32);
11958             gen_muldiv(ctx, op1, rs, rt);
11959             break;
11960         case OPC_MUL:
11961             gen_arith(env, ctx, op1, rd, rs, rt);
11962             break;
11963         case OPC_CLO:
11964         case OPC_CLZ:
11965             check_insn(env, ctx, ISA_MIPS32);
11966             gen_cl(ctx, op1, rd, rs);
11967             break;
11968         case OPC_SDBBP:
11969             /* XXX: not clear which exception should be raised
11970              *      when in debug mode...
11971              */
11972             check_insn(env, ctx, ISA_MIPS32);
11973             if (!(ctx->hflags & MIPS_HFLAG_DM)) {
11974                 generate_exception(ctx, EXCP_DBp);
11975             } else {
11976                 generate_exception(ctx, EXCP_DBp);
11977             }
11978             /* Treat as NOP. */
11979             break;
11980         case OPC_DIV_G_2F:
11981         case OPC_DIVU_G_2F:
11982         case OPC_MULT_G_2F:
11983         case OPC_MULTU_G_2F:
11984         case OPC_MOD_G_2F:
11985         case OPC_MODU_G_2F:
11986             check_insn(env, ctx, INSN_LOONGSON2F);
11987             gen_loongson_integer(ctx, op1, rd, rs, rt);
11988             break;
11989 #if defined(TARGET_MIPS64)
11990         case OPC_DCLO:
11991         case OPC_DCLZ:
11992             check_insn(env, ctx, ISA_MIPS64);
11993             check_mips_64(ctx);
11994             gen_cl(ctx, op1, rd, rs);
11995             break;
11996         case OPC_DMULT_G_2F:
11997         case OPC_DMULTU_G_2F:
11998         case OPC_DDIV_G_2F:
11999         case OPC_DDIVU_G_2F:
12000         case OPC_DMOD_G_2F:
12001         case OPC_DMODU_G_2F:
12002             check_insn(env, ctx, INSN_LOONGSON2F);
12003             gen_loongson_integer(ctx, op1, rd, rs, rt);
12004             break;
12005 #endif
12006         default:            /* Invalid */
12007             MIPS_INVAL("special2");
12008             generate_exception(ctx, EXCP_RI);
12009             break;
12010         }
12011         break;
12012     case OPC_SPECIAL3:
12013         op1 = MASK_SPECIAL3(ctx->opcode);
12014         switch (op1) {
12015         case OPC_EXT:
12016         case OPC_INS:
12017             check_insn(env, ctx, ISA_MIPS32R2);
12018             gen_bitops(ctx, op1, rt, rs, sa, rd);
12019             break;
12020         case OPC_BSHFL:
12021             check_insn(env, ctx, ISA_MIPS32R2);
12022             op2 = MASK_BSHFL(ctx->opcode);
12023             gen_bshfl(ctx, op2, rt, rd);
12024             break;
12025         case OPC_RDHWR:
12026             gen_rdhwr(env, ctx, rt, rd);
12027             break;
12028         case OPC_FORK:
12029             check_insn(env, ctx, ASE_MT);
12030             {
12031                 TCGv t0 = tcg_temp_new();
12032                 TCGv t1 = tcg_temp_new();
12033
12034                 gen_load_gpr(t0, rt);
12035                 gen_load_gpr(t1, rs);
12036                 gen_helper_fork(t0, t1);
12037                 tcg_temp_free(t0);
12038                 tcg_temp_free(t1);
12039             }
12040             break;
12041         case OPC_YIELD:
12042             check_insn(env, ctx, ASE_MT);
12043             {
12044                 TCGv t0 = tcg_temp_new();
12045
12046                 save_cpu_state(ctx, 1);
12047                 gen_load_gpr(t0, rs);
12048                 gen_helper_yield(t0, t0);
12049                 gen_store_gpr(t0, rd);
12050                 tcg_temp_free(t0);
12051             }
12052             break;
12053         case OPC_DIV_G_2E ... OPC_DIVU_G_2E:
12054         case OPC_MULT_G_2E ... OPC_MULTU_G_2E:
12055         case OPC_MOD_G_2E ... OPC_MODU_G_2E:
12056             check_insn(env, ctx, INSN_LOONGSON2E);
12057             gen_loongson_integer(ctx, op1, rd, rs, rt);
12058             break;
12059 #if defined(TARGET_MIPS64)
12060         case OPC_DEXTM ... OPC_DEXT:
12061         case OPC_DINSM ... OPC_DINS:
12062             check_insn(env, ctx, ISA_MIPS64R2);
12063             check_mips_64(ctx);
12064             gen_bitops(ctx, op1, rt, rs, sa, rd);
12065             break;
12066         case OPC_DBSHFL:
12067             check_insn(env, ctx, ISA_MIPS64R2);
12068             check_mips_64(ctx);
12069             op2 = MASK_DBSHFL(ctx->opcode);
12070             gen_bshfl(ctx, op2, rt, rd);
12071             break;
12072         case OPC_DDIV_G_2E ... OPC_DDIVU_G_2E:
12073         case OPC_DMULT_G_2E ... OPC_DMULTU_G_2E:
12074         case OPC_DMOD_G_2E ... OPC_DMODU_G_2E:
12075             check_insn(env, ctx, INSN_LOONGSON2E);
12076             gen_loongson_integer(ctx, op1, rd, rs, rt);
12077             break;
12078 #endif
12079         default:            /* Invalid */
12080             MIPS_INVAL("special3");
12081             generate_exception(ctx, EXCP_RI);
12082             break;
12083         }
12084         break;
12085     case OPC_REGIMM:
12086         op1 = MASK_REGIMM(ctx->opcode);
12087         switch (op1) {
12088         case OPC_BLTZ ... OPC_BGEZL: /* REGIMM branches */
12089         case OPC_BLTZAL ... OPC_BGEZALL:
12090             gen_compute_branch(ctx, op1, 4, rs, -1, imm << 2);
12091             *is_branch = 1;
12092             break;
12093         case OPC_TGEI ... OPC_TEQI: /* REGIMM traps */
12094         case OPC_TNEI:
12095             gen_trap(ctx, op1, rs, -1, imm);
12096             break;
12097         case OPC_SYNCI:
12098             check_insn(env, ctx, ISA_MIPS32R2);
12099             /* Treat as NOP. */
12100             break;
12101         default:            /* Invalid */
12102             MIPS_INVAL("regimm");
12103             generate_exception(ctx, EXCP_RI);
12104             break;
12105         }
12106         break;
12107     case OPC_CP0:
12108         check_cp0_enabled(ctx);
12109         op1 = MASK_CP0(ctx->opcode);
12110         switch (op1) {
12111         case OPC_MFC0:
12112         case OPC_MTC0:
12113         case OPC_MFTR:
12114         case OPC_MTTR:
12115 #if defined(TARGET_MIPS64)
12116         case OPC_DMFC0:
12117         case OPC_DMTC0:
12118 #endif
12119 #ifndef CONFIG_USER_ONLY
12120             gen_cp0(env, ctx, op1, rt, rd);
12121 #endif /* !CONFIG_USER_ONLY */
12122             break;
12123         case OPC_C0_FIRST ... OPC_C0_LAST:
12124 #ifndef CONFIG_USER_ONLY
12125             gen_cp0(env, ctx, MASK_C0(ctx->opcode), rt, rd);
12126 #endif /* !CONFIG_USER_ONLY */
12127             break;
12128         case OPC_MFMC0:
12129 #ifndef CONFIG_USER_ONLY
12130             {
12131                 TCGv t0 = tcg_temp_new();
12132
12133                 op2 = MASK_MFMC0(ctx->opcode);
12134                 switch (op2) {
12135                 case OPC_DMT:
12136                     check_insn(env, ctx, ASE_MT);
12137                     gen_helper_dmt(t0);
12138                     gen_store_gpr(t0, rt);
12139                     break;
12140                 case OPC_EMT:
12141                     check_insn(env, ctx, ASE_MT);
12142                     gen_helper_emt(t0);
12143                     gen_store_gpr(t0, rt);
12144                     break;
12145                 case OPC_DVPE:
12146                     check_insn(env, ctx, ASE_MT);
12147                     gen_helper_dvpe(t0);
12148                     gen_store_gpr(t0, rt);
12149                     break;
12150                 case OPC_EVPE:
12151                     check_insn(env, ctx, ASE_MT);
12152                     gen_helper_evpe(t0);
12153                     gen_store_gpr(t0, rt);
12154                     break;
12155                 case OPC_DI:
12156                     check_insn(env, ctx, ISA_MIPS32R2);
12157                     save_cpu_state(ctx, 1);
12158                     gen_helper_di(t0);
12159                     gen_store_gpr(t0, rt);
12160                     /* Stop translation as we may have switched the execution mode */
12161                     ctx->bstate = BS_STOP;
12162                     break;
12163                 case OPC_EI:
12164                     check_insn(env, ctx, ISA_MIPS32R2);
12165                     save_cpu_state(ctx, 1);
12166                     gen_helper_ei(t0);
12167                     gen_store_gpr(t0, rt);
12168                     /* Stop translation as we may have switched the execution mode */
12169                     ctx->bstate = BS_STOP;
12170                     break;
12171                 default:            /* Invalid */
12172                     MIPS_INVAL("mfmc0");
12173                     generate_exception(ctx, EXCP_RI);
12174                     break;
12175                 }
12176                 tcg_temp_free(t0);
12177             }
12178 #endif /* !CONFIG_USER_ONLY */
12179             break;
12180         case OPC_RDPGPR:
12181             check_insn(env, ctx, ISA_MIPS32R2);
12182             gen_load_srsgpr(rt, rd);
12183             break;
12184         case OPC_WRPGPR:
12185             check_insn(env, ctx, ISA_MIPS32R2);
12186             gen_store_srsgpr(rt, rd);
12187             break;
12188         default:
12189             MIPS_INVAL("cp0");
12190             generate_exception(ctx, EXCP_RI);
12191             break;
12192         }
12193         break;
12194     case OPC_ADDI: /* Arithmetic with immediate opcode */
12195     case OPC_ADDIU:
12196          gen_arith_imm(env, ctx, op, rt, rs, imm);
12197          break;
12198     case OPC_SLTI: /* Set on less than with immediate opcode */
12199     case OPC_SLTIU:
12200          gen_slt_imm(env, op, rt, rs, imm);
12201          break;
12202     case OPC_ANDI: /* Arithmetic with immediate opcode */
12203     case OPC_LUI:
12204     case OPC_ORI:
12205     case OPC_XORI:
12206          gen_logic_imm(env, op, rt, rs, imm);
12207          break;
12208     case OPC_J ... OPC_JAL: /* Jump */
12209          offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
12210          gen_compute_branch(ctx, op, 4, rs, rt, offset);
12211          *is_branch = 1;
12212          break;
12213     case OPC_BEQ ... OPC_BGTZ: /* Branch */
12214     case OPC_BEQL ... OPC_BGTZL:
12215          gen_compute_branch(ctx, op, 4, rs, rt, imm << 2);
12216          *is_branch = 1;
12217          break;
12218     case OPC_LB ... OPC_LWR: /* Load and stores */
12219     case OPC_LL:
12220          gen_ld(env, ctx, op, rt, rs, imm);
12221          break;
12222     case OPC_SB ... OPC_SW:
12223     case OPC_SWR:
12224          gen_st(ctx, op, rt, rs, imm);
12225          break;
12226     case OPC_SC:
12227          gen_st_cond(ctx, op, rt, rs, imm);
12228          break;
12229     case OPC_CACHE:
12230         check_cp0_enabled(ctx);
12231         check_insn(env, ctx, ISA_MIPS3 | ISA_MIPS32);
12232         /* Treat as NOP. */
12233         break;
12234     case OPC_PREF:
12235         check_insn(env, ctx, ISA_MIPS4 | ISA_MIPS32);
12236         /* Treat as NOP. */
12237         break;
12238
12239     /* Floating point (COP1). */
12240     case OPC_LWC1:
12241     case OPC_LDC1:
12242     case OPC_SWC1:
12243     case OPC_SDC1:
12244         gen_cop1_ldst(env, ctx, op, rt, rs, imm);
12245         break;
12246
12247     case OPC_CP1:
12248         if (env->CP0_Config1 & (1 << CP0C1_FP)) {
12249             check_cp1_enabled(ctx);
12250             op1 = MASK_CP1(ctx->opcode);
12251             switch (op1) {
12252             case OPC_MFHC1:
12253             case OPC_MTHC1:
12254                 check_insn(env, ctx, ISA_MIPS32R2);
12255             case OPC_MFC1:
12256             case OPC_CFC1:
12257             case OPC_MTC1:
12258             case OPC_CTC1:
12259                 gen_cp1(ctx, op1, rt, rd);
12260                 break;
12261 #if defined(TARGET_MIPS64)
12262             case OPC_DMFC1:
12263             case OPC_DMTC1:
12264                 check_insn(env, ctx, ISA_MIPS3);
12265                 gen_cp1(ctx, op1, rt, rd);
12266                 break;
12267 #endif
12268             case OPC_BC1ANY2:
12269             case OPC_BC1ANY4:
12270                 check_cop1x(ctx);
12271                 check_insn(env, ctx, ASE_MIPS3D);
12272                 /* fall through */
12273             case OPC_BC1:
12274                 gen_compute_branch1(env, ctx, MASK_BC1(ctx->opcode),
12275                                     (rt >> 2) & 0x7, imm << 2);
12276                 *is_branch = 1;
12277                 break;
12278             case OPC_S_FMT:
12279             case OPC_D_FMT:
12280             case OPC_W_FMT:
12281             case OPC_L_FMT:
12282             case OPC_PS_FMT:
12283                 gen_farith(ctx, ctx->opcode & FOP(0x3f, 0x1f), rt, rd, sa,
12284                            (imm >> 8) & 0x7);
12285                 break;
12286             default:
12287                 MIPS_INVAL("cp1");
12288                 generate_exception (ctx, EXCP_RI);
12289                 break;
12290             }
12291         } else {
12292             generate_exception_err(ctx, EXCP_CpU, 1);
12293         }
12294         break;
12295
12296     /* COP2.  */
12297     case OPC_LWC2:
12298     case OPC_LDC2:
12299     case OPC_SWC2:
12300     case OPC_SDC2:
12301     case OPC_CP2:
12302         /* COP2: Not implemented. */
12303         generate_exception_err(ctx, EXCP_CpU, 2);
12304         break;
12305
12306     case OPC_CP3:
12307         if (env->CP0_Config1 & (1 << CP0C1_FP)) {
12308             check_cp1_enabled(ctx);
12309             op1 = MASK_CP3(ctx->opcode);
12310             switch (op1) {
12311             case OPC_LWXC1:
12312             case OPC_LDXC1:
12313             case OPC_LUXC1:
12314             case OPC_SWXC1:
12315             case OPC_SDXC1:
12316             case OPC_SUXC1:
12317                 gen_flt3_ldst(ctx, op1, sa, rd, rs, rt);
12318                 break;
12319             case OPC_PREFX:
12320                 /* Treat as NOP. */
12321                 break;
12322             case OPC_ALNV_PS:
12323             case OPC_MADD_S:
12324             case OPC_MADD_D:
12325             case OPC_MADD_PS:
12326             case OPC_MSUB_S:
12327             case OPC_MSUB_D:
12328             case OPC_MSUB_PS:
12329             case OPC_NMADD_S:
12330             case OPC_NMADD_D:
12331             case OPC_NMADD_PS:
12332             case OPC_NMSUB_S:
12333             case OPC_NMSUB_D:
12334             case OPC_NMSUB_PS:
12335                 gen_flt3_arith(ctx, op1, sa, rs, rd, rt);
12336                 break;
12337             default:
12338                 MIPS_INVAL("cp3");
12339                 generate_exception (ctx, EXCP_RI);
12340                 break;
12341             }
12342         } else {
12343             generate_exception_err(ctx, EXCP_CpU, 1);
12344         }
12345         break;
12346
12347 #if defined(TARGET_MIPS64)
12348     /* MIPS64 opcodes */
12349     case OPC_LWU:
12350     case OPC_LDL ... OPC_LDR:
12351     case OPC_LLD:
12352     case OPC_LD:
12353         check_insn(env, ctx, ISA_MIPS3);
12354         check_mips_64(ctx);
12355         gen_ld(env, ctx, op, rt, rs, imm);
12356         break;
12357     case OPC_SDL ... OPC_SDR:
12358     case OPC_SD:
12359         check_insn(env, ctx, ISA_MIPS3);
12360         check_mips_64(ctx);
12361         gen_st(ctx, op, rt, rs, imm);
12362         break;
12363     case OPC_SCD:
12364         check_insn(env, ctx, ISA_MIPS3);
12365         check_mips_64(ctx);
12366         gen_st_cond(ctx, op, rt, rs, imm);
12367         break;
12368     case OPC_DADDI:
12369     case OPC_DADDIU:
12370         check_insn(env, ctx, ISA_MIPS3);
12371         check_mips_64(ctx);
12372         gen_arith_imm(env, ctx, op, rt, rs, imm);
12373         break;
12374 #endif
12375     case OPC_JALX:
12376         check_insn(env, ctx, ASE_MIPS16 | ASE_MICROMIPS);
12377         offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
12378         gen_compute_branch(ctx, op, 4, rs, rt, offset);
12379         *is_branch = 1;
12380         break;
12381     case OPC_MDMX:
12382         check_insn(env, ctx, ASE_MDMX);
12383         /* MDMX: Not implemented. */
12384     default:            /* Invalid */
12385         MIPS_INVAL("major opcode");
12386         generate_exception(ctx, EXCP_RI);
12387         break;
12388     }
12389 }
12390
12391 static inline void
12392 gen_intermediate_code_internal (CPUMIPSState *env, TranslationBlock *tb,
12393                                 int search_pc)
12394 {
12395     DisasContext ctx;
12396     target_ulong pc_start;
12397     uint16_t *gen_opc_end;
12398     CPUBreakpoint *bp;
12399     int j, lj = -1;
12400     int num_insns;
12401     int max_insns;
12402     int insn_bytes;
12403     int is_branch;
12404
12405     if (search_pc)
12406         qemu_log("search pc %d\n", search_pc);
12407
12408     pc_start = tb->pc;
12409     gen_opc_end = gen_opc_buf + OPC_MAX_SIZE;
12410     ctx.pc = pc_start;
12411     ctx.saved_pc = -1;
12412     ctx.singlestep_enabled = env->singlestep_enabled;
12413     ctx.tb = tb;
12414     ctx.bstate = BS_NONE;
12415     /* Restore delay slot state from the tb context.  */
12416     ctx.hflags = (uint32_t)tb->flags; /* FIXME: maybe use 64 bits here? */
12417     restore_cpu_state(env, &ctx);
12418 #ifdef CONFIG_USER_ONLY
12419         ctx.mem_idx = MIPS_HFLAG_UM;
12420 #else
12421         ctx.mem_idx = ctx.hflags & MIPS_HFLAG_KSU;
12422 #endif
12423     num_insns = 0;
12424     max_insns = tb->cflags & CF_COUNT_MASK;
12425     if (max_insns == 0)
12426         max_insns = CF_COUNT_MASK;
12427     LOG_DISAS("\ntb %p idx %d hflags %04x\n", tb, ctx.mem_idx, ctx.hflags);
12428     gen_icount_start();
12429     while (ctx.bstate == BS_NONE) {
12430         if (unlikely(!QTAILQ_EMPTY(&env->breakpoints))) {
12431             QTAILQ_FOREACH(bp, &env->breakpoints, entry) {
12432                 if (bp->pc == ctx.pc) {
12433                     save_cpu_state(&ctx, 1);
12434                     ctx.bstate = BS_BRANCH;
12435                     gen_helper_0i(raise_exception, EXCP_DEBUG);
12436                     /* Include the breakpoint location or the tb won't
12437                      * be flushed when it must be.  */
12438                     ctx.pc += 4;
12439                     goto done_generating;
12440                 }
12441             }
12442         }
12443
12444         if (search_pc) {
12445             j = gen_opc_ptr - gen_opc_buf;
12446             if (lj < j) {
12447                 lj++;
12448                 while (lj < j)
12449                     gen_opc_instr_start[lj++] = 0;
12450             }
12451             gen_opc_pc[lj] = ctx.pc;
12452             gen_opc_hflags[lj] = ctx.hflags & MIPS_HFLAG_BMASK;
12453             gen_opc_instr_start[lj] = 1;
12454             gen_opc_icount[lj] = num_insns;
12455         }
12456         if (num_insns + 1 == max_insns && (tb->cflags & CF_LAST_IO))
12457             gen_io_start();
12458
12459         is_branch = 0;
12460         if (!(ctx.hflags & MIPS_HFLAG_M16)) {
12461             ctx.opcode = ldl_code(ctx.pc);
12462             insn_bytes = 4;
12463             decode_opc(env, &ctx, &is_branch);
12464         } else if (env->insn_flags & ASE_MICROMIPS) {
12465             ctx.opcode = lduw_code(ctx.pc);
12466             insn_bytes = decode_micromips_opc(env, &ctx, &is_branch);
12467         } else if (env->insn_flags & ASE_MIPS16) {
12468             ctx.opcode = lduw_code(ctx.pc);
12469             insn_bytes = decode_mips16_opc(env, &ctx, &is_branch);
12470         } else {
12471             generate_exception(&ctx, EXCP_RI);
12472             ctx.bstate = BS_STOP;
12473             break;
12474         }
12475         if (!is_branch) {
12476             handle_delay_slot(env, &ctx, insn_bytes);
12477         }
12478         ctx.pc += insn_bytes;
12479
12480         num_insns++;
12481
12482         /* Execute a branch and its delay slot as a single instruction.
12483            This is what GDB expects and is consistent with what the
12484            hardware does (e.g. if a delay slot instruction faults, the
12485            reported PC is the PC of the branch).  */
12486         if (env->singlestep_enabled && (ctx.hflags & MIPS_HFLAG_BMASK) == 0)
12487             break;
12488
12489         if ((ctx.pc & (TARGET_PAGE_SIZE - 1)) == 0)
12490             break;
12491
12492         if (gen_opc_ptr >= gen_opc_end)
12493             break;
12494
12495         if (num_insns >= max_insns)
12496             break;
12497
12498         if (singlestep)
12499             break;
12500     }
12501     if (tb->cflags & CF_LAST_IO)
12502         gen_io_end();
12503     if (env->singlestep_enabled && ctx.bstate != BS_BRANCH) {
12504         save_cpu_state(&ctx, ctx.bstate == BS_NONE);
12505         gen_helper_0i(raise_exception, EXCP_DEBUG);
12506     } else {
12507         switch (ctx.bstate) {
12508         case BS_STOP:
12509             gen_goto_tb(&ctx, 0, ctx.pc);
12510             break;
12511         case BS_NONE:
12512             save_cpu_state(&ctx, 0);
12513             gen_goto_tb(&ctx, 0, ctx.pc);
12514             break;
12515         case BS_EXCP:
12516             tcg_gen_exit_tb(0);
12517             break;
12518         case BS_BRANCH:
12519         default:
12520             break;
12521         }
12522     }
12523 done_generating:
12524     gen_icount_end(tb, num_insns);
12525     *gen_opc_ptr = INDEX_op_end;
12526     if (search_pc) {
12527         j = gen_opc_ptr - gen_opc_buf;
12528         lj++;
12529         while (lj <= j)
12530             gen_opc_instr_start[lj++] = 0;
12531     } else {
12532         tb->size = ctx.pc - pc_start;
12533         tb->icount = num_insns;
12534     }
12535 #ifdef DEBUG_DISAS
12536     LOG_DISAS("\n");
12537     if (qemu_loglevel_mask(CPU_LOG_TB_IN_ASM)) {
12538         qemu_log("IN: %s\n", lookup_symbol(pc_start));
12539         log_target_disas(pc_start, ctx.pc - pc_start, 0);
12540         qemu_log("\n");
12541     }
12542 #endif
12543 }
12544
12545 void gen_intermediate_code (CPUMIPSState *env, struct TranslationBlock *tb)
12546 {
12547     gen_intermediate_code_internal(env, tb, 0);
12548 }
12549
12550 void gen_intermediate_code_pc (CPUMIPSState *env, struct TranslationBlock *tb)
12551 {
12552     gen_intermediate_code_internal(env, tb, 1);
12553 }
12554
12555 static void fpu_dump_state(CPUMIPSState *env, FILE *f, fprintf_function fpu_fprintf,
12556                            int flags)
12557 {
12558     int i;
12559     int is_fpu64 = !!(env->hflags & MIPS_HFLAG_F64);
12560
12561 #define printfpr(fp)                                                    \
12562     do {                                                                \
12563         if (is_fpu64)                                                   \
12564             fpu_fprintf(f, "w:%08x d:%016" PRIx64                       \
12565                         " fd:%13g fs:%13g psu: %13g\n",                 \
12566                         (fp)->w[FP_ENDIAN_IDX], (fp)->d,                \
12567                         (double)(fp)->fd,                               \
12568                         (double)(fp)->fs[FP_ENDIAN_IDX],                \
12569                         (double)(fp)->fs[!FP_ENDIAN_IDX]);              \
12570         else {                                                          \
12571             fpr_t tmp;                                                  \
12572             tmp.w[FP_ENDIAN_IDX] = (fp)->w[FP_ENDIAN_IDX];              \
12573             tmp.w[!FP_ENDIAN_IDX] = ((fp) + 1)->w[FP_ENDIAN_IDX];       \
12574             fpu_fprintf(f, "w:%08x d:%016" PRIx64                       \
12575                         " fd:%13g fs:%13g psu:%13g\n",                  \
12576                         tmp.w[FP_ENDIAN_IDX], tmp.d,                    \
12577                         (double)tmp.fd,                                 \
12578                         (double)tmp.fs[FP_ENDIAN_IDX],                  \
12579                         (double)tmp.fs[!FP_ENDIAN_IDX]);                \
12580         }                                                               \
12581     } while(0)
12582
12583
12584     fpu_fprintf(f, "CP1 FCR0 0x%08x  FCR31 0x%08x  SR.FR %d  fp_status 0x%02x\n",
12585                 env->active_fpu.fcr0, env->active_fpu.fcr31, is_fpu64,
12586                 get_float_exception_flags(&env->active_fpu.fp_status));
12587     for (i = 0; i < 32; (is_fpu64) ? i++ : (i += 2)) {
12588         fpu_fprintf(f, "%3s: ", fregnames[i]);
12589         printfpr(&env->active_fpu.fpr[i]);
12590     }
12591
12592 #undef printfpr
12593 }
12594
12595 #if defined(TARGET_MIPS64) && defined(MIPS_DEBUG_SIGN_EXTENSIONS)
12596 /* Debug help: The architecture requires 32bit code to maintain proper
12597    sign-extended values on 64bit machines.  */
12598
12599 #define SIGN_EXT_P(val) ((((val) & ~0x7fffffff) == 0) || (((val) & ~0x7fffffff) == ~0x7fffffff))
12600
12601 static void
12602 cpu_mips_check_sign_extensions (CPUMIPSState *env, FILE *f,
12603                                 fprintf_function cpu_fprintf,
12604                                 int flags)
12605 {
12606     int i;
12607
12608     if (!SIGN_EXT_P(env->active_tc.PC))
12609         cpu_fprintf(f, "BROKEN: pc=0x" TARGET_FMT_lx "\n", env->active_tc.PC);
12610     if (!SIGN_EXT_P(env->active_tc.HI[0]))
12611         cpu_fprintf(f, "BROKEN: HI=0x" TARGET_FMT_lx "\n", env->active_tc.HI[0]);
12612     if (!SIGN_EXT_P(env->active_tc.LO[0]))
12613         cpu_fprintf(f, "BROKEN: LO=0x" TARGET_FMT_lx "\n", env->active_tc.LO[0]);
12614     if (!SIGN_EXT_P(env->btarget))
12615         cpu_fprintf(f, "BROKEN: btarget=0x" TARGET_FMT_lx "\n", env->btarget);
12616
12617     for (i = 0; i < 32; i++) {
12618         if (!SIGN_EXT_P(env->active_tc.gpr[i]))
12619             cpu_fprintf(f, "BROKEN: %s=0x" TARGET_FMT_lx "\n", regnames[i], env->active_tc.gpr[i]);
12620     }
12621
12622     if (!SIGN_EXT_P(env->CP0_EPC))
12623         cpu_fprintf(f, "BROKEN: EPC=0x" TARGET_FMT_lx "\n", env->CP0_EPC);
12624     if (!SIGN_EXT_P(env->lladdr))
12625         cpu_fprintf(f, "BROKEN: LLAddr=0x" TARGET_FMT_lx "\n", env->lladdr);
12626 }
12627 #endif
12628
12629 void cpu_dump_state (CPUMIPSState *env, FILE *f, fprintf_function cpu_fprintf,
12630                      int flags)
12631 {
12632     int i;
12633
12634     cpu_fprintf(f, "pc=0x" TARGET_FMT_lx " HI=0x" TARGET_FMT_lx
12635                 " LO=0x" TARGET_FMT_lx " ds %04x "
12636                 TARGET_FMT_lx " " TARGET_FMT_ld "\n",
12637                 env->active_tc.PC, env->active_tc.HI[0], env->active_tc.LO[0],
12638                 env->hflags, env->btarget, env->bcond);
12639     for (i = 0; i < 32; i++) {
12640         if ((i & 3) == 0)
12641             cpu_fprintf(f, "GPR%02d:", i);
12642         cpu_fprintf(f, " %s " TARGET_FMT_lx, regnames[i], env->active_tc.gpr[i]);
12643         if ((i & 3) == 3)
12644             cpu_fprintf(f, "\n");
12645     }
12646
12647     cpu_fprintf(f, "CP0 Status  0x%08x Cause   0x%08x EPC    0x" TARGET_FMT_lx "\n",
12648                 env->CP0_Status, env->CP0_Cause, env->CP0_EPC);
12649     cpu_fprintf(f, "    Config0 0x%08x Config1 0x%08x LLAddr 0x" TARGET_FMT_lx "\n",
12650                 env->CP0_Config0, env->CP0_Config1, env->lladdr);
12651     if (env->hflags & MIPS_HFLAG_FPU)
12652         fpu_dump_state(env, f, cpu_fprintf, flags);
12653 #if defined(TARGET_MIPS64) && defined(MIPS_DEBUG_SIGN_EXTENSIONS)
12654     cpu_mips_check_sign_extensions(env, f, cpu_fprintf, flags);
12655 #endif
12656 }
12657
12658 static void mips_tcg_init(void)
12659 {
12660     int i;
12661     static int inited;
12662
12663     /* Initialize various static tables. */
12664     if (inited)
12665         return;
12666
12667     cpu_env = tcg_global_reg_new_ptr(TCG_AREG0, "env");
12668     TCGV_UNUSED(cpu_gpr[0]);
12669     for (i = 1; i < 32; i++)
12670         cpu_gpr[i] = tcg_global_mem_new(TCG_AREG0,
12671                                         offsetof(CPUMIPSState, active_tc.gpr[i]),
12672                                         regnames[i]);
12673     cpu_PC = tcg_global_mem_new(TCG_AREG0,
12674                                 offsetof(CPUMIPSState, active_tc.PC), "PC");
12675     for (i = 0; i < MIPS_DSP_ACC; i++) {
12676         cpu_HI[i] = tcg_global_mem_new(TCG_AREG0,
12677                                        offsetof(CPUMIPSState, active_tc.HI[i]),
12678                                        regnames_HI[i]);
12679         cpu_LO[i] = tcg_global_mem_new(TCG_AREG0,
12680                                        offsetof(CPUMIPSState, active_tc.LO[i]),
12681                                        regnames_LO[i]);
12682         cpu_ACX[i] = tcg_global_mem_new(TCG_AREG0,
12683                                         offsetof(CPUMIPSState, active_tc.ACX[i]),
12684                                         regnames_ACX[i]);
12685     }
12686     cpu_dspctrl = tcg_global_mem_new(TCG_AREG0,
12687                                      offsetof(CPUMIPSState, active_tc.DSPControl),
12688                                      "DSPControl");
12689     bcond = tcg_global_mem_new(TCG_AREG0,
12690                                offsetof(CPUMIPSState, bcond), "bcond");
12691     btarget = tcg_global_mem_new(TCG_AREG0,
12692                                  offsetof(CPUMIPSState, btarget), "btarget");
12693     hflags = tcg_global_mem_new_i32(TCG_AREG0,
12694                                     offsetof(CPUMIPSState, hflags), "hflags");
12695
12696     fpu_fcr0 = tcg_global_mem_new_i32(TCG_AREG0,
12697                                       offsetof(CPUMIPSState, active_fpu.fcr0),
12698                                       "fcr0");
12699     fpu_fcr31 = tcg_global_mem_new_i32(TCG_AREG0,
12700                                        offsetof(CPUMIPSState, active_fpu.fcr31),
12701                                        "fcr31");
12702
12703     /* register helpers */
12704 #define GEN_HELPER 2
12705 #include "helper.h"
12706
12707     inited = 1;
12708 }
12709
12710 #include "translate_init.c"
12711
12712 MIPSCPU *cpu_mips_init(const char *cpu_model)
12713 {
12714     MIPSCPU *cpu;
12715     CPUMIPSState *env;
12716     const mips_def_t *def;
12717
12718     def = cpu_mips_find_by_name(cpu_model);
12719     if (!def)
12720         return NULL;
12721     cpu = MIPS_CPU(object_new(TYPE_MIPS_CPU));
12722     env = &cpu->env;
12723     env->cpu_model = def;
12724     env->cpu_model_str = cpu_model;
12725
12726 #ifndef CONFIG_USER_ONLY
12727     mmu_init(env, def);
12728 #endif
12729     fpu_init(env, def);
12730     mvp_init(env, def);
12731     mips_tcg_init();
12732     cpu_reset(CPU(cpu));
12733     qemu_init_vcpu(env);
12734     return cpu;
12735 }
12736
12737 void cpu_state_reset(CPUMIPSState *env)
12738 {
12739     if (qemu_loglevel_mask(CPU_LOG_RESET)) {
12740         qemu_log("CPU Reset (CPU %d)\n", env->cpu_index);
12741         log_cpu_state(env, 0);
12742     }
12743
12744     memset(env, 0, offsetof(CPUMIPSState, breakpoints));
12745     tlb_flush(env, 1);
12746
12747     /* Reset registers to their default values */
12748     env->CP0_PRid = env->cpu_model->CP0_PRid;
12749     env->CP0_Config0 = env->cpu_model->CP0_Config0;
12750 #ifdef TARGET_WORDS_BIGENDIAN
12751     env->CP0_Config0 |= (1 << CP0C0_BE);
12752 #endif
12753     env->CP0_Config1 = env->cpu_model->CP0_Config1;
12754     env->CP0_Config2 = env->cpu_model->CP0_Config2;
12755     env->CP0_Config3 = env->cpu_model->CP0_Config3;
12756     env->CP0_Config6 = env->cpu_model->CP0_Config6;
12757     env->CP0_Config7 = env->cpu_model->CP0_Config7;
12758     env->CP0_LLAddr_rw_bitmask = env->cpu_model->CP0_LLAddr_rw_bitmask
12759                                  << env->cpu_model->CP0_LLAddr_shift;
12760     env->CP0_LLAddr_shift = env->cpu_model->CP0_LLAddr_shift;
12761     env->SYNCI_Step = env->cpu_model->SYNCI_Step;
12762     env->CCRes = env->cpu_model->CCRes;
12763     env->CP0_Status_rw_bitmask = env->cpu_model->CP0_Status_rw_bitmask;
12764     env->CP0_TCStatus_rw_bitmask = env->cpu_model->CP0_TCStatus_rw_bitmask;
12765     env->CP0_SRSCtl = env->cpu_model->CP0_SRSCtl;
12766     env->current_tc = 0;
12767     env->SEGBITS = env->cpu_model->SEGBITS;
12768     env->SEGMask = (target_ulong)((1ULL << env->cpu_model->SEGBITS) - 1);
12769 #if defined(TARGET_MIPS64)
12770     if (env->cpu_model->insn_flags & ISA_MIPS3) {
12771         env->SEGMask |= 3ULL << 62;
12772     }
12773 #endif
12774     env->PABITS = env->cpu_model->PABITS;
12775     env->PAMask = (target_ulong)((1ULL << env->cpu_model->PABITS) - 1);
12776     env->CP0_SRSConf0_rw_bitmask = env->cpu_model->CP0_SRSConf0_rw_bitmask;
12777     env->CP0_SRSConf0 = env->cpu_model->CP0_SRSConf0;
12778     env->CP0_SRSConf1_rw_bitmask = env->cpu_model->CP0_SRSConf1_rw_bitmask;
12779     env->CP0_SRSConf1 = env->cpu_model->CP0_SRSConf1;
12780     env->CP0_SRSConf2_rw_bitmask = env->cpu_model->CP0_SRSConf2_rw_bitmask;
12781     env->CP0_SRSConf2 = env->cpu_model->CP0_SRSConf2;
12782     env->CP0_SRSConf3_rw_bitmask = env->cpu_model->CP0_SRSConf3_rw_bitmask;
12783     env->CP0_SRSConf3 = env->cpu_model->CP0_SRSConf3;
12784     env->CP0_SRSConf4_rw_bitmask = env->cpu_model->CP0_SRSConf4_rw_bitmask;
12785     env->CP0_SRSConf4 = env->cpu_model->CP0_SRSConf4;
12786     env->active_fpu.fcr0 = env->cpu_model->CP1_fcr0;
12787     env->insn_flags = env->cpu_model->insn_flags;
12788
12789 #if defined(CONFIG_USER_ONLY)
12790     env->hflags = MIPS_HFLAG_UM;
12791     /* Enable access to the CPUNum, SYNCI_Step, CC, and CCRes RDHWR
12792        hardware registers.  */
12793     env->CP0_HWREna |= 0x0000000F;
12794     if (env->CP0_Config1 & (1 << CP0C1_FP)) {
12795         env->hflags |= MIPS_HFLAG_FPU;
12796     }
12797 #ifdef TARGET_MIPS64
12798     if (env->active_fpu.fcr0 & (1 << FCR0_F64)) {
12799         env->hflags |= MIPS_HFLAG_F64;
12800     }
12801 #endif
12802 #else
12803     if (env->hflags & MIPS_HFLAG_BMASK) {
12804         /* If the exception was raised from a delay slot,
12805            come back to the jump.  */
12806         env->CP0_ErrorEPC = env->active_tc.PC - 4;
12807     } else {
12808         env->CP0_ErrorEPC = env->active_tc.PC;
12809     }
12810     env->active_tc.PC = (int32_t)0xBFC00000;
12811     env->CP0_Random = env->tlb->nb_tlb - 1;
12812     env->tlb->tlb_in_use = env->tlb->nb_tlb;
12813     env->CP0_Wired = 0;
12814     env->CP0_EBase = 0x80000000 | (env->cpu_index & 0x3FF);
12815     env->CP0_Status = (1 << CP0St_BEV) | (1 << CP0St_ERL);
12816     /* vectored interrupts not implemented, timer on int 7,
12817        no performance counters. */
12818     env->CP0_IntCtl = 0xe0000000;
12819     {
12820         int i;
12821
12822         for (i = 0; i < 7; i++) {
12823             env->CP0_WatchLo[i] = 0;
12824             env->CP0_WatchHi[i] = 0x80000000;
12825         }
12826         env->CP0_WatchLo[7] = 0;
12827         env->CP0_WatchHi[7] = 0;
12828     }
12829     /* Count register increments in debug mode, EJTAG version 1 */
12830     env->CP0_Debug = (1 << CP0DB_CNT) | (0x1 << CP0DB_VER);
12831     env->hflags = MIPS_HFLAG_CP0;
12832
12833     if (env->CP0_Config3 & (1 << CP0C3_MT)) {
12834         int i;
12835
12836         /* Only TC0 on VPE 0 starts as active.  */
12837         for (i = 0; i < ARRAY_SIZE(env->tcs); i++) {
12838             env->tcs[i].CP0_TCBind = env->cpu_index << CP0TCBd_CurVPE;
12839             env->tcs[i].CP0_TCHalt = 1;
12840         }
12841         env->active_tc.CP0_TCHalt = 1;
12842         env->halted = 1;
12843
12844         if (!env->cpu_index) {
12845             /* VPE0 starts up enabled.  */
12846             env->mvp->CP0_MVPControl |= (1 << CP0MVPCo_EVP);
12847             env->CP0_VPEConf0 |= (1 << CP0VPEC0_MVP) | (1 << CP0VPEC0_VPA);
12848
12849             /* TC0 starts up unhalted.  */
12850             env->halted = 0;
12851             env->active_tc.CP0_TCHalt = 0;
12852             env->tcs[0].CP0_TCHalt = 0;
12853             /* With thread 0 active.  */
12854             env->active_tc.CP0_TCStatus = (1 << CP0TCSt_A);
12855             env->tcs[0].CP0_TCStatus = (1 << CP0TCSt_A);
12856         }
12857     }
12858 #endif
12859 #if defined(TARGET_MIPS64)
12860     if (env->cpu_model->insn_flags & ISA_MIPS3) {
12861         env->hflags |= MIPS_HFLAG_64;
12862     }
12863 #endif
12864     env->exception_index = EXCP_NONE;
12865 }
12866
12867 void restore_state_to_opc(CPUMIPSState *env, TranslationBlock *tb, int pc_pos)
12868 {
12869     env->active_tc.PC = gen_opc_pc[pc_pos];
12870     env->hflags &= ~MIPS_HFLAG_BMASK;
12871     env->hflags |= gen_opc_hflags[pc_pos];
12872 }