xref: /openbmc/qemu/target/mips/tcg/translate.c (revision 020cafa58e2b7e2f3687bfe31b141c7b87790791)
1 /*
2  *  MIPS 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  *  Copyright (c) 2012 Jia Liu & Dongxue Zhang (MIPS ASE DSP support)
9  *  Copyright (c) 2020 Philippe Mathieu-Daudé
10  *
11  * This library is free software; you can redistribute it and/or
12  * modify it under the terms of the GNU Lesser General Public
13  * License as published by the Free Software Foundation; either
14  * version 2.1 of the License, or (at your option) any later version.
15  *
16  * This library is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
19  * Lesser General Public License for more details.
20  *
21  * You should have received a copy of the GNU Lesser General Public
22  * License along with this library; if not, see <http://www.gnu.org/licenses/>.
23  */
24 
25 #include "qemu/osdep.h"
26 #include "translate.h"
27 #include "internal.h"
28 #include "exec/helper-proto.h"
29 #include "exec/translation-block.h"
30 #include "semihosting/semihost.h"
31 #include "trace.h"
32 #include "fpu_helper.h"
33 
34 #define HELPER_H "helper.h"
35 #include "exec/helper-info.c.inc"
36 #undef  HELPER_H
37 
38 
39 /*
40  * Many sysemu-only helpers are not reachable for user-only.
41  * Define stub generators here, so that we need not either sprinkle
42  * ifdefs through the translator, nor provide the helper function.
43  */
44 #define STUB_HELPER(NAME, ...) \
45     static inline void gen_helper_##NAME(__VA_ARGS__) \
46     { g_assert_not_reached(); }
47 
48 #ifdef CONFIG_USER_ONLY
49 STUB_HELPER(cache, TCGv_env env, TCGv val, TCGv_i32 reg)
50 #endif
51 
52 enum {
53     /* indirect opcode tables */
54     OPC_SPECIAL  = (0x00 << 26),
55     OPC_REGIMM   = (0x01 << 26),
56     OPC_CP0      = (0x10 << 26),
57     OPC_CP2      = (0x12 << 26),
58     OPC_CP3      = (0x13 << 26),
59     OPC_SPECIAL2 = (0x1C << 26),
60     OPC_SPECIAL3 = (0x1F << 26),
61     /* arithmetic with immediate */
62     OPC_ADDI     = (0x08 << 26),
63     OPC_ADDIU    = (0x09 << 26),
64     OPC_SLTI     = (0x0A << 26),
65     OPC_SLTIU    = (0x0B << 26),
66     /* logic with immediate */
67     OPC_ANDI     = (0x0C << 26),
68     OPC_ORI      = (0x0D << 26),
69     OPC_XORI     = (0x0E << 26),
70     OPC_LUI      = (0x0F << 26),
71     /* arithmetic with immediate */
72     OPC_DADDI    = (0x18 << 26),
73     OPC_DADDIU   = (0x19 << 26),
74     /* Jump and branches */
75     OPC_J        = (0x02 << 26),
76     OPC_JAL      = (0x03 << 26),
77     OPC_BEQ      = (0x04 << 26),  /* Unconditional if rs = rt = 0 (B) */
78     OPC_BEQL     = (0x14 << 26),
79     OPC_BNE      = (0x05 << 26),
80     OPC_BNEL     = (0x15 << 26),
81     OPC_BLEZ     = (0x06 << 26),
82     OPC_BLEZL    = (0x16 << 26),
83     OPC_BGTZ     = (0x07 << 26),
84     OPC_BGTZL    = (0x17 << 26),
85     OPC_JALX     = (0x1D << 26),
86     OPC_DAUI     = (0x1D << 26),
87     /* Load and stores */
88     OPC_LDL      = (0x1A << 26),
89     OPC_LDR      = (0x1B << 26),
90     OPC_LB       = (0x20 << 26),
91     OPC_LH       = (0x21 << 26),
92     OPC_LWL      = (0x22 << 26),
93     OPC_LW       = (0x23 << 26),
94     OPC_LWPC     = OPC_LW | 0x5,
95     OPC_LBU      = (0x24 << 26),
96     OPC_LHU      = (0x25 << 26),
97     OPC_LWR      = (0x26 << 26),
98     OPC_LWU      = (0x27 << 26),
99     OPC_SB       = (0x28 << 26),
100     OPC_SH       = (0x29 << 26),
101     OPC_SWL      = (0x2A << 26),
102     OPC_SW       = (0x2B << 26),
103     OPC_SDL      = (0x2C << 26),
104     OPC_SDR      = (0x2D << 26),
105     OPC_SWR      = (0x2E << 26),
106     OPC_LL       = (0x30 << 26),
107     OPC_LLD      = (0x34 << 26),
108     OPC_LD       = (0x37 << 26),
109     OPC_LDPC     = OPC_LD | 0x5,
110     OPC_SC       = (0x38 << 26),
111     OPC_SCD      = (0x3C << 26),
112     OPC_SD       = (0x3F << 26),
113     /* Floating point load/store */
114     OPC_LWC1     = (0x31 << 26),
115     OPC_LWC2     = (0x32 << 26),
116     OPC_LDC1     = (0x35 << 26),
117     OPC_LDC2     = (0x36 << 26),
118     OPC_SWC1     = (0x39 << 26),
119     OPC_SWC2     = (0x3A << 26),
120     OPC_SDC1     = (0x3D << 26),
121     OPC_SDC2     = (0x3E << 26),
122     /* Compact Branches */
123     OPC_BLEZALC  = (0x06 << 26),
124     OPC_BGEZALC  = (0x06 << 26),
125     OPC_BGEUC    = (0x06 << 26),
126     OPC_BGTZALC  = (0x07 << 26),
127     OPC_BLTZALC  = (0x07 << 26),
128     OPC_BLTUC    = (0x07 << 26),
129     OPC_BOVC     = (0x08 << 26),
130     OPC_BEQZALC  = (0x08 << 26),
131     OPC_BEQC     = (0x08 << 26),
132     OPC_BLEZC    = (0x16 << 26),
133     OPC_BGEZC    = (0x16 << 26),
134     OPC_BGEC     = (0x16 << 26),
135     OPC_BGTZC    = (0x17 << 26),
136     OPC_BLTZC    = (0x17 << 26),
137     OPC_BLTC     = (0x17 << 26),
138     OPC_BNVC     = (0x18 << 26),
139     OPC_BNEZALC  = (0x18 << 26),
140     OPC_BNEC     = (0x18 << 26),
141     OPC_BC       = (0x32 << 26),
142     OPC_BEQZC    = (0x36 << 26),
143     OPC_JIC      = (0x36 << 26),
144     OPC_BALC     = (0x3A << 26),
145     OPC_BNEZC    = (0x3E << 26),
146     OPC_JIALC    = (0x3E << 26),
147     /* MDMX ASE specific */
148     OPC_MDMX     = (0x1E << 26),
149     /* Cache and prefetch */
150     OPC_CACHE    = (0x2F << 26),
151     OPC_PREF     = (0x33 << 26),
152     /* PC-relative address computation / loads */
153     OPC_PCREL    = (0x3B << 26),
154 };
155 
156 /* PC-relative address computation / loads  */
157 #define MASK_OPC_PCREL_TOP2BITS(op) (MASK_OP_MAJOR(op) | (op & (3 << 19)))
158 #define MASK_OPC_PCREL_TOP5BITS(op) (MASK_OP_MAJOR(op) | (op & (0x1f << 16)))
159 enum {
160     /* Instructions determined by bits 19 and 20 */
161     OPC_ADDIUPC = OPC_PCREL | (0 << 19),
162     R6_OPC_LWPC = OPC_PCREL | (1 << 19),
163     OPC_LWUPC   = OPC_PCREL | (2 << 19),
164 
165     /* Instructions determined by bits 16 ... 20 */
166     OPC_AUIPC   = OPC_PCREL | (0x1e << 16),
167     OPC_ALUIPC  = OPC_PCREL | (0x1f << 16),
168 
169     /* Other */
170     R6_OPC_LDPC = OPC_PCREL | (6 << 18),
171 };
172 
173 /* MIPS special opcodes */
174 #define MASK_SPECIAL(op)            (MASK_OP_MAJOR(op) | (op & 0x3F))
175 
176 enum {
177     /* Shifts */
178     OPC_SLL      = 0x00 | OPC_SPECIAL,
179     /* NOP is SLL r0, r0, 0   */
180     /* SSNOP is SLL r0, r0, 1 */
181     /* EHB is SLL r0, r0, 3 */
182     OPC_SRL      = 0x02 | OPC_SPECIAL, /* also ROTR */
183     OPC_ROTR     = OPC_SRL | (1 << 21),
184     OPC_SRA      = 0x03 | OPC_SPECIAL,
185     OPC_SLLV     = 0x04 | OPC_SPECIAL,
186     OPC_SRLV     = 0x06 | OPC_SPECIAL, /* also ROTRV */
187     OPC_ROTRV    = OPC_SRLV | (1 << 6),
188     OPC_SRAV     = 0x07 | OPC_SPECIAL,
189     OPC_DSLLV    = 0x14 | OPC_SPECIAL,
190     OPC_DSRLV    = 0x16 | OPC_SPECIAL, /* also DROTRV */
191     OPC_DROTRV   = OPC_DSRLV | (1 << 6),
192     OPC_DSRAV    = 0x17 | OPC_SPECIAL,
193     OPC_DSLL     = 0x38 | OPC_SPECIAL,
194     OPC_DSRL     = 0x3A | OPC_SPECIAL, /* also DROTR */
195     OPC_DROTR    = OPC_DSRL | (1 << 21),
196     OPC_DSRA     = 0x3B | OPC_SPECIAL,
197     OPC_DSLL32   = 0x3C | OPC_SPECIAL,
198     OPC_DSRL32   = 0x3E | OPC_SPECIAL, /* also DROTR32 */
199     OPC_DROTR32  = OPC_DSRL32 | (1 << 21),
200     OPC_DSRA32   = 0x3F | OPC_SPECIAL,
201     /* Multiplication / division */
202     OPC_MULT     = 0x18 | OPC_SPECIAL,
203     OPC_MULTU    = 0x19 | OPC_SPECIAL,
204     OPC_DIV      = 0x1A | OPC_SPECIAL,
205     OPC_DIVU     = 0x1B | OPC_SPECIAL,
206     OPC_DMULT    = 0x1C | OPC_SPECIAL,
207     OPC_DMULTU   = 0x1D | OPC_SPECIAL,
208     OPC_DDIV     = 0x1E | OPC_SPECIAL,
209     OPC_DDIVU    = 0x1F | OPC_SPECIAL,
210 
211     /* 2 registers arithmetic / logic */
212     OPC_ADD      = 0x20 | OPC_SPECIAL,
213     OPC_ADDU     = 0x21 | OPC_SPECIAL,
214     OPC_SUB      = 0x22 | OPC_SPECIAL,
215     OPC_SUBU     = 0x23 | OPC_SPECIAL,
216     OPC_AND      = 0x24 | OPC_SPECIAL,
217     OPC_OR       = 0x25 | OPC_SPECIAL,
218     OPC_XOR      = 0x26 | OPC_SPECIAL,
219     OPC_NOR      = 0x27 | OPC_SPECIAL,
220     OPC_SLT      = 0x2A | OPC_SPECIAL,
221     OPC_SLTU     = 0x2B | OPC_SPECIAL,
222     OPC_DADD     = 0x2C | OPC_SPECIAL,
223     OPC_DADDU    = 0x2D | OPC_SPECIAL,
224     OPC_DSUB     = 0x2E | OPC_SPECIAL,
225     OPC_DSUBU    = 0x2F | OPC_SPECIAL,
226     /* Jumps */
227     OPC_JR       = 0x08 | OPC_SPECIAL, /* Also JR.HB */
228     OPC_JALR     = 0x09 | OPC_SPECIAL, /* Also JALR.HB */
229     /* Traps */
230     OPC_TGE      = 0x30 | OPC_SPECIAL,
231     OPC_TGEU     = 0x31 | OPC_SPECIAL,
232     OPC_TLT      = 0x32 | OPC_SPECIAL,
233     OPC_TLTU     = 0x33 | OPC_SPECIAL,
234     OPC_TEQ      = 0x34 | OPC_SPECIAL,
235     OPC_TNE      = 0x36 | OPC_SPECIAL,
236     /* HI / LO registers load & stores */
237     OPC_MFHI     = 0x10 | OPC_SPECIAL,
238     OPC_MTHI     = 0x11 | OPC_SPECIAL,
239     OPC_MFLO     = 0x12 | OPC_SPECIAL,
240     OPC_MTLO     = 0x13 | OPC_SPECIAL,
241     /* Conditional moves */
242     OPC_MOVZ     = 0x0A | OPC_SPECIAL,
243     OPC_MOVN     = 0x0B | OPC_SPECIAL,
244 
245     OPC_SELEQZ   = 0x35 | OPC_SPECIAL,
246     OPC_SELNEZ   = 0x37 | OPC_SPECIAL,
247 
248     OPC_MOVCI    = 0x01 | OPC_SPECIAL,
249 
250     /* Special */
251     OPC_PMON     = 0x05 | OPC_SPECIAL, /* unofficial */
252     OPC_SYSCALL  = 0x0C | OPC_SPECIAL,
253     OPC_BREAK    = 0x0D | OPC_SPECIAL,
254     OPC_SPIM     = 0x0E | OPC_SPECIAL, /* unofficial */
255     OPC_SYNC     = 0x0F | OPC_SPECIAL,
256 
257     OPC_SPECIAL28_RESERVED = 0x28 | OPC_SPECIAL,
258     OPC_SPECIAL29_RESERVED = 0x29 | OPC_SPECIAL,
259     OPC_SPECIAL39_RESERVED = 0x39 | OPC_SPECIAL,
260     OPC_SPECIAL3D_RESERVED = 0x3D | OPC_SPECIAL,
261 };
262 
263 /*
264  * R6 Multiply and Divide instructions have the same opcode
265  * and function field as legacy OPC_MULT[U]/OPC_DIV[U]
266  */
267 #define MASK_R6_MULDIV(op)          (MASK_SPECIAL(op) | (op & (0x7ff)))
268 
269 enum {
270     R6_OPC_MUL   = OPC_MULT  | (2 << 6),
271     R6_OPC_MUH   = OPC_MULT  | (3 << 6),
272     R6_OPC_MULU  = OPC_MULTU | (2 << 6),
273     R6_OPC_MUHU  = OPC_MULTU | (3 << 6),
274     R6_OPC_DIV   = OPC_DIV   | (2 << 6),
275     R6_OPC_MOD   = OPC_DIV   | (3 << 6),
276     R6_OPC_DIVU  = OPC_DIVU  | (2 << 6),
277     R6_OPC_MODU  = OPC_DIVU  | (3 << 6),
278 
279     R6_OPC_DMUL   = OPC_DMULT  | (2 << 6),
280     R6_OPC_DMUH   = OPC_DMULT  | (3 << 6),
281     R6_OPC_DMULU  = OPC_DMULTU | (2 << 6),
282     R6_OPC_DMUHU  = OPC_DMULTU | (3 << 6),
283     R6_OPC_DDIV   = OPC_DDIV   | (2 << 6),
284     R6_OPC_DMOD   = OPC_DDIV   | (3 << 6),
285     R6_OPC_DDIVU  = OPC_DDIVU  | (2 << 6),
286     R6_OPC_DMODU  = OPC_DDIVU  | (3 << 6),
287 
288     R6_OPC_CLZ      = 0x10 | OPC_SPECIAL,
289     R6_OPC_CLO      = 0x11 | OPC_SPECIAL,
290     R6_OPC_DCLZ     = 0x12 | OPC_SPECIAL,
291     R6_OPC_DCLO     = 0x13 | OPC_SPECIAL,
292     R6_OPC_SDBBP    = 0x0e | OPC_SPECIAL,
293 };
294 
295 /* REGIMM (rt field) opcodes */
296 #define MASK_REGIMM(op)             (MASK_OP_MAJOR(op) | (op & (0x1F << 16)))
297 
298 enum {
299     OPC_BLTZ     = (0x00 << 16) | OPC_REGIMM,
300     OPC_BLTZL    = (0x02 << 16) | OPC_REGIMM,
301     OPC_BGEZ     = (0x01 << 16) | OPC_REGIMM,
302     OPC_BGEZL    = (0x03 << 16) | OPC_REGIMM,
303     OPC_BLTZAL   = (0x10 << 16) | OPC_REGIMM,
304     OPC_BLTZALL  = (0x12 << 16) | OPC_REGIMM,
305     OPC_BGEZAL   = (0x11 << 16) | OPC_REGIMM,
306     OPC_BGEZALL  = (0x13 << 16) | OPC_REGIMM,
307     OPC_TGEI     = (0x08 << 16) | OPC_REGIMM,
308     OPC_TGEIU    = (0x09 << 16) | OPC_REGIMM,
309     OPC_TLTI     = (0x0A << 16) | OPC_REGIMM,
310     OPC_TLTIU    = (0x0B << 16) | OPC_REGIMM,
311     OPC_TEQI     = (0x0C << 16) | OPC_REGIMM,
312     OPC_TNEI     = (0x0E << 16) | OPC_REGIMM,
313     OPC_SIGRIE   = (0x17 << 16) | OPC_REGIMM,
314     OPC_SYNCI    = (0x1F << 16) | OPC_REGIMM,
315 
316     OPC_DAHI     = (0x06 << 16) | OPC_REGIMM,
317     OPC_DATI     = (0x1e << 16) | OPC_REGIMM,
318 };
319 
320 /* Special2 opcodes */
321 #define MASK_SPECIAL2(op)           (MASK_OP_MAJOR(op) | (op & 0x3F))
322 
323 enum {
324     /* Multiply & xxx operations */
325     OPC_MADD     = 0x00 | OPC_SPECIAL2,
326     OPC_MADDU    = 0x01 | OPC_SPECIAL2,
327     OPC_MUL      = 0x02 | OPC_SPECIAL2,
328     OPC_MSUB     = 0x04 | OPC_SPECIAL2,
329     OPC_MSUBU    = 0x05 | OPC_SPECIAL2,
330     /* Loongson 2F */
331     OPC_MULT_G_2F   = 0x10 | OPC_SPECIAL2,
332     OPC_DMULT_G_2F  = 0x11 | OPC_SPECIAL2,
333     OPC_MULTU_G_2F  = 0x12 | OPC_SPECIAL2,
334     OPC_DMULTU_G_2F = 0x13 | OPC_SPECIAL2,
335     /* Misc */
336     OPC_CLZ      = 0x20 | OPC_SPECIAL2,
337     OPC_CLO      = 0x21 | OPC_SPECIAL2,
338     OPC_DCLZ     = 0x24 | OPC_SPECIAL2,
339     OPC_DCLO     = 0x25 | OPC_SPECIAL2,
340     /* Special */
341     OPC_SDBBP    = 0x3F | OPC_SPECIAL2,
342 };
343 
344 /* Special3 opcodes */
345 #define MASK_SPECIAL3(op)           (MASK_OP_MAJOR(op) | (op & 0x3F))
346 
347 enum {
348     OPC_EXT      = 0x00 | OPC_SPECIAL3,
349     OPC_DEXTM    = 0x01 | OPC_SPECIAL3,
350     OPC_DEXTU    = 0x02 | OPC_SPECIAL3,
351     OPC_DEXT     = 0x03 | OPC_SPECIAL3,
352     OPC_INS      = 0x04 | OPC_SPECIAL3,
353     OPC_DINSM    = 0x05 | OPC_SPECIAL3,
354     OPC_DINSU    = 0x06 | OPC_SPECIAL3,
355     OPC_DINS     = 0x07 | OPC_SPECIAL3,
356     OPC_FORK     = 0x08 | OPC_SPECIAL3,
357     OPC_YIELD    = 0x09 | OPC_SPECIAL3,
358     OPC_BSHFL    = 0x20 | OPC_SPECIAL3,
359     OPC_DBSHFL   = 0x24 | OPC_SPECIAL3,
360     OPC_RDHWR    = 0x3B | OPC_SPECIAL3,
361     OPC_GINV     = 0x3D | OPC_SPECIAL3,
362 
363     /* Loongson 2E */
364     OPC_MULT_G_2E   = 0x18 | OPC_SPECIAL3,
365     OPC_MULTU_G_2E  = 0x19 | OPC_SPECIAL3,
366     OPC_DMULT_G_2E  = 0x1C | OPC_SPECIAL3,
367     OPC_DMULTU_G_2E = 0x1D | OPC_SPECIAL3,
368 
369     /* MIPS DSP Load */
370     OPC_LX_DSP         = 0x0A | OPC_SPECIAL3,
371     /* MIPS DSP Arithmetic */
372     OPC_ADDU_QB_DSP    = 0x10 | OPC_SPECIAL3,
373     OPC_ADDU_OB_DSP    = 0x14 | OPC_SPECIAL3,
374     OPC_ABSQ_S_PH_DSP  = 0x12 | OPC_SPECIAL3,
375     OPC_ABSQ_S_QH_DSP  = 0x16 | OPC_SPECIAL3,
376     OPC_ADDUH_QB_DSP   = 0x18 | OPC_SPECIAL3,
377     OPC_CMPU_EQ_QB_DSP = 0x11 | OPC_SPECIAL3,
378     OPC_CMPU_EQ_OB_DSP = 0x15 | OPC_SPECIAL3,
379     /* MIPS DSP GPR-Based Shift Sub-class */
380     OPC_SHLL_QB_DSP    = 0x13 | OPC_SPECIAL3,
381     OPC_SHLL_OB_DSP    = 0x17 | OPC_SPECIAL3,
382     /* MIPS DSP Multiply Sub-class insns */
383     OPC_MUL_PH_DSP     = 0x18 | OPC_SPECIAL3,
384     OPC_DPA_W_PH_DSP   = 0x30 | OPC_SPECIAL3,
385     OPC_DPAQ_W_QH_DSP  = 0x34 | OPC_SPECIAL3,
386     /* DSP Bit/Manipulation Sub-class */
387     OPC_INSV_DSP       = 0x0C | OPC_SPECIAL3,
388     OPC_DINSV_DSP      = 0x0D | OPC_SPECIAL3,
389     /* MIPS DSP Append Sub-class */
390     OPC_APPEND_DSP     = 0x31 | OPC_SPECIAL3,
391     OPC_DAPPEND_DSP    = 0x35 | OPC_SPECIAL3,
392     /* MIPS DSP Accumulator and DSPControl Access Sub-class */
393     OPC_EXTR_W_DSP     = 0x38 | OPC_SPECIAL3,
394     OPC_DEXTR_W_DSP    = 0x3C | OPC_SPECIAL3,
395 
396     /* EVA */
397     OPC_LWLE           = 0x19 | OPC_SPECIAL3,
398     OPC_LWRE           = 0x1A | OPC_SPECIAL3,
399     OPC_CACHEE         = 0x1B | OPC_SPECIAL3,
400     OPC_SBE            = 0x1C | OPC_SPECIAL3,
401     OPC_SHE            = 0x1D | OPC_SPECIAL3,
402     OPC_SCE            = 0x1E | OPC_SPECIAL3,
403     OPC_SWE            = 0x1F | OPC_SPECIAL3,
404     OPC_SWLE           = 0x21 | OPC_SPECIAL3,
405     OPC_SWRE           = 0x22 | OPC_SPECIAL3,
406     OPC_PREFE          = 0x23 | OPC_SPECIAL3,
407     OPC_LBUE           = 0x28 | OPC_SPECIAL3,
408     OPC_LHUE           = 0x29 | OPC_SPECIAL3,
409     OPC_LBE            = 0x2C | OPC_SPECIAL3,
410     OPC_LHE            = 0x2D | OPC_SPECIAL3,
411     OPC_LLE            = 0x2E | OPC_SPECIAL3,
412     OPC_LWE            = 0x2F | OPC_SPECIAL3,
413 
414     /* R6 */
415     R6_OPC_PREF        = 0x35 | OPC_SPECIAL3,
416     R6_OPC_CACHE       = 0x25 | OPC_SPECIAL3,
417     R6_OPC_LL          = 0x36 | OPC_SPECIAL3,
418     R6_OPC_SC          = 0x26 | OPC_SPECIAL3,
419     R6_OPC_LLD         = 0x37 | OPC_SPECIAL3,
420     R6_OPC_SCD         = 0x27 | OPC_SPECIAL3,
421 };
422 
423 /* Loongson EXT load/store quad word opcodes */
424 #define MASK_LOONGSON_GSLSQ(op)           (MASK_OP_MAJOR(op) | (op & 0x8020))
425 enum {
426     OPC_GSLQ        = 0x0020 | OPC_LWC2,
427     OPC_GSLQC1      = 0x8020 | OPC_LWC2,
428     OPC_GSSHFL      = OPC_LWC2,
429     OPC_GSSQ        = 0x0020 | OPC_SWC2,
430     OPC_GSSQC1      = 0x8020 | OPC_SWC2,
431     OPC_GSSHFS      = OPC_SWC2,
432 };
433 
434 /* Loongson EXT shifted load/store opcodes */
435 #define MASK_LOONGSON_GSSHFLS(op)         (MASK_OP_MAJOR(op) | (op & 0xc03f))
436 enum {
437     OPC_GSLWLC1     = 0x4 | OPC_GSSHFL,
438     OPC_GSLWRC1     = 0x5 | OPC_GSSHFL,
439     OPC_GSLDLC1     = 0x6 | OPC_GSSHFL,
440     OPC_GSLDRC1     = 0x7 | OPC_GSSHFL,
441     OPC_GSSWLC1     = 0x4 | OPC_GSSHFS,
442     OPC_GSSWRC1     = 0x5 | OPC_GSSHFS,
443     OPC_GSSDLC1     = 0x6 | OPC_GSSHFS,
444     OPC_GSSDRC1     = 0x7 | OPC_GSSHFS,
445 };
446 
447 /* Loongson EXT LDC2/SDC2 opcodes */
448 #define MASK_LOONGSON_LSDC2(op)           (MASK_OP_MAJOR(op) | (op & 0x7))
449 
450 enum {
451     OPC_GSLBX      = 0x0 | OPC_LDC2,
452     OPC_GSLHX      = 0x1 | OPC_LDC2,
453     OPC_GSLWX      = 0x2 | OPC_LDC2,
454     OPC_GSLDX      = 0x3 | OPC_LDC2,
455     OPC_GSLWXC1    = 0x6 | OPC_LDC2,
456     OPC_GSLDXC1    = 0x7 | OPC_LDC2,
457     OPC_GSSBX      = 0x0 | OPC_SDC2,
458     OPC_GSSHX      = 0x1 | OPC_SDC2,
459     OPC_GSSWX      = 0x2 | OPC_SDC2,
460     OPC_GSSDX      = 0x3 | OPC_SDC2,
461     OPC_GSSWXC1    = 0x6 | OPC_SDC2,
462     OPC_GSSDXC1    = 0x7 | OPC_SDC2,
463 };
464 
465 /* BSHFL opcodes */
466 #define MASK_BSHFL(op)              (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
467 
468 enum {
469     OPC_WSBH      = (0x02 << 6) | OPC_BSHFL,
470     OPC_SEB       = (0x10 << 6) | OPC_BSHFL,
471     OPC_SEH       = (0x18 << 6) | OPC_BSHFL,
472     OPC_ALIGN     = (0x08 << 6) | OPC_BSHFL, /* 010.bp (010.00 to 010.11) */
473     OPC_ALIGN_1   = (0x09 << 6) | OPC_BSHFL,
474     OPC_ALIGN_2   = (0x0A << 6) | OPC_BSHFL,
475     OPC_ALIGN_3   = (0x0B << 6) | OPC_BSHFL,
476     OPC_BITSWAP   = (0x00 << 6) | OPC_BSHFL  /* 00000 */
477 };
478 
479 /* DBSHFL opcodes */
480 #define MASK_DBSHFL(op)             (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
481 
482 enum {
483     OPC_DSBH       = (0x02 << 6) | OPC_DBSHFL,
484     OPC_DSHD       = (0x05 << 6) | OPC_DBSHFL,
485     OPC_DALIGN     = (0x08 << 6) | OPC_DBSHFL, /* 01.bp (01.000 to 01.111) */
486     OPC_DALIGN_1   = (0x09 << 6) | OPC_DBSHFL,
487     OPC_DALIGN_2   = (0x0A << 6) | OPC_DBSHFL,
488     OPC_DALIGN_3   = (0x0B << 6) | OPC_DBSHFL,
489     OPC_DALIGN_4   = (0x0C << 6) | OPC_DBSHFL,
490     OPC_DALIGN_5   = (0x0D << 6) | OPC_DBSHFL,
491     OPC_DALIGN_6   = (0x0E << 6) | OPC_DBSHFL,
492     OPC_DALIGN_7   = (0x0F << 6) | OPC_DBSHFL,
493     OPC_DBITSWAP   = (0x00 << 6) | OPC_DBSHFL, /* 00000 */
494 };
495 
496 /* MIPS DSP REGIMM opcodes */
497 enum {
498     OPC_BPOSGE32 = (0x1C << 16) | OPC_REGIMM,
499     OPC_BPOSGE64 = (0x1D << 16) | OPC_REGIMM,
500 };
501 
502 #define MASK_LX(op)                 (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
503 /* MIPS DSP Load */
504 enum {
505     OPC_LBUX = (0x06 << 6) | OPC_LX_DSP,
506     OPC_LHX  = (0x04 << 6) | OPC_LX_DSP,
507     OPC_LWX  = (0x00 << 6) | OPC_LX_DSP,
508     OPC_LDX = (0x08 << 6) | OPC_LX_DSP,
509 };
510 
511 #define MASK_ADDU_QB(op)            (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
512 enum {
513     /* MIPS DSP Arithmetic Sub-class */
514     OPC_ADDQ_PH        = (0x0A << 6) | OPC_ADDU_QB_DSP,
515     OPC_ADDQ_S_PH      = (0x0E << 6) | OPC_ADDU_QB_DSP,
516     OPC_ADDQ_S_W       = (0x16 << 6) | OPC_ADDU_QB_DSP,
517     OPC_ADDU_QB        = (0x00 << 6) | OPC_ADDU_QB_DSP,
518     OPC_ADDU_S_QB      = (0x04 << 6) | OPC_ADDU_QB_DSP,
519     OPC_ADDU_PH        = (0x08 << 6) | OPC_ADDU_QB_DSP,
520     OPC_ADDU_S_PH      = (0x0C << 6) | OPC_ADDU_QB_DSP,
521     OPC_SUBQ_PH        = (0x0B << 6) | OPC_ADDU_QB_DSP,
522     OPC_SUBQ_S_PH      = (0x0F << 6) | OPC_ADDU_QB_DSP,
523     OPC_SUBQ_S_W       = (0x17 << 6) | OPC_ADDU_QB_DSP,
524     OPC_SUBU_QB        = (0x01 << 6) | OPC_ADDU_QB_DSP,
525     OPC_SUBU_S_QB      = (0x05 << 6) | OPC_ADDU_QB_DSP,
526     OPC_SUBU_PH        = (0x09 << 6) | OPC_ADDU_QB_DSP,
527     OPC_SUBU_S_PH      = (0x0D << 6) | OPC_ADDU_QB_DSP,
528     OPC_ADDSC          = (0x10 << 6) | OPC_ADDU_QB_DSP,
529     OPC_ADDWC          = (0x11 << 6) | OPC_ADDU_QB_DSP,
530     OPC_MODSUB         = (0x12 << 6) | OPC_ADDU_QB_DSP,
531     OPC_RADDU_W_QB     = (0x14 << 6) | OPC_ADDU_QB_DSP,
532     /* MIPS DSP Multiply Sub-class insns */
533     OPC_MULEU_S_PH_QBL = (0x06 << 6) | OPC_ADDU_QB_DSP,
534     OPC_MULEU_S_PH_QBR = (0x07 << 6) | OPC_ADDU_QB_DSP,
535     OPC_MULQ_RS_PH     = (0x1F << 6) | OPC_ADDU_QB_DSP,
536     OPC_MULEQ_S_W_PHL  = (0x1C << 6) | OPC_ADDU_QB_DSP,
537     OPC_MULEQ_S_W_PHR  = (0x1D << 6) | OPC_ADDU_QB_DSP,
538     OPC_MULQ_S_PH      = (0x1E << 6) | OPC_ADDU_QB_DSP,
539 };
540 
541 #define MASK_ADDUH_QB(op)           (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
542 enum {
543     /* MIPS DSP Arithmetic Sub-class */
544     OPC_ADDUH_QB   = (0x00 << 6) | OPC_ADDUH_QB_DSP,
545     OPC_ADDUH_R_QB = (0x02 << 6) | OPC_ADDUH_QB_DSP,
546     OPC_ADDQH_PH   = (0x08 << 6) | OPC_ADDUH_QB_DSP,
547     OPC_ADDQH_R_PH = (0x0A << 6) | OPC_ADDUH_QB_DSP,
548     OPC_ADDQH_W    = (0x10 << 6) | OPC_ADDUH_QB_DSP,
549     OPC_ADDQH_R_W  = (0x12 << 6) | OPC_ADDUH_QB_DSP,
550     OPC_SUBUH_QB   = (0x01 << 6) | OPC_ADDUH_QB_DSP,
551     OPC_SUBUH_R_QB = (0x03 << 6) | OPC_ADDUH_QB_DSP,
552     OPC_SUBQH_PH   = (0x09 << 6) | OPC_ADDUH_QB_DSP,
553     OPC_SUBQH_R_PH = (0x0B << 6) | OPC_ADDUH_QB_DSP,
554     OPC_SUBQH_W    = (0x11 << 6) | OPC_ADDUH_QB_DSP,
555     OPC_SUBQH_R_W  = (0x13 << 6) | OPC_ADDUH_QB_DSP,
556     /* MIPS DSP Multiply Sub-class insns */
557     OPC_MUL_PH     = (0x0C << 6) | OPC_ADDUH_QB_DSP,
558     OPC_MUL_S_PH   = (0x0E << 6) | OPC_ADDUH_QB_DSP,
559     OPC_MULQ_S_W   = (0x16 << 6) | OPC_ADDUH_QB_DSP,
560     OPC_MULQ_RS_W  = (0x17 << 6) | OPC_ADDUH_QB_DSP,
561 };
562 
563 #define MASK_ABSQ_S_PH(op)          (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
564 enum {
565     /* MIPS DSP Arithmetic Sub-class */
566     OPC_ABSQ_S_QB       = (0x01 << 6) | OPC_ABSQ_S_PH_DSP,
567     OPC_ABSQ_S_PH       = (0x09 << 6) | OPC_ABSQ_S_PH_DSP,
568     OPC_ABSQ_S_W        = (0x11 << 6) | OPC_ABSQ_S_PH_DSP,
569     OPC_PRECEQ_W_PHL    = (0x0C << 6) | OPC_ABSQ_S_PH_DSP,
570     OPC_PRECEQ_W_PHR    = (0x0D << 6) | OPC_ABSQ_S_PH_DSP,
571     OPC_PRECEQU_PH_QBL  = (0x04 << 6) | OPC_ABSQ_S_PH_DSP,
572     OPC_PRECEQU_PH_QBR  = (0x05 << 6) | OPC_ABSQ_S_PH_DSP,
573     OPC_PRECEQU_PH_QBLA = (0x06 << 6) | OPC_ABSQ_S_PH_DSP,
574     OPC_PRECEQU_PH_QBRA = (0x07 << 6) | OPC_ABSQ_S_PH_DSP,
575     OPC_PRECEU_PH_QBL   = (0x1C << 6) | OPC_ABSQ_S_PH_DSP,
576     OPC_PRECEU_PH_QBR   = (0x1D << 6) | OPC_ABSQ_S_PH_DSP,
577     OPC_PRECEU_PH_QBLA  = (0x1E << 6) | OPC_ABSQ_S_PH_DSP,
578     OPC_PRECEU_PH_QBRA  = (0x1F << 6) | OPC_ABSQ_S_PH_DSP,
579     /* DSP Bit/Manipulation Sub-class */
580     OPC_BITREV          = (0x1B << 6) | OPC_ABSQ_S_PH_DSP,
581     OPC_REPL_QB         = (0x02 << 6) | OPC_ABSQ_S_PH_DSP,
582     OPC_REPLV_QB        = (0x03 << 6) | OPC_ABSQ_S_PH_DSP,
583     OPC_REPL_PH         = (0x0A << 6) | OPC_ABSQ_S_PH_DSP,
584     OPC_REPLV_PH        = (0x0B << 6) | OPC_ABSQ_S_PH_DSP,
585 };
586 
587 #define MASK_CMPU_EQ_QB(op)         (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
588 enum {
589     /* MIPS DSP Arithmetic Sub-class */
590     OPC_PRECR_QB_PH      = (0x0D << 6) | OPC_CMPU_EQ_QB_DSP,
591     OPC_PRECRQ_QB_PH     = (0x0C << 6) | OPC_CMPU_EQ_QB_DSP,
592     OPC_PRECR_SRA_PH_W   = (0x1E << 6) | OPC_CMPU_EQ_QB_DSP,
593     OPC_PRECR_SRA_R_PH_W = (0x1F << 6) | OPC_CMPU_EQ_QB_DSP,
594     OPC_PRECRQ_PH_W      = (0x14 << 6) | OPC_CMPU_EQ_QB_DSP,
595     OPC_PRECRQ_RS_PH_W   = (0x15 << 6) | OPC_CMPU_EQ_QB_DSP,
596     OPC_PRECRQU_S_QB_PH  = (0x0F << 6) | OPC_CMPU_EQ_QB_DSP,
597     /* DSP Compare-Pick Sub-class */
598     OPC_CMPU_EQ_QB       = (0x00 << 6) | OPC_CMPU_EQ_QB_DSP,
599     OPC_CMPU_LT_QB       = (0x01 << 6) | OPC_CMPU_EQ_QB_DSP,
600     OPC_CMPU_LE_QB       = (0x02 << 6) | OPC_CMPU_EQ_QB_DSP,
601     OPC_CMPGU_EQ_QB      = (0x04 << 6) | OPC_CMPU_EQ_QB_DSP,
602     OPC_CMPGU_LT_QB      = (0x05 << 6) | OPC_CMPU_EQ_QB_DSP,
603     OPC_CMPGU_LE_QB      = (0x06 << 6) | OPC_CMPU_EQ_QB_DSP,
604     OPC_CMPGDU_EQ_QB     = (0x18 << 6) | OPC_CMPU_EQ_QB_DSP,
605     OPC_CMPGDU_LT_QB     = (0x19 << 6) | OPC_CMPU_EQ_QB_DSP,
606     OPC_CMPGDU_LE_QB     = (0x1A << 6) | OPC_CMPU_EQ_QB_DSP,
607     OPC_CMP_EQ_PH        = (0x08 << 6) | OPC_CMPU_EQ_QB_DSP,
608     OPC_CMP_LT_PH        = (0x09 << 6) | OPC_CMPU_EQ_QB_DSP,
609     OPC_CMP_LE_PH        = (0x0A << 6) | OPC_CMPU_EQ_QB_DSP,
610     OPC_PICK_QB          = (0x03 << 6) | OPC_CMPU_EQ_QB_DSP,
611     OPC_PICK_PH          = (0x0B << 6) | OPC_CMPU_EQ_QB_DSP,
612     OPC_PACKRL_PH        = (0x0E << 6) | OPC_CMPU_EQ_QB_DSP,
613 };
614 
615 #define MASK_SHLL_QB(op)            (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
616 enum {
617     /* MIPS DSP GPR-Based Shift Sub-class */
618     OPC_SHLL_QB    = (0x00 << 6) | OPC_SHLL_QB_DSP,
619     OPC_SHLLV_QB   = (0x02 << 6) | OPC_SHLL_QB_DSP,
620     OPC_SHLL_PH    = (0x08 << 6) | OPC_SHLL_QB_DSP,
621     OPC_SHLLV_PH   = (0x0A << 6) | OPC_SHLL_QB_DSP,
622     OPC_SHLL_S_PH  = (0x0C << 6) | OPC_SHLL_QB_DSP,
623     OPC_SHLLV_S_PH = (0x0E << 6) | OPC_SHLL_QB_DSP,
624     OPC_SHLL_S_W   = (0x14 << 6) | OPC_SHLL_QB_DSP,
625     OPC_SHLLV_S_W  = (0x16 << 6) | OPC_SHLL_QB_DSP,
626     OPC_SHRL_QB    = (0x01 << 6) | OPC_SHLL_QB_DSP,
627     OPC_SHRLV_QB   = (0x03 << 6) | OPC_SHLL_QB_DSP,
628     OPC_SHRL_PH    = (0x19 << 6) | OPC_SHLL_QB_DSP,
629     OPC_SHRLV_PH   = (0x1B << 6) | OPC_SHLL_QB_DSP,
630     OPC_SHRA_QB    = (0x04 << 6) | OPC_SHLL_QB_DSP,
631     OPC_SHRA_R_QB  = (0x05 << 6) | OPC_SHLL_QB_DSP,
632     OPC_SHRAV_QB   = (0x06 << 6) | OPC_SHLL_QB_DSP,
633     OPC_SHRAV_R_QB = (0x07 << 6) | OPC_SHLL_QB_DSP,
634     OPC_SHRA_PH    = (0x09 << 6) | OPC_SHLL_QB_DSP,
635     OPC_SHRAV_PH   = (0x0B << 6) | OPC_SHLL_QB_DSP,
636     OPC_SHRA_R_PH  = (0x0D << 6) | OPC_SHLL_QB_DSP,
637     OPC_SHRAV_R_PH = (0x0F << 6) | OPC_SHLL_QB_DSP,
638     OPC_SHRA_R_W   = (0x15 << 6) | OPC_SHLL_QB_DSP,
639     OPC_SHRAV_R_W  = (0x17 << 6) | OPC_SHLL_QB_DSP,
640 };
641 
642 #define MASK_DPA_W_PH(op)           (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
643 enum {
644     /* MIPS DSP Multiply Sub-class insns */
645     OPC_DPAU_H_QBL    = (0x03 << 6) | OPC_DPA_W_PH_DSP,
646     OPC_DPAU_H_QBR    = (0x07 << 6) | OPC_DPA_W_PH_DSP,
647     OPC_DPSU_H_QBL    = (0x0B << 6) | OPC_DPA_W_PH_DSP,
648     OPC_DPSU_H_QBR    = (0x0F << 6) | OPC_DPA_W_PH_DSP,
649     OPC_DPA_W_PH      = (0x00 << 6) | OPC_DPA_W_PH_DSP,
650     OPC_DPAX_W_PH     = (0x08 << 6) | OPC_DPA_W_PH_DSP,
651     OPC_DPAQ_S_W_PH   = (0x04 << 6) | OPC_DPA_W_PH_DSP,
652     OPC_DPAQX_S_W_PH  = (0x18 << 6) | OPC_DPA_W_PH_DSP,
653     OPC_DPAQX_SA_W_PH = (0x1A << 6) | OPC_DPA_W_PH_DSP,
654     OPC_DPS_W_PH      = (0x01 << 6) | OPC_DPA_W_PH_DSP,
655     OPC_DPSX_W_PH     = (0x09 << 6) | OPC_DPA_W_PH_DSP,
656     OPC_DPSQ_S_W_PH   = (0x05 << 6) | OPC_DPA_W_PH_DSP,
657     OPC_DPSQX_S_W_PH  = (0x19 << 6) | OPC_DPA_W_PH_DSP,
658     OPC_DPSQX_SA_W_PH = (0x1B << 6) | OPC_DPA_W_PH_DSP,
659     OPC_MULSAQ_S_W_PH = (0x06 << 6) | OPC_DPA_W_PH_DSP,
660     OPC_DPAQ_SA_L_W   = (0x0C << 6) | OPC_DPA_W_PH_DSP,
661     OPC_DPSQ_SA_L_W   = (0x0D << 6) | OPC_DPA_W_PH_DSP,
662     OPC_MAQ_S_W_PHL   = (0x14 << 6) | OPC_DPA_W_PH_DSP,
663     OPC_MAQ_S_W_PHR   = (0x16 << 6) | OPC_DPA_W_PH_DSP,
664     OPC_MAQ_SA_W_PHL  = (0x10 << 6) | OPC_DPA_W_PH_DSP,
665     OPC_MAQ_SA_W_PHR  = (0x12 << 6) | OPC_DPA_W_PH_DSP,
666     OPC_MULSA_W_PH    = (0x02 << 6) | OPC_DPA_W_PH_DSP,
667 };
668 
669 #define MASK_INSV(op)               (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
670 enum {
671     /* DSP Bit/Manipulation Sub-class */
672     OPC_INSV = (0x00 << 6) | OPC_INSV_DSP,
673 };
674 
675 #define MASK_APPEND(op)             (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
676 enum {
677     /* MIPS DSP Append Sub-class */
678     OPC_APPEND  = (0x00 << 6) | OPC_APPEND_DSP,
679     OPC_PREPEND = (0x01 << 6) | OPC_APPEND_DSP,
680     OPC_BALIGN  = (0x10 << 6) | OPC_APPEND_DSP,
681 };
682 
683 #define MASK_EXTR_W(op)             (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
684 enum {
685     /* MIPS DSP Accumulator and DSPControl Access Sub-class */
686     OPC_EXTR_W     = (0x00 << 6) | OPC_EXTR_W_DSP,
687     OPC_EXTR_R_W   = (0x04 << 6) | OPC_EXTR_W_DSP,
688     OPC_EXTR_RS_W  = (0x06 << 6) | OPC_EXTR_W_DSP,
689     OPC_EXTR_S_H   = (0x0E << 6) | OPC_EXTR_W_DSP,
690     OPC_EXTRV_S_H  = (0x0F << 6) | OPC_EXTR_W_DSP,
691     OPC_EXTRV_W    = (0x01 << 6) | OPC_EXTR_W_DSP,
692     OPC_EXTRV_R_W  = (0x05 << 6) | OPC_EXTR_W_DSP,
693     OPC_EXTRV_RS_W = (0x07 << 6) | OPC_EXTR_W_DSP,
694     OPC_EXTP       = (0x02 << 6) | OPC_EXTR_W_DSP,
695     OPC_EXTPV      = (0x03 << 6) | OPC_EXTR_W_DSP,
696     OPC_EXTPDP     = (0x0A << 6) | OPC_EXTR_W_DSP,
697     OPC_EXTPDPV    = (0x0B << 6) | OPC_EXTR_W_DSP,
698     OPC_SHILO      = (0x1A << 6) | OPC_EXTR_W_DSP,
699     OPC_SHILOV     = (0x1B << 6) | OPC_EXTR_W_DSP,
700     OPC_MTHLIP     = (0x1F << 6) | OPC_EXTR_W_DSP,
701     OPC_WRDSP      = (0x13 << 6) | OPC_EXTR_W_DSP,
702     OPC_RDDSP      = (0x12 << 6) | OPC_EXTR_W_DSP,
703 };
704 
705 #define MASK_ABSQ_S_QH(op)          (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
706 enum {
707     /* MIPS DSP Arithmetic Sub-class */
708     OPC_PRECEQ_L_PWL    = (0x14 << 6) | OPC_ABSQ_S_QH_DSP,
709     OPC_PRECEQ_L_PWR    = (0x15 << 6) | OPC_ABSQ_S_QH_DSP,
710     OPC_PRECEQ_PW_QHL   = (0x0C << 6) | OPC_ABSQ_S_QH_DSP,
711     OPC_PRECEQ_PW_QHR   = (0x0D << 6) | OPC_ABSQ_S_QH_DSP,
712     OPC_PRECEQ_PW_QHLA  = (0x0E << 6) | OPC_ABSQ_S_QH_DSP,
713     OPC_PRECEQ_PW_QHRA  = (0x0F << 6) | OPC_ABSQ_S_QH_DSP,
714     OPC_PRECEQU_QH_OBL  = (0x04 << 6) | OPC_ABSQ_S_QH_DSP,
715     OPC_PRECEQU_QH_OBR  = (0x05 << 6) | OPC_ABSQ_S_QH_DSP,
716     OPC_PRECEQU_QH_OBLA = (0x06 << 6) | OPC_ABSQ_S_QH_DSP,
717     OPC_PRECEQU_QH_OBRA = (0x07 << 6) | OPC_ABSQ_S_QH_DSP,
718     OPC_PRECEU_QH_OBL   = (0x1C << 6) | OPC_ABSQ_S_QH_DSP,
719     OPC_PRECEU_QH_OBR   = (0x1D << 6) | OPC_ABSQ_S_QH_DSP,
720     OPC_PRECEU_QH_OBLA  = (0x1E << 6) | OPC_ABSQ_S_QH_DSP,
721     OPC_PRECEU_QH_OBRA  = (0x1F << 6) | OPC_ABSQ_S_QH_DSP,
722     OPC_ABSQ_S_OB       = (0x01 << 6) | OPC_ABSQ_S_QH_DSP,
723     OPC_ABSQ_S_PW       = (0x11 << 6) | OPC_ABSQ_S_QH_DSP,
724     OPC_ABSQ_S_QH       = (0x09 << 6) | OPC_ABSQ_S_QH_DSP,
725     /* DSP Bit/Manipulation Sub-class */
726     OPC_REPL_OB         = (0x02 << 6) | OPC_ABSQ_S_QH_DSP,
727     OPC_REPL_PW         = (0x12 << 6) | OPC_ABSQ_S_QH_DSP,
728     OPC_REPL_QH         = (0x0A << 6) | OPC_ABSQ_S_QH_DSP,
729     OPC_REPLV_OB        = (0x03 << 6) | OPC_ABSQ_S_QH_DSP,
730     OPC_REPLV_PW        = (0x13 << 6) | OPC_ABSQ_S_QH_DSP,
731     OPC_REPLV_QH        = (0x0B << 6) | OPC_ABSQ_S_QH_DSP,
732 };
733 
734 #define MASK_ADDU_OB(op)            (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
735 enum {
736     /* MIPS DSP Multiply Sub-class insns */
737     OPC_MULEQ_S_PW_QHL = (0x1C << 6) | OPC_ADDU_OB_DSP,
738     OPC_MULEQ_S_PW_QHR = (0x1D << 6) | OPC_ADDU_OB_DSP,
739     OPC_MULEU_S_QH_OBL = (0x06 << 6) | OPC_ADDU_OB_DSP,
740     OPC_MULEU_S_QH_OBR = (0x07 << 6) | OPC_ADDU_OB_DSP,
741     OPC_MULQ_RS_QH     = (0x1F << 6) | OPC_ADDU_OB_DSP,
742     /* MIPS DSP Arithmetic Sub-class */
743     OPC_RADDU_L_OB     = (0x14 << 6) | OPC_ADDU_OB_DSP,
744     OPC_SUBQ_PW        = (0x13 << 6) | OPC_ADDU_OB_DSP,
745     OPC_SUBQ_S_PW      = (0x17 << 6) | OPC_ADDU_OB_DSP,
746     OPC_SUBQ_QH        = (0x0B << 6) | OPC_ADDU_OB_DSP,
747     OPC_SUBQ_S_QH      = (0x0F << 6) | OPC_ADDU_OB_DSP,
748     OPC_SUBU_OB        = (0x01 << 6) | OPC_ADDU_OB_DSP,
749     OPC_SUBU_S_OB      = (0x05 << 6) | OPC_ADDU_OB_DSP,
750     OPC_SUBU_QH        = (0x09 << 6) | OPC_ADDU_OB_DSP,
751     OPC_SUBU_S_QH      = (0x0D << 6) | OPC_ADDU_OB_DSP,
752     OPC_SUBUH_OB       = (0x19 << 6) | OPC_ADDU_OB_DSP,
753     OPC_SUBUH_R_OB     = (0x1B << 6) | OPC_ADDU_OB_DSP,
754     OPC_ADDQ_PW        = (0x12 << 6) | OPC_ADDU_OB_DSP,
755     OPC_ADDQ_S_PW      = (0x16 << 6) | OPC_ADDU_OB_DSP,
756     OPC_ADDQ_QH        = (0x0A << 6) | OPC_ADDU_OB_DSP,
757     OPC_ADDQ_S_QH      = (0x0E << 6) | OPC_ADDU_OB_DSP,
758     OPC_ADDU_OB        = (0x00 << 6) | OPC_ADDU_OB_DSP,
759     OPC_ADDU_S_OB      = (0x04 << 6) | OPC_ADDU_OB_DSP,
760     OPC_ADDU_QH        = (0x08 << 6) | OPC_ADDU_OB_DSP,
761     OPC_ADDU_S_QH      = (0x0C << 6) | OPC_ADDU_OB_DSP,
762     OPC_ADDUH_OB       = (0x18 << 6) | OPC_ADDU_OB_DSP,
763     OPC_ADDUH_R_OB     = (0x1A << 6) | OPC_ADDU_OB_DSP,
764 };
765 
766 #define MASK_CMPU_EQ_OB(op)         (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
767 enum {
768     /* DSP Compare-Pick Sub-class */
769     OPC_CMP_EQ_PW         = (0x10 << 6) | OPC_CMPU_EQ_OB_DSP,
770     OPC_CMP_LT_PW         = (0x11 << 6) | OPC_CMPU_EQ_OB_DSP,
771     OPC_CMP_LE_PW         = (0x12 << 6) | OPC_CMPU_EQ_OB_DSP,
772     OPC_CMP_EQ_QH         = (0x08 << 6) | OPC_CMPU_EQ_OB_DSP,
773     OPC_CMP_LT_QH         = (0x09 << 6) | OPC_CMPU_EQ_OB_DSP,
774     OPC_CMP_LE_QH         = (0x0A << 6) | OPC_CMPU_EQ_OB_DSP,
775     OPC_CMPGDU_EQ_OB      = (0x18 << 6) | OPC_CMPU_EQ_OB_DSP,
776     OPC_CMPGDU_LT_OB      = (0x19 << 6) | OPC_CMPU_EQ_OB_DSP,
777     OPC_CMPGDU_LE_OB      = (0x1A << 6) | OPC_CMPU_EQ_OB_DSP,
778     OPC_CMPGU_EQ_OB       = (0x04 << 6) | OPC_CMPU_EQ_OB_DSP,
779     OPC_CMPGU_LT_OB       = (0x05 << 6) | OPC_CMPU_EQ_OB_DSP,
780     OPC_CMPGU_LE_OB       = (0x06 << 6) | OPC_CMPU_EQ_OB_DSP,
781     OPC_CMPU_EQ_OB        = (0x00 << 6) | OPC_CMPU_EQ_OB_DSP,
782     OPC_CMPU_LT_OB        = (0x01 << 6) | OPC_CMPU_EQ_OB_DSP,
783     OPC_CMPU_LE_OB        = (0x02 << 6) | OPC_CMPU_EQ_OB_DSP,
784     OPC_PACKRL_PW         = (0x0E << 6) | OPC_CMPU_EQ_OB_DSP,
785     OPC_PICK_OB           = (0x03 << 6) | OPC_CMPU_EQ_OB_DSP,
786     OPC_PICK_PW           = (0x13 << 6) | OPC_CMPU_EQ_OB_DSP,
787     OPC_PICK_QH           = (0x0B << 6) | OPC_CMPU_EQ_OB_DSP,
788     /* MIPS DSP Arithmetic Sub-class */
789     OPC_PRECR_OB_QH       = (0x0D << 6) | OPC_CMPU_EQ_OB_DSP,
790     OPC_PRECR_SRA_QH_PW   = (0x1E << 6) | OPC_CMPU_EQ_OB_DSP,
791     OPC_PRECR_SRA_R_QH_PW = (0x1F << 6) | OPC_CMPU_EQ_OB_DSP,
792     OPC_PRECRQ_OB_QH      = (0x0C << 6) | OPC_CMPU_EQ_OB_DSP,
793     OPC_PRECRQ_PW_L       = (0x1C << 6) | OPC_CMPU_EQ_OB_DSP,
794     OPC_PRECRQ_QH_PW      = (0x14 << 6) | OPC_CMPU_EQ_OB_DSP,
795     OPC_PRECRQ_RS_QH_PW   = (0x15 << 6) | OPC_CMPU_EQ_OB_DSP,
796     OPC_PRECRQU_S_OB_QH   = (0x0F << 6) | OPC_CMPU_EQ_OB_DSP,
797 };
798 
799 #define MASK_DAPPEND(op)            (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
800 enum {
801     /* DSP Append Sub-class */
802     OPC_DAPPEND  = (0x00 << 6) | OPC_DAPPEND_DSP,
803     OPC_PREPENDD = (0x03 << 6) | OPC_DAPPEND_DSP,
804     OPC_PREPENDW = (0x01 << 6) | OPC_DAPPEND_DSP,
805     OPC_DBALIGN  = (0x10 << 6) | OPC_DAPPEND_DSP,
806 };
807 
808 #define MASK_DEXTR_W(op)            (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
809 enum {
810     /* MIPS DSP Accumulator and DSPControl Access Sub-class */
811     OPC_DMTHLIP     = (0x1F << 6) | OPC_DEXTR_W_DSP,
812     OPC_DSHILO      = (0x1A << 6) | OPC_DEXTR_W_DSP,
813     OPC_DEXTP       = (0x02 << 6) | OPC_DEXTR_W_DSP,
814     OPC_DEXTPDP     = (0x0A << 6) | OPC_DEXTR_W_DSP,
815     OPC_DEXTPDPV    = (0x0B << 6) | OPC_DEXTR_W_DSP,
816     OPC_DEXTPV      = (0x03 << 6) | OPC_DEXTR_W_DSP,
817     OPC_DEXTR_L     = (0x10 << 6) | OPC_DEXTR_W_DSP,
818     OPC_DEXTR_R_L   = (0x14 << 6) | OPC_DEXTR_W_DSP,
819     OPC_DEXTR_RS_L  = (0x16 << 6) | OPC_DEXTR_W_DSP,
820     OPC_DEXTR_W     = (0x00 << 6) | OPC_DEXTR_W_DSP,
821     OPC_DEXTR_R_W   = (0x04 << 6) | OPC_DEXTR_W_DSP,
822     OPC_DEXTR_RS_W  = (0x06 << 6) | OPC_DEXTR_W_DSP,
823     OPC_DEXTR_S_H   = (0x0E << 6) | OPC_DEXTR_W_DSP,
824     OPC_DEXTRV_L    = (0x11 << 6) | OPC_DEXTR_W_DSP,
825     OPC_DEXTRV_R_L  = (0x15 << 6) | OPC_DEXTR_W_DSP,
826     OPC_DEXTRV_RS_L = (0x17 << 6) | OPC_DEXTR_W_DSP,
827     OPC_DEXTRV_S_H  = (0x0F << 6) | OPC_DEXTR_W_DSP,
828     OPC_DEXTRV_W    = (0x01 << 6) | OPC_DEXTR_W_DSP,
829     OPC_DEXTRV_R_W  = (0x05 << 6) | OPC_DEXTR_W_DSP,
830     OPC_DEXTRV_RS_W = (0x07 << 6) | OPC_DEXTR_W_DSP,
831     OPC_DSHILOV     = (0x1B << 6) | OPC_DEXTR_W_DSP,
832 };
833 
834 #define MASK_DINSV(op)              (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
835 enum {
836     /* DSP Bit/Manipulation Sub-class */
837     OPC_DINSV = (0x00 << 6) | OPC_DINSV_DSP,
838 };
839 
840 #define MASK_DPAQ_W_QH(op)          (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
841 enum {
842     /* MIPS DSP Multiply Sub-class insns */
843     OPC_DMADD         = (0x19 << 6) | OPC_DPAQ_W_QH_DSP,
844     OPC_DMADDU        = (0x1D << 6) | OPC_DPAQ_W_QH_DSP,
845     OPC_DMSUB         = (0x1B << 6) | OPC_DPAQ_W_QH_DSP,
846     OPC_DMSUBU        = (0x1F << 6) | OPC_DPAQ_W_QH_DSP,
847     OPC_DPA_W_QH      = (0x00 << 6) | OPC_DPAQ_W_QH_DSP,
848     OPC_DPAQ_S_W_QH   = (0x04 << 6) | OPC_DPAQ_W_QH_DSP,
849     OPC_DPAQ_SA_L_PW  = (0x0C << 6) | OPC_DPAQ_W_QH_DSP,
850     OPC_DPAU_H_OBL    = (0x03 << 6) | OPC_DPAQ_W_QH_DSP,
851     OPC_DPAU_H_OBR    = (0x07 << 6) | OPC_DPAQ_W_QH_DSP,
852     OPC_DPS_W_QH      = (0x01 << 6) | OPC_DPAQ_W_QH_DSP,
853     OPC_DPSQ_S_W_QH   = (0x05 << 6) | OPC_DPAQ_W_QH_DSP,
854     OPC_DPSQ_SA_L_PW  = (0x0D << 6) | OPC_DPAQ_W_QH_DSP,
855     OPC_DPSU_H_OBL    = (0x0B << 6) | OPC_DPAQ_W_QH_DSP,
856     OPC_DPSU_H_OBR    = (0x0F << 6) | OPC_DPAQ_W_QH_DSP,
857     OPC_MAQ_S_L_PWL   = (0x1C << 6) | OPC_DPAQ_W_QH_DSP,
858     OPC_MAQ_S_L_PWR   = (0x1E << 6) | OPC_DPAQ_W_QH_DSP,
859     OPC_MAQ_S_W_QHLL  = (0x14 << 6) | OPC_DPAQ_W_QH_DSP,
860     OPC_MAQ_SA_W_QHLL = (0x10 << 6) | OPC_DPAQ_W_QH_DSP,
861     OPC_MAQ_S_W_QHLR  = (0x15 << 6) | OPC_DPAQ_W_QH_DSP,
862     OPC_MAQ_SA_W_QHLR = (0x11 << 6) | OPC_DPAQ_W_QH_DSP,
863     OPC_MAQ_S_W_QHRL  = (0x16 << 6) | OPC_DPAQ_W_QH_DSP,
864     OPC_MAQ_SA_W_QHRL = (0x12 << 6) | OPC_DPAQ_W_QH_DSP,
865     OPC_MAQ_S_W_QHRR  = (0x17 << 6) | OPC_DPAQ_W_QH_DSP,
866     OPC_MAQ_SA_W_QHRR = (0x13 << 6) | OPC_DPAQ_W_QH_DSP,
867     OPC_MULSAQ_S_L_PW = (0x0E << 6) | OPC_DPAQ_W_QH_DSP,
868     OPC_MULSAQ_S_W_QH = (0x06 << 6) | OPC_DPAQ_W_QH_DSP,
869 };
870 
871 #define MASK_SHLL_OB(op)            (MASK_SPECIAL3(op) | (op & (0x1F << 6)))
872 enum {
873     /* MIPS DSP GPR-Based Shift Sub-class */
874     OPC_SHLL_PW    = (0x10 << 6) | OPC_SHLL_OB_DSP,
875     OPC_SHLL_S_PW  = (0x14 << 6) | OPC_SHLL_OB_DSP,
876     OPC_SHLLV_OB   = (0x02 << 6) | OPC_SHLL_OB_DSP,
877     OPC_SHLLV_PW   = (0x12 << 6) | OPC_SHLL_OB_DSP,
878     OPC_SHLLV_S_PW = (0x16 << 6) | OPC_SHLL_OB_DSP,
879     OPC_SHLLV_QH   = (0x0A << 6) | OPC_SHLL_OB_DSP,
880     OPC_SHLLV_S_QH = (0x0E << 6) | OPC_SHLL_OB_DSP,
881     OPC_SHRA_PW    = (0x11 << 6) | OPC_SHLL_OB_DSP,
882     OPC_SHRA_R_PW  = (0x15 << 6) | OPC_SHLL_OB_DSP,
883     OPC_SHRAV_OB   = (0x06 << 6) | OPC_SHLL_OB_DSP,
884     OPC_SHRAV_R_OB = (0x07 << 6) | OPC_SHLL_OB_DSP,
885     OPC_SHRAV_PW   = (0x13 << 6) | OPC_SHLL_OB_DSP,
886     OPC_SHRAV_R_PW = (0x17 << 6) | OPC_SHLL_OB_DSP,
887     OPC_SHRAV_QH   = (0x0B << 6) | OPC_SHLL_OB_DSP,
888     OPC_SHRAV_R_QH = (0x0F << 6) | OPC_SHLL_OB_DSP,
889     OPC_SHRLV_OB   = (0x03 << 6) | OPC_SHLL_OB_DSP,
890     OPC_SHRLV_QH   = (0x1B << 6) | OPC_SHLL_OB_DSP,
891     OPC_SHLL_OB    = (0x00 << 6) | OPC_SHLL_OB_DSP,
892     OPC_SHLL_QH    = (0x08 << 6) | OPC_SHLL_OB_DSP,
893     OPC_SHLL_S_QH  = (0x0C << 6) | OPC_SHLL_OB_DSP,
894     OPC_SHRA_OB    = (0x04 << 6) | OPC_SHLL_OB_DSP,
895     OPC_SHRA_R_OB  = (0x05 << 6) | OPC_SHLL_OB_DSP,
896     OPC_SHRA_QH    = (0x09 << 6) | OPC_SHLL_OB_DSP,
897     OPC_SHRA_R_QH  = (0x0D << 6) | OPC_SHLL_OB_DSP,
898     OPC_SHRL_OB    = (0x01 << 6) | OPC_SHLL_OB_DSP,
899     OPC_SHRL_QH    = (0x19 << 6) | OPC_SHLL_OB_DSP,
900 };
901 
902 /* Coprocessor 0 (rs field) */
903 #define MASK_CP0(op)                (MASK_OP_MAJOR(op) | (op & (0x1F << 21)))
904 
905 enum {
906     OPC_MFC0     = (0x00 << 21) | OPC_CP0,
907     OPC_DMFC0    = (0x01 << 21) | OPC_CP0,
908     OPC_MFHC0    = (0x02 << 21) | OPC_CP0,
909     OPC_MTC0     = (0x04 << 21) | OPC_CP0,
910     OPC_DMTC0    = (0x05 << 21) | OPC_CP0,
911     OPC_MTHC0    = (0x06 << 21) | OPC_CP0,
912     OPC_MFTR     = (0x08 << 21) | OPC_CP0,
913     OPC_RDPGPR   = (0x0A << 21) | OPC_CP0,
914     OPC_MFMC0    = (0x0B << 21) | OPC_CP0,
915     OPC_MTTR     = (0x0C << 21) | OPC_CP0,
916     OPC_WRPGPR   = (0x0E << 21) | OPC_CP0,
917     OPC_C0       = (0x10 << 21) | OPC_CP0,
918     OPC_C0_1     = (0x11 << 21) | OPC_CP0,
919     OPC_C0_2     = (0x12 << 21) | OPC_CP0,
920     OPC_C0_3     = (0x13 << 21) | OPC_CP0,
921     OPC_C0_4     = (0x14 << 21) | OPC_CP0,
922     OPC_C0_5     = (0x15 << 21) | OPC_CP0,
923     OPC_C0_6     = (0x16 << 21) | OPC_CP0,
924     OPC_C0_7     = (0x17 << 21) | OPC_CP0,
925     OPC_C0_8     = (0x18 << 21) | OPC_CP0,
926     OPC_C0_9     = (0x19 << 21) | OPC_CP0,
927     OPC_C0_A     = (0x1A << 21) | OPC_CP0,
928     OPC_C0_B     = (0x1B << 21) | OPC_CP0,
929     OPC_C0_C     = (0x1C << 21) | OPC_CP0,
930     OPC_C0_D     = (0x1D << 21) | OPC_CP0,
931     OPC_C0_E     = (0x1E << 21) | OPC_CP0,
932     OPC_C0_F     = (0x1F << 21) | OPC_CP0,
933 };
934 
935 /* MFMC0 opcodes */
936 #define MASK_MFMC0(op)              (MASK_CP0(op) | (op & 0xFFFF))
937 
938 enum {
939     OPC_DMT      = 0x01 | (0 << 5) | (0x0F << 6) | (0x01 << 11) | OPC_MFMC0,
940     OPC_EMT      = 0x01 | (1 << 5) | (0x0F << 6) | (0x01 << 11) | OPC_MFMC0,
941     OPC_DVPE     = 0x01 | (0 << 5) | OPC_MFMC0,
942     OPC_EVPE     = 0x01 | (1 << 5) | OPC_MFMC0,
943     OPC_DI       = (0 << 5) | (0x0C << 11) | OPC_MFMC0,
944     OPC_EI       = (1 << 5) | (0x0C << 11) | OPC_MFMC0,
945     OPC_DVP      = 0x04 | (0 << 3) | (1 << 5) | (0 << 11) | OPC_MFMC0,
946     OPC_EVP      = 0x04 | (0 << 3) | (0 << 5) | (0 << 11) | OPC_MFMC0,
947 };
948 
949 /* Coprocessor 0 (with rs == C0) */
950 #define MASK_C0(op)                 (MASK_CP0(op) | (op & 0x3F))
951 
952 enum {
953     OPC_TLBR     = 0x01 | OPC_C0,
954     OPC_TLBWI    = 0x02 | OPC_C0,
955     OPC_TLBINV   = 0x03 | OPC_C0,
956     OPC_TLBINVF  = 0x04 | OPC_C0,
957     OPC_TLBWR    = 0x06 | OPC_C0,
958     OPC_TLBP     = 0x08 | OPC_C0,
959     OPC_RFE      = 0x10 | OPC_C0,
960     OPC_ERET     = 0x18 | OPC_C0,
961     OPC_DERET    = 0x1F | OPC_C0,
962     OPC_WAIT     = 0x20 | OPC_C0,
963 };
964 
965 #define MASK_CP2(op)                (MASK_OP_MAJOR(op) | (op & (0x1F << 21)))
966 
967 enum {
968     OPC_MFC2    = (0x00 << 21) | OPC_CP2,
969     OPC_DMFC2   = (0x01 << 21) | OPC_CP2,
970     OPC_CFC2    = (0x02 << 21) | OPC_CP2,
971     OPC_MFHC2   = (0x03 << 21) | OPC_CP2,
972     OPC_MTC2    = (0x04 << 21) | OPC_CP2,
973     OPC_DMTC2   = (0x05 << 21) | OPC_CP2,
974     OPC_CTC2    = (0x06 << 21) | OPC_CP2,
975     OPC_MTHC2   = (0x07 << 21) | OPC_CP2,
976     OPC_BC2     = (0x08 << 21) | OPC_CP2,
977     OPC_BC2EQZ  = (0x09 << 21) | OPC_CP2,
978     OPC_BC2NEZ  = (0x0D << 21) | OPC_CP2,
979 };
980 
981 #define MASK_LMMI(op)    (MASK_OP_MAJOR(op) | (op & (0x1F << 21)) | (op & 0x1F))
982 
983 enum {
984     OPC_PADDSH      = (24 << 21) | (0x00) | OPC_CP2,
985     OPC_PADDUSH     = (25 << 21) | (0x00) | OPC_CP2,
986     OPC_PADDH       = (26 << 21) | (0x00) | OPC_CP2,
987     OPC_PADDW       = (27 << 21) | (0x00) | OPC_CP2,
988     OPC_PADDSB      = (28 << 21) | (0x00) | OPC_CP2,
989     OPC_PADDUSB     = (29 << 21) | (0x00) | OPC_CP2,
990     OPC_PADDB       = (30 << 21) | (0x00) | OPC_CP2,
991     OPC_PADDD       = (31 << 21) | (0x00) | OPC_CP2,
992 
993     OPC_PSUBSH      = (24 << 21) | (0x01) | OPC_CP2,
994     OPC_PSUBUSH     = (25 << 21) | (0x01) | OPC_CP2,
995     OPC_PSUBH       = (26 << 21) | (0x01) | OPC_CP2,
996     OPC_PSUBW       = (27 << 21) | (0x01) | OPC_CP2,
997     OPC_PSUBSB      = (28 << 21) | (0x01) | OPC_CP2,
998     OPC_PSUBUSB     = (29 << 21) | (0x01) | OPC_CP2,
999     OPC_PSUBB       = (30 << 21) | (0x01) | OPC_CP2,
1000     OPC_PSUBD       = (31 << 21) | (0x01) | OPC_CP2,
1001 
1002     OPC_PSHUFH      = (24 << 21) | (0x02) | OPC_CP2,
1003     OPC_PACKSSWH    = (25 << 21) | (0x02) | OPC_CP2,
1004     OPC_PACKSSHB    = (26 << 21) | (0x02) | OPC_CP2,
1005     OPC_PACKUSHB    = (27 << 21) | (0x02) | OPC_CP2,
1006     OPC_XOR_CP2     = (28 << 21) | (0x02) | OPC_CP2,
1007     OPC_NOR_CP2     = (29 << 21) | (0x02) | OPC_CP2,
1008     OPC_AND_CP2     = (30 << 21) | (0x02) | OPC_CP2,
1009     OPC_PANDN       = (31 << 21) | (0x02) | OPC_CP2,
1010 
1011     OPC_PUNPCKLHW   = (24 << 21) | (0x03) | OPC_CP2,
1012     OPC_PUNPCKHHW   = (25 << 21) | (0x03) | OPC_CP2,
1013     OPC_PUNPCKLBH   = (26 << 21) | (0x03) | OPC_CP2,
1014     OPC_PUNPCKHBH   = (27 << 21) | (0x03) | OPC_CP2,
1015     OPC_PINSRH_0    = (28 << 21) | (0x03) | OPC_CP2,
1016     OPC_PINSRH_1    = (29 << 21) | (0x03) | OPC_CP2,
1017     OPC_PINSRH_2    = (30 << 21) | (0x03) | OPC_CP2,
1018     OPC_PINSRH_3    = (31 << 21) | (0x03) | OPC_CP2,
1019 
1020     OPC_PAVGH       = (24 << 21) | (0x08) | OPC_CP2,
1021     OPC_PAVGB       = (25 << 21) | (0x08) | OPC_CP2,
1022     OPC_PMAXSH      = (26 << 21) | (0x08) | OPC_CP2,
1023     OPC_PMINSH      = (27 << 21) | (0x08) | OPC_CP2,
1024     OPC_PMAXUB      = (28 << 21) | (0x08) | OPC_CP2,
1025     OPC_PMINUB      = (29 << 21) | (0x08) | OPC_CP2,
1026 
1027     OPC_PCMPEQW     = (24 << 21) | (0x09) | OPC_CP2,
1028     OPC_PCMPGTW     = (25 << 21) | (0x09) | OPC_CP2,
1029     OPC_PCMPEQH     = (26 << 21) | (0x09) | OPC_CP2,
1030     OPC_PCMPGTH     = (27 << 21) | (0x09) | OPC_CP2,
1031     OPC_PCMPEQB     = (28 << 21) | (0x09) | OPC_CP2,
1032     OPC_PCMPGTB     = (29 << 21) | (0x09) | OPC_CP2,
1033 
1034     OPC_PSLLW       = (24 << 21) | (0x0A) | OPC_CP2,
1035     OPC_PSLLH       = (25 << 21) | (0x0A) | OPC_CP2,
1036     OPC_PMULLH      = (26 << 21) | (0x0A) | OPC_CP2,
1037     OPC_PMULHH      = (27 << 21) | (0x0A) | OPC_CP2,
1038     OPC_PMULUW      = (28 << 21) | (0x0A) | OPC_CP2,
1039     OPC_PMULHUH     = (29 << 21) | (0x0A) | OPC_CP2,
1040 
1041     OPC_PSRLW       = (24 << 21) | (0x0B) | OPC_CP2,
1042     OPC_PSRLH       = (25 << 21) | (0x0B) | OPC_CP2,
1043     OPC_PSRAW       = (26 << 21) | (0x0B) | OPC_CP2,
1044     OPC_PSRAH       = (27 << 21) | (0x0B) | OPC_CP2,
1045     OPC_PUNPCKLWD   = (28 << 21) | (0x0B) | OPC_CP2,
1046     OPC_PUNPCKHWD   = (29 << 21) | (0x0B) | OPC_CP2,
1047 
1048     OPC_ADDU_CP2    = (24 << 21) | (0x0C) | OPC_CP2,
1049     OPC_OR_CP2      = (25 << 21) | (0x0C) | OPC_CP2,
1050     OPC_ADD_CP2     = (26 << 21) | (0x0C) | OPC_CP2,
1051     OPC_DADD_CP2    = (27 << 21) | (0x0C) | OPC_CP2,
1052     OPC_SEQU_CP2    = (28 << 21) | (0x0C) | OPC_CP2,
1053     OPC_SEQ_CP2     = (29 << 21) | (0x0C) | OPC_CP2,
1054 
1055     OPC_SUBU_CP2    = (24 << 21) | (0x0D) | OPC_CP2,
1056     OPC_PASUBUB     = (25 << 21) | (0x0D) | OPC_CP2,
1057     OPC_SUB_CP2     = (26 << 21) | (0x0D) | OPC_CP2,
1058     OPC_DSUB_CP2    = (27 << 21) | (0x0D) | OPC_CP2,
1059     OPC_SLTU_CP2    = (28 << 21) | (0x0D) | OPC_CP2,
1060     OPC_SLT_CP2     = (29 << 21) | (0x0D) | OPC_CP2,
1061 
1062     OPC_SLL_CP2     = (24 << 21) | (0x0E) | OPC_CP2,
1063     OPC_DSLL_CP2    = (25 << 21) | (0x0E) | OPC_CP2,
1064     OPC_PEXTRH      = (26 << 21) | (0x0E) | OPC_CP2,
1065     OPC_PMADDHW     = (27 << 21) | (0x0E) | OPC_CP2,
1066     OPC_SLEU_CP2    = (28 << 21) | (0x0E) | OPC_CP2,
1067     OPC_SLE_CP2     = (29 << 21) | (0x0E) | OPC_CP2,
1068 
1069     OPC_SRL_CP2     = (24 << 21) | (0x0F) | OPC_CP2,
1070     OPC_DSRL_CP2    = (25 << 21) | (0x0F) | OPC_CP2,
1071     OPC_SRA_CP2     = (26 << 21) | (0x0F) | OPC_CP2,
1072     OPC_DSRA_CP2    = (27 << 21) | (0x0F) | OPC_CP2,
1073     OPC_BIADD       = (28 << 21) | (0x0F) | OPC_CP2,
1074     OPC_PMOVMSKB    = (29 << 21) | (0x0F) | OPC_CP2,
1075 };
1076 
1077 
1078 #define MASK_CP3(op)                (MASK_OP_MAJOR(op) | (op & 0x3F))
1079 
1080 enum {
1081     OPC_LWXC1       = 0x00 | OPC_CP3,
1082     OPC_LDXC1       = 0x01 | OPC_CP3,
1083     OPC_LUXC1       = 0x05 | OPC_CP3,
1084     OPC_SWXC1       = 0x08 | OPC_CP3,
1085     OPC_SDXC1       = 0x09 | OPC_CP3,
1086     OPC_SUXC1       = 0x0D | OPC_CP3,
1087     OPC_PREFX       = 0x0F | OPC_CP3,
1088     OPC_ALNV_PS     = 0x1E | OPC_CP3,
1089     OPC_MADD_S      = 0x20 | OPC_CP3,
1090     OPC_MADD_D      = 0x21 | OPC_CP3,
1091     OPC_MADD_PS     = 0x26 | OPC_CP3,
1092     OPC_MSUB_S      = 0x28 | OPC_CP3,
1093     OPC_MSUB_D      = 0x29 | OPC_CP3,
1094     OPC_MSUB_PS     = 0x2E | OPC_CP3,
1095     OPC_NMADD_S     = 0x30 | OPC_CP3,
1096     OPC_NMADD_D     = 0x31 | OPC_CP3,
1097     OPC_NMADD_PS    = 0x36 | OPC_CP3,
1098     OPC_NMSUB_S     = 0x38 | OPC_CP3,
1099     OPC_NMSUB_D     = 0x39 | OPC_CP3,
1100     OPC_NMSUB_PS    = 0x3E | OPC_CP3,
1101 };
1102 
1103 /*
1104  *     MMI (MultiMedia Instruction) encodings
1105  *     ======================================
1106  *
1107  * MMI instructions encoding table keys:
1108  *
1109  *     *   This code is reserved for future use. An attempt to execute it
1110  *         causes a Reserved Instruction exception.
1111  *     %   This code indicates an instruction class. The instruction word
1112  *         must be further decoded by examining additional tables that show
1113  *         the values for other instruction fields.
1114  *     #   This code is reserved for the unsupported instructions DMULT,
1115  *         DMULTU, DDIV, DDIVU, LL, LLD, SC, SCD, LWC2 and SWC2. An attempt
1116  *         to execute it causes a Reserved Instruction exception.
1117  *
1118  * MMI instructions encoded by opcode field (MMI, LQ, SQ):
1119  *
1120  *  31    26                                        0
1121  * +--------+----------------------------------------+
1122  * | opcode |                                        |
1123  * +--------+----------------------------------------+
1124  *
1125  *   opcode  bits 28..26
1126  *     bits |   0   |   1   |   2   |   3   |   4   |   5   |   6   |   7
1127  *   31..29 |  000  |  001  |  010  |  011  |  100  |  101  |  110  |  111
1128  *   -------+-------+-------+-------+-------+-------+-------+-------+-------
1129  *    0 000 |SPECIAL| REGIMM|   J   |  JAL  |  BEQ  |  BNE  |  BLEZ |  BGTZ
1130  *    1 001 |  ADDI | ADDIU |  SLTI | SLTIU |  ANDI |  ORI  |  XORI |  LUI
1131  *    2 010 |  COP0 |  COP1 |   *   |   *   |  BEQL |  BNEL | BLEZL | BGTZL
1132  *    3 011 | DADDI | DADDIU|  LDL  |  LDR  |  MMI% |   *   |   LQ  |   SQ
1133  *    4 100 |   LB  |   LH  |  LWL  |   LW  |  LBU  |  LHU  |  LWR  |  LWU
1134  *    5 101 |   SB  |   SH  |  SWL  |   SW  |  SDL  |  SDR  |  SWR  | CACHE
1135  *    6 110 |   #   |  LWC1 |   #   |  PREF |   #   |  LDC1 |   #   |   LD
1136  *    7 111 |   #   |  SWC1 |   #   |   *   |   #   |  SDC1 |   #   |   SD
1137  */
1138 
1139 enum {
1140     MMI_OPC_CLASS_MMI = 0x1C << 26,    /* Same as OPC_SPECIAL2 */
1141     MMI_OPC_SQ        = 0x1F << 26,    /* Same as OPC_SPECIAL3 */
1142 };
1143 
1144 /*
1145  * MMI instructions with opcode field = MMI:
1146  *
1147  *  31    26                                 5      0
1148  * +--------+-------------------------------+--------+
1149  * |   MMI  |                               |function|
1150  * +--------+-------------------------------+--------+
1151  *
1152  * function  bits 2..0
1153  *     bits |   0   |   1   |   2   |   3   |   4   |   5   |   6   |   7
1154  *     5..3 |  000  |  001  |  010  |  011  |  100  |  101  |  110  |  111
1155  *   -------+-------+-------+-------+-------+-------+-------+-------+-------
1156  *    0 000 |  MADD | MADDU |   *   |   *   | PLZCW |   *   |   *   |   *
1157  *    1 001 | MMI0% | MMI2% |   *   |   *   |   *   |   *   |   *   |   *
1158  *    2 010 | MFHI1 | MTHI1 | MFLO1 | MTLO1 |   *   |   *   |   *   |   *
1159  *    3 011 | MULT1 | MULTU1|  DIV1 | DIVU1 |   *   |   *   |   *   |   *
1160  *    4 100 | MADD1 | MADDU1|   *   |   *   |   *   |   *   |   *   |   *
1161  *    5 101 | MMI1% | MMI3% |   *   |   *   |   *   |   *   |   *   |   *
1162  *    6 110 | PMFHL | PMTHL |   *   |   *   | PSLLH |   *   | PSRLH | PSRAH
1163  *    7 111 |   *   |   *   |   *   |   *   | PSLLW |   *   | PSRLW | PSRAW
1164  */
1165 
1166 #define MASK_MMI(op) (MASK_OP_MAJOR(op) | ((op) & 0x3F))
1167 enum {
1168     MMI_OPC_MADD       = 0x00 | MMI_OPC_CLASS_MMI, /* Same as OPC_MADD */
1169     MMI_OPC_MADDU      = 0x01 | MMI_OPC_CLASS_MMI, /* Same as OPC_MADDU */
1170     MMI_OPC_MULT1      = 0x18 | MMI_OPC_CLASS_MMI, /* Same minor as OPC_MULT */
1171     MMI_OPC_MULTU1     = 0x19 | MMI_OPC_CLASS_MMI, /* Same min. as OPC_MULTU */
1172     MMI_OPC_DIV1       = 0x1A | MMI_OPC_CLASS_MMI, /* Same minor as OPC_DIV  */
1173     MMI_OPC_DIVU1      = 0x1B | MMI_OPC_CLASS_MMI, /* Same minor as OPC_DIVU */
1174     MMI_OPC_MADD1      = 0x20 | MMI_OPC_CLASS_MMI,
1175     MMI_OPC_MADDU1     = 0x21 | MMI_OPC_CLASS_MMI,
1176 };
1177 
1178 /* global register indices */
1179 TCGv cpu_gpr[32], cpu_PC;
1180 /*
1181  * For CPUs using 128-bit GPR registers, we put the lower halves in cpu_gpr[])
1182  * and the upper halves in cpu_gpr_hi[].
1183  */
1184 TCGv_i64 cpu_gpr_hi[32];
1185 TCGv cpu_HI[MIPS_DSP_ACC], cpu_LO[MIPS_DSP_ACC];
1186 static TCGv cpu_dspctrl, btarget;
1187 TCGv bcond;
1188 static TCGv cpu_lladdr, cpu_llval;
1189 static TCGv_i32 hflags;
1190 TCGv_i32 fpu_fcr0, fpu_fcr31;
1191 TCGv_i64 fpu_f64[32];
1192 
1193 static const char regnames_HI[][4] = {
1194     "HI0", "HI1", "HI2", "HI3",
1195 };
1196 
1197 static const char regnames_LO[][4] = {
1198     "LO0", "LO1", "LO2", "LO3",
1199 };
1200 
1201 /* General purpose registers moves. */
1202 void gen_load_gpr(TCGv t, int reg)
1203 {
1204     assert(reg >= 0 && reg <= ARRAY_SIZE(cpu_gpr));
1205     if (reg == 0) {
1206         tcg_gen_movi_tl(t, 0);
1207     } else {
1208         tcg_gen_mov_tl(t, cpu_gpr[reg]);
1209     }
1210 }
1211 
1212 void gen_store_gpr(TCGv t, int reg)
1213 {
1214     assert(reg >= 0 && reg <= ARRAY_SIZE(cpu_gpr));
1215     if (reg != 0) {
1216         tcg_gen_mov_tl(cpu_gpr[reg], t);
1217     }
1218 }
1219 
1220 #if defined(TARGET_MIPS64)
1221 void gen_load_gpr_hi(TCGv_i64 t, int reg)
1222 {
1223     assert(reg >= 0 && reg <= ARRAY_SIZE(cpu_gpr_hi));
1224     if (reg == 0) {
1225         tcg_gen_movi_i64(t, 0);
1226     } else {
1227         tcg_gen_mov_i64(t, cpu_gpr_hi[reg]);
1228     }
1229 }
1230 
1231 void gen_store_gpr_hi(TCGv_i64 t, int reg)
1232 {
1233     assert(reg >= 0 && reg <= ARRAY_SIZE(cpu_gpr_hi));
1234     if (reg != 0) {
1235         tcg_gen_mov_i64(cpu_gpr_hi[reg], t);
1236     }
1237 }
1238 #endif /* TARGET_MIPS64 */
1239 
1240 /* Moves to/from shadow registers. */
1241 static inline void gen_load_srsgpr(int from, int to)
1242 {
1243     TCGv t0 = tcg_temp_new();
1244 
1245     if (from == 0) {
1246         tcg_gen_movi_tl(t0, 0);
1247     } else {
1248         TCGv_i32 t2 = tcg_temp_new_i32();
1249         TCGv_ptr addr = tcg_temp_new_ptr();
1250 
1251         tcg_gen_ld_i32(t2, tcg_env, offsetof(CPUMIPSState, CP0_SRSCtl));
1252         tcg_gen_shri_i32(t2, t2, CP0SRSCtl_PSS);
1253         tcg_gen_andi_i32(t2, t2, 0xf);
1254         tcg_gen_muli_i32(t2, t2, sizeof(target_ulong) * 32);
1255         tcg_gen_ext_i32_ptr(addr, t2);
1256         tcg_gen_add_ptr(addr, tcg_env, addr);
1257 
1258         tcg_gen_ld_tl(t0, addr, sizeof(target_ulong) * from);
1259     }
1260     gen_store_gpr(t0, to);
1261 }
1262 
1263 static inline void gen_store_srsgpr(int from, int to)
1264 {
1265     if (to != 0) {
1266         TCGv t0 = tcg_temp_new();
1267         TCGv_i32 t2 = tcg_temp_new_i32();
1268         TCGv_ptr addr = tcg_temp_new_ptr();
1269 
1270         gen_load_gpr(t0, from);
1271         tcg_gen_ld_i32(t2, tcg_env, offsetof(CPUMIPSState, CP0_SRSCtl));
1272         tcg_gen_shri_i32(t2, t2, CP0SRSCtl_PSS);
1273         tcg_gen_andi_i32(t2, t2, 0xf);
1274         tcg_gen_muli_i32(t2, t2, sizeof(target_ulong) * 32);
1275         tcg_gen_ext_i32_ptr(addr, t2);
1276         tcg_gen_add_ptr(addr, tcg_env, addr);
1277 
1278         tcg_gen_st_tl(t0, addr, sizeof(target_ulong) * to);
1279     }
1280 }
1281 
1282 /* Tests */
1283 static inline void gen_save_pc(target_ulong pc)
1284 {
1285     tcg_gen_movi_tl(cpu_PC, pc);
1286 }
1287 
1288 static inline void save_cpu_state(DisasContext *ctx, int do_save_pc)
1289 {
1290     LOG_DISAS("hflags %08x saved %08x\n", ctx->hflags, ctx->saved_hflags);
1291     if (do_save_pc && ctx->base.pc_next != ctx->saved_pc) {
1292         gen_save_pc(ctx->base.pc_next);
1293         ctx->saved_pc = ctx->base.pc_next;
1294     }
1295     if (ctx->hflags != ctx->saved_hflags) {
1296         tcg_gen_movi_i32(hflags, ctx->hflags);
1297         ctx->saved_hflags = ctx->hflags;
1298         switch (ctx->hflags & MIPS_HFLAG_BMASK_BASE) {
1299         case MIPS_HFLAG_BR:
1300             break;
1301         case MIPS_HFLAG_BC:
1302         case MIPS_HFLAG_BL:
1303         case MIPS_HFLAG_B:
1304             tcg_gen_movi_tl(btarget, ctx->btarget);
1305             break;
1306         }
1307     }
1308 }
1309 
1310 static inline void restore_cpu_state(CPUMIPSState *env, DisasContext *ctx)
1311 {
1312     ctx->saved_hflags = ctx->hflags;
1313     switch (ctx->hflags & MIPS_HFLAG_BMASK_BASE) {
1314     case MIPS_HFLAG_BR:
1315         break;
1316     case MIPS_HFLAG_BC:
1317     case MIPS_HFLAG_BL:
1318     case MIPS_HFLAG_B:
1319         ctx->btarget = env->btarget;
1320         break;
1321     }
1322 }
1323 
1324 void generate_exception_err(DisasContext *ctx, int excp, int err)
1325 {
1326     save_cpu_state(ctx, 1);
1327     gen_helper_raise_exception_err(tcg_env, tcg_constant_i32(excp),
1328                                    tcg_constant_i32(err));
1329     ctx->base.is_jmp = DISAS_NORETURN;
1330 }
1331 
1332 void generate_exception(DisasContext *ctx, int excp)
1333 {
1334     gen_helper_raise_exception(tcg_env, tcg_constant_i32(excp));
1335 }
1336 
1337 void generate_exception_end(DisasContext *ctx, int excp)
1338 {
1339     generate_exception_err(ctx, excp, 0);
1340 }
1341 
1342 void generate_exception_break(DisasContext *ctx, int code)
1343 {
1344 #ifdef CONFIG_USER_ONLY
1345     /* Pass the break code along to cpu_loop. */
1346     tcg_gen_st_i32(tcg_constant_i32(code), tcg_env,
1347                    offsetof(CPUMIPSState, error_code));
1348 #endif
1349     generate_exception_end(ctx, EXCP_BREAK);
1350 }
1351 
1352 void gen_reserved_instruction(DisasContext *ctx)
1353 {
1354     generate_exception_end(ctx, EXCP_RI);
1355 }
1356 
1357 /* Floating point register moves. */
1358 void gen_load_fpr32(DisasContext *ctx, TCGv_i32 t, int reg)
1359 {
1360     if (ctx->hflags & MIPS_HFLAG_FRE) {
1361         generate_exception(ctx, EXCP_RI);
1362     }
1363     tcg_gen_extrl_i64_i32(t, fpu_f64[reg]);
1364 }
1365 
1366 void gen_store_fpr32(DisasContext *ctx, TCGv_i32 t, int reg)
1367 {
1368     TCGv_i64 t64;
1369     if (ctx->hflags & MIPS_HFLAG_FRE) {
1370         generate_exception(ctx, EXCP_RI);
1371     }
1372     t64 = tcg_temp_new_i64();
1373     tcg_gen_extu_i32_i64(t64, t);
1374     tcg_gen_deposit_i64(fpu_f64[reg], fpu_f64[reg], t64, 0, 32);
1375 }
1376 
1377 static void gen_load_fpr32h(DisasContext *ctx, TCGv_i32 t, int reg)
1378 {
1379     if (ctx->hflags & MIPS_HFLAG_F64) {
1380         tcg_gen_extrh_i64_i32(t, fpu_f64[reg]);
1381     } else {
1382         gen_load_fpr32(ctx, t, reg | 1);
1383     }
1384 }
1385 
1386 static void gen_store_fpr32h(DisasContext *ctx, TCGv_i32 t, int reg)
1387 {
1388     if (ctx->hflags & MIPS_HFLAG_F64) {
1389         TCGv_i64 t64 = tcg_temp_new_i64();
1390         tcg_gen_extu_i32_i64(t64, t);
1391         tcg_gen_deposit_i64(fpu_f64[reg], fpu_f64[reg], t64, 32, 32);
1392     } else {
1393         gen_store_fpr32(ctx, t, reg | 1);
1394     }
1395 }
1396 
1397 void gen_load_fpr64(DisasContext *ctx, TCGv_i64 t, int reg)
1398 {
1399     if (ctx->hflags & MIPS_HFLAG_F64) {
1400         tcg_gen_mov_i64(t, fpu_f64[reg]);
1401     } else {
1402         tcg_gen_concat32_i64(t, fpu_f64[reg & ~1], fpu_f64[reg | 1]);
1403     }
1404 }
1405 
1406 void gen_store_fpr64(DisasContext *ctx, TCGv_i64 t, int reg)
1407 {
1408     if (ctx->hflags & MIPS_HFLAG_F64) {
1409         tcg_gen_mov_i64(fpu_f64[reg], t);
1410     } else {
1411         TCGv_i64 t0;
1412         tcg_gen_deposit_i64(fpu_f64[reg & ~1], fpu_f64[reg & ~1], t, 0, 32);
1413         t0 = tcg_temp_new_i64();
1414         tcg_gen_shri_i64(t0, t, 32);
1415         tcg_gen_deposit_i64(fpu_f64[reg | 1], fpu_f64[reg | 1], t0, 0, 32);
1416     }
1417 }
1418 
1419 int get_fp_bit(int cc)
1420 {
1421     if (cc) {
1422         return 24 + cc;
1423     } else {
1424         return 23;
1425     }
1426 }
1427 
1428 /* Addresses computation */
1429 void gen_op_addr_add(DisasContext *ctx, TCGv ret, TCGv arg0, TCGv arg1)
1430 {
1431     tcg_gen_add_tl(ret, arg0, arg1);
1432 
1433 #if defined(TARGET_MIPS64)
1434     if (ctx->hflags & MIPS_HFLAG_AWRAP) {
1435         tcg_gen_ext32s_i64(ret, ret);
1436     }
1437 #endif
1438 }
1439 
1440 void gen_op_addr_addi(DisasContext *ctx, TCGv ret, TCGv base, target_long ofs)
1441 {
1442     tcg_gen_addi_tl(ret, base, ofs);
1443 
1444 #if defined(TARGET_MIPS64)
1445     if (ctx->hflags & MIPS_HFLAG_AWRAP) {
1446         tcg_gen_ext32s_i64(ret, ret);
1447     }
1448 #endif
1449 }
1450 
1451 /* Addresses computation (translation time) */
1452 static target_long addr_add(DisasContext *ctx, target_long base,
1453                             target_long offset)
1454 {
1455     target_long sum = base + offset;
1456 
1457 #if defined(TARGET_MIPS64)
1458     if (ctx->hflags & MIPS_HFLAG_AWRAP) {
1459         sum = (int32_t)sum;
1460     }
1461 #endif
1462     return sum;
1463 }
1464 
1465 /* Sign-extract the low 32-bits to a target_long.  */
1466 void gen_move_low32(TCGv ret, TCGv_i64 arg)
1467 {
1468 #if defined(TARGET_MIPS64)
1469     tcg_gen_ext32s_i64(ret, arg);
1470 #else
1471     tcg_gen_extrl_i64_i32(ret, arg);
1472 #endif
1473 }
1474 
1475 /* Sign-extract the high 32-bits to a target_long.  */
1476 void gen_move_high32(TCGv ret, TCGv_i64 arg)
1477 {
1478 #if defined(TARGET_MIPS64)
1479     tcg_gen_sari_i64(ret, arg, 32);
1480 #else
1481     tcg_gen_extrh_i64_i32(ret, arg);
1482 #endif
1483 }
1484 
1485 bool check_cp0_enabled(DisasContext *ctx)
1486 {
1487     if (unlikely(!(ctx->hflags & MIPS_HFLAG_CP0))) {
1488         generate_exception_end(ctx, EXCP_CpU);
1489         return false;
1490     }
1491     return true;
1492 }
1493 
1494 void check_cp1_enabled(DisasContext *ctx)
1495 {
1496     if (unlikely(!(ctx->hflags & MIPS_HFLAG_FPU))) {
1497         generate_exception_err(ctx, EXCP_CpU, 1);
1498     }
1499 }
1500 
1501 /*
1502  * Verify that the processor is running with COP1X instructions enabled.
1503  * This is associated with the nabla symbol in the MIPS32 and MIPS64
1504  * opcode tables.
1505  */
1506 void check_cop1x(DisasContext *ctx)
1507 {
1508     if (unlikely(!(ctx->hflags & MIPS_HFLAG_COP1X))) {
1509         gen_reserved_instruction(ctx);
1510     }
1511 }
1512 
1513 /*
1514  * Verify that the processor is running with 64-bit floating-point
1515  * operations enabled.
1516  */
1517 void check_cp1_64bitmode(DisasContext *ctx)
1518 {
1519     if (unlikely(~ctx->hflags & MIPS_HFLAG_F64)) {
1520         gen_reserved_instruction(ctx);
1521     }
1522 }
1523 
1524 /*
1525  * Verify if floating point register is valid; an operation is not defined
1526  * if bit 0 of any register specification is set and the FR bit in the
1527  * Status register equals zero, since the register numbers specify an
1528  * even-odd pair of adjacent coprocessor general registers. When the FR bit
1529  * in the Status register equals one, both even and odd register numbers
1530  * are valid. This limitation exists only for 64 bit wide (d,l,ps) registers.
1531  *
1532  * Multiple 64 bit wide registers can be checked by calling
1533  * gen_op_cp1_registers(freg1 | freg2 | ... | fregN);
1534  */
1535 void check_cp1_registers(DisasContext *ctx, int regs)
1536 {
1537     if (unlikely(!(ctx->hflags & MIPS_HFLAG_F64) && (regs & 1))) {
1538         gen_reserved_instruction(ctx);
1539     }
1540 }
1541 
1542 /*
1543  * Verify that the processor is running with DSP instructions enabled.
1544  * This is enabled by CP0 Status register MX(24) bit.
1545  */
1546 static inline void check_dsp(DisasContext *ctx)
1547 {
1548     if (unlikely(!(ctx->hflags & MIPS_HFLAG_DSP))) {
1549         if (ctx->insn_flags & ASE_DSP) {
1550             generate_exception_end(ctx, EXCP_DSPDIS);
1551         } else {
1552             gen_reserved_instruction(ctx);
1553         }
1554     }
1555 }
1556 
1557 static inline void check_dsp_r2(DisasContext *ctx)
1558 {
1559     if (unlikely(!(ctx->hflags & MIPS_HFLAG_DSP_R2))) {
1560         if (ctx->insn_flags & ASE_DSP) {
1561             generate_exception_end(ctx, EXCP_DSPDIS);
1562         } else {
1563             gen_reserved_instruction(ctx);
1564         }
1565     }
1566 }
1567 
1568 static inline void check_dsp_r3(DisasContext *ctx)
1569 {
1570     if (unlikely(!(ctx->hflags & MIPS_HFLAG_DSP_R3))) {
1571         if (ctx->insn_flags & ASE_DSP) {
1572             generate_exception_end(ctx, EXCP_DSPDIS);
1573         } else {
1574             gen_reserved_instruction(ctx);
1575         }
1576     }
1577 }
1578 
1579 /*
1580  * This code generates a "reserved instruction" exception if the
1581  * CPU does not support the instruction set corresponding to flags.
1582  */
1583 void check_insn(DisasContext *ctx, uint64_t flags)
1584 {
1585     if (unlikely(!(ctx->insn_flags & flags))) {
1586         gen_reserved_instruction(ctx);
1587     }
1588 }
1589 
1590 /*
1591  * This code generates a "reserved instruction" exception if the
1592  * CPU has corresponding flag set which indicates that the instruction
1593  * has been removed.
1594  */
1595 static inline void check_insn_opc_removed(DisasContext *ctx, uint64_t flags)
1596 {
1597     if (unlikely(ctx->insn_flags & flags)) {
1598         gen_reserved_instruction(ctx);
1599     }
1600 }
1601 
1602 /*
1603  * The Linux kernel traps certain reserved instruction exceptions to
1604  * emulate the corresponding instructions. QEMU is the kernel in user
1605  * mode, so those traps are emulated by accepting the instructions.
1606  *
1607  * A reserved instruction exception is generated for flagged CPUs if
1608  * QEMU runs in system mode.
1609  */
1610 static inline void check_insn_opc_user_only(DisasContext *ctx, uint64_t flags)
1611 {
1612 #ifndef CONFIG_USER_ONLY
1613     check_insn_opc_removed(ctx, flags);
1614 #endif
1615 }
1616 
1617 /*
1618  * This code generates a "reserved instruction" exception if the
1619  * CPU does not support 64-bit paired-single (PS) floating point data type.
1620  */
1621 static inline void check_ps(DisasContext *ctx)
1622 {
1623     if (unlikely(!ctx->ps)) {
1624         generate_exception(ctx, EXCP_RI);
1625     }
1626     check_cp1_64bitmode(ctx);
1627 }
1628 
1629 bool decode_64bit_enabled(DisasContext *ctx)
1630 {
1631     return ctx->hflags & MIPS_HFLAG_64;
1632 }
1633 
1634 /*
1635  * This code generates a "reserved instruction" exception if cpu is not
1636  * 64-bit or 64-bit instructions are not enabled.
1637  */
1638 void check_mips_64(DisasContext *ctx)
1639 {
1640     if (unlikely((TARGET_LONG_BITS != 64) || !decode_64bit_enabled(ctx))) {
1641         gen_reserved_instruction(ctx);
1642     }
1643 }
1644 
1645 #ifndef CONFIG_USER_ONLY
1646 static inline void check_mvh(DisasContext *ctx)
1647 {
1648     if (unlikely(!ctx->mvh)) {
1649         generate_exception(ctx, EXCP_RI);
1650     }
1651 }
1652 #endif
1653 
1654 /*
1655  * This code generates a "reserved instruction" exception if the
1656  * Config5 XNP bit is set.
1657  */
1658 static inline void check_xnp(DisasContext *ctx)
1659 {
1660     if (unlikely(ctx->CP0_Config5 & (1 << CP0C5_XNP))) {
1661         gen_reserved_instruction(ctx);
1662     }
1663 }
1664 
1665 #ifndef CONFIG_USER_ONLY
1666 /*
1667  * This code generates a "reserved instruction" exception if the
1668  * Config3 PW bit is NOT set.
1669  */
1670 static inline void check_pw(DisasContext *ctx)
1671 {
1672     if (unlikely(!(ctx->CP0_Config3 & (1 << CP0C3_PW)))) {
1673         gen_reserved_instruction(ctx);
1674     }
1675 }
1676 #endif
1677 
1678 /*
1679  * This code generates a "reserved instruction" exception if the
1680  * Config3 MT bit is NOT set.
1681  */
1682 static inline void check_mt(DisasContext *ctx)
1683 {
1684     if (unlikely(!(ctx->CP0_Config3 & (1 << CP0C3_MT)))) {
1685         gen_reserved_instruction(ctx);
1686     }
1687 }
1688 
1689 #ifndef CONFIG_USER_ONLY
1690 /*
1691  * This code generates a "coprocessor unusable" exception if CP0 is not
1692  * available, and, if that is not the case, generates a "reserved instruction"
1693  * exception if the Config5 MT bit is NOT set. This is needed for availability
1694  * control of some of MT ASE instructions.
1695  */
1696 static inline void check_cp0_mt(DisasContext *ctx)
1697 {
1698     if (unlikely(!(ctx->hflags & MIPS_HFLAG_CP0))) {
1699         generate_exception_end(ctx, EXCP_CpU);
1700     } else {
1701         if (unlikely(!(ctx->CP0_Config3 & (1 << CP0C3_MT)))) {
1702             gen_reserved_instruction(ctx);
1703         }
1704     }
1705 }
1706 #endif
1707 
1708 /*
1709  * This code generates a "reserved instruction" exception if the
1710  * Config5 NMS bit is set.
1711  */
1712 static inline void check_nms(DisasContext *ctx)
1713 {
1714     if (unlikely(ctx->CP0_Config5 & (1 << CP0C5_NMS))) {
1715         gen_reserved_instruction(ctx);
1716     }
1717 }
1718 
1719 /*
1720  * This code generates a "reserved instruction" exception if the
1721  * Config5 NMS bit is set, and Config1 DL, Config1 IL, Config2 SL,
1722  * Config2 TL, and Config5 L2C are unset.
1723  */
1724 static inline void check_nms_dl_il_sl_tl_l2c(DisasContext *ctx)
1725 {
1726     if (unlikely((ctx->CP0_Config5 & (1 << CP0C5_NMS)) &&
1727                  !(ctx->CP0_Config1 & (1 << CP0C1_DL)) &&
1728                  !(ctx->CP0_Config1 & (1 << CP0C1_IL)) &&
1729                  !(ctx->CP0_Config2 & (1 << CP0C2_SL)) &&
1730                  !(ctx->CP0_Config2 & (1 << CP0C2_TL)) &&
1731                  !(ctx->CP0_Config5 & (1 << CP0C5_L2C)))) {
1732         gen_reserved_instruction(ctx);
1733     }
1734 }
1735 
1736 /*
1737  * This code generates a "reserved instruction" exception if the
1738  * Config5 EVA bit is NOT set.
1739  */
1740 static inline void check_eva(DisasContext *ctx)
1741 {
1742     if (unlikely(!(ctx->CP0_Config5 & (1 << CP0C5_EVA)))) {
1743         gen_reserved_instruction(ctx);
1744     }
1745 }
1746 
1747 
1748 /*
1749  * Define small wrappers for gen_load_fpr* so that we have a uniform
1750  * calling interface for 32 and 64-bit FPRs.  No sense in changing
1751  * all callers for gen_load_fpr32 when we need the CTX parameter for
1752  * this one use.
1753  */
1754 #define gen_ldcmp_fpr32(ctx, x, y) gen_load_fpr32(ctx, x, y)
1755 #define gen_ldcmp_fpr64(ctx, x, y) gen_load_fpr64(ctx, x, y)
1756 #define FOP_CONDS(type, abs, fmt, ifmt, bits)                                 \
1757 static inline void gen_cmp ## type ## _ ## fmt(DisasContext *ctx, int n,      \
1758                                                int ft, int fs, int cc)        \
1759 {                                                                             \
1760     TCGv_i##bits fp0 = tcg_temp_new_i##bits();                                \
1761     TCGv_i##bits fp1 = tcg_temp_new_i##bits();                                \
1762     switch (ifmt) {                                                           \
1763     case FMT_PS:                                                              \
1764         check_ps(ctx);                                                        \
1765         break;                                                                \
1766     case FMT_D:                                                               \
1767         if (abs) {                                                            \
1768             check_cop1x(ctx);                                                 \
1769         }                                                                     \
1770         check_cp1_registers(ctx, fs | ft);                                    \
1771         break;                                                                \
1772     case FMT_S:                                                               \
1773         if (abs) {                                                            \
1774             check_cop1x(ctx);                                                 \
1775         }                                                                     \
1776         break;                                                                \
1777     }                                                                         \
1778     gen_ldcmp_fpr##bits(ctx, fp0, fs);                                        \
1779     gen_ldcmp_fpr##bits(ctx, fp1, ft);                                        \
1780     switch (n) {                                                              \
1781     case  0:                                                                  \
1782         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _f, fp0, fp1, cc);         \
1783     break;                                                                    \
1784     case  1:                                                                  \
1785         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _un, fp0, fp1, cc);        \
1786     break;                                                                    \
1787     case  2:                                                                  \
1788         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _eq, fp0, fp1, cc);        \
1789     break;                                                                    \
1790     case  3:                                                                  \
1791         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _ueq, fp0, fp1, cc);       \
1792     break;                                                                    \
1793     case  4:                                                                  \
1794         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _olt, fp0, fp1, cc);       \
1795     break;                                                                    \
1796     case  5:                                                                  \
1797         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _ult, fp0, fp1, cc);       \
1798     break;                                                                    \
1799     case  6:                                                                  \
1800         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _ole, fp0, fp1, cc);       \
1801     break;                                                                    \
1802     case  7:                                                                  \
1803         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _ule, fp0, fp1, cc);       \
1804     break;                                                                    \
1805     case  8:                                                                  \
1806         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _sf, fp0, fp1, cc);        \
1807     break;                                                                    \
1808     case  9:                                                                  \
1809         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _ngle, fp0, fp1, cc);      \
1810     break;                                                                    \
1811     case 10:                                                                  \
1812         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _seq, fp0, fp1, cc);       \
1813     break;                                                                    \
1814     case 11:                                                                  \
1815         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _ngl, fp0, fp1, cc);       \
1816     break;                                                                    \
1817     case 12:                                                                  \
1818         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _lt, fp0, fp1, cc);        \
1819     break;                                                                    \
1820     case 13:                                                                  \
1821         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _nge, fp0, fp1, cc);       \
1822     break;                                                                    \
1823     case 14:                                                                  \
1824         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _le, fp0, fp1, cc);        \
1825     break;                                                                    \
1826     case 15:                                                                  \
1827         gen_helper_0e2i(cmp ## type ## _ ## fmt ## _ngt, fp0, fp1, cc);       \
1828     break;                                                                    \
1829     default:                                                                  \
1830         abort();                                                              \
1831     }                                                                         \
1832 }
1833 
1834 FOP_CONDS(, 0, d, FMT_D, 64)
1835 FOP_CONDS(abs, 1, d, FMT_D, 64)
1836 FOP_CONDS(, 0, s, FMT_S, 32)
1837 FOP_CONDS(abs, 1, s, FMT_S, 32)
1838 FOP_CONDS(, 0, ps, FMT_PS, 64)
1839 FOP_CONDS(abs, 1, ps, FMT_PS, 64)
1840 #undef FOP_CONDS
1841 
1842 #define FOP_CONDNS(fmt, ifmt, bits, STORE)                              \
1843 static inline void gen_r6_cmp_ ## fmt(DisasContext *ctx, int n,         \
1844                                       int ft, int fs, int fd)           \
1845 {                                                                       \
1846     TCGv_i ## bits fp0 = tcg_temp_new_i ## bits();                      \
1847     TCGv_i ## bits fp1 = tcg_temp_new_i ## bits();                      \
1848     if (ifmt == FMT_D) {                                                \
1849         check_cp1_registers(ctx, fs | ft | fd);                         \
1850     }                                                                   \
1851     gen_ldcmp_fpr ## bits(ctx, fp0, fs);                                \
1852     gen_ldcmp_fpr ## bits(ctx, fp1, ft);                                \
1853     switch (n) {                                                        \
1854     case  0:                                                            \
1855         gen_helper_r6_cmp_ ## fmt ## _af(fp0, tcg_env, fp0, fp1);       \
1856         break;                                                          \
1857     case  1:                                                            \
1858         gen_helper_r6_cmp_ ## fmt ## _un(fp0, tcg_env, fp0, fp1);       \
1859         break;                                                          \
1860     case  2:                                                            \
1861         gen_helper_r6_cmp_ ## fmt ## _eq(fp0, tcg_env, fp0, fp1);       \
1862         break;                                                          \
1863     case  3:                                                            \
1864         gen_helper_r6_cmp_ ## fmt ## _ueq(fp0, tcg_env, fp0, fp1);      \
1865         break;                                                          \
1866     case  4:                                                            \
1867         gen_helper_r6_cmp_ ## fmt ## _lt(fp0, tcg_env, fp0, fp1);       \
1868         break;                                                          \
1869     case  5:                                                            \
1870         gen_helper_r6_cmp_ ## fmt ## _ult(fp0, tcg_env, fp0, fp1);      \
1871         break;                                                          \
1872     case  6:                                                            \
1873         gen_helper_r6_cmp_ ## fmt ## _le(fp0, tcg_env, fp0, fp1);       \
1874         break;                                                          \
1875     case  7:                                                            \
1876         gen_helper_r6_cmp_ ## fmt ## _ule(fp0, tcg_env, fp0, fp1);      \
1877         break;                                                          \
1878     case  8:                                                            \
1879         gen_helper_r6_cmp_ ## fmt ## _saf(fp0, tcg_env, fp0, fp1);      \
1880         break;                                                          \
1881     case  9:                                                            \
1882         gen_helper_r6_cmp_ ## fmt ## _sun(fp0, tcg_env, fp0, fp1);      \
1883         break;                                                          \
1884     case 10:                                                            \
1885         gen_helper_r6_cmp_ ## fmt ## _seq(fp0, tcg_env, fp0, fp1);      \
1886         break;                                                          \
1887     case 11:                                                            \
1888         gen_helper_r6_cmp_ ## fmt ## _sueq(fp0, tcg_env, fp0, fp1);     \
1889         break;                                                          \
1890     case 12:                                                            \
1891         gen_helper_r6_cmp_ ## fmt ## _slt(fp0, tcg_env, fp0, fp1);      \
1892         break;                                                          \
1893     case 13:                                                            \
1894         gen_helper_r6_cmp_ ## fmt ## _sult(fp0, tcg_env, fp0, fp1);     \
1895         break;                                                          \
1896     case 14:                                                            \
1897         gen_helper_r6_cmp_ ## fmt ## _sle(fp0, tcg_env, fp0, fp1);      \
1898         break;                                                          \
1899     case 15:                                                            \
1900         gen_helper_r6_cmp_ ## fmt ## _sule(fp0, tcg_env, fp0, fp1);     \
1901         break;                                                          \
1902     case 17:                                                            \
1903         gen_helper_r6_cmp_ ## fmt ## _or(fp0, tcg_env, fp0, fp1);       \
1904         break;                                                          \
1905     case 18:                                                            \
1906         gen_helper_r6_cmp_ ## fmt ## _une(fp0, tcg_env, fp0, fp1);      \
1907         break;                                                          \
1908     case 19:                                                            \
1909         gen_helper_r6_cmp_ ## fmt ## _ne(fp0, tcg_env, fp0, fp1);       \
1910         break;                                                          \
1911     case 25:                                                            \
1912         gen_helper_r6_cmp_ ## fmt ## _sor(fp0, tcg_env, fp0, fp1);      \
1913         break;                                                          \
1914     case 26:                                                            \
1915         gen_helper_r6_cmp_ ## fmt ## _sune(fp0, tcg_env, fp0, fp1);     \
1916         break;                                                          \
1917     case 27:                                                            \
1918         gen_helper_r6_cmp_ ## fmt ## _sne(fp0, tcg_env, fp0, fp1);      \
1919         break;                                                          \
1920     default:                                                            \
1921         abort();                                                        \
1922     }                                                                   \
1923     STORE;                                                              \
1924 }
1925 
1926 FOP_CONDNS(d, FMT_D, 64, gen_store_fpr64(ctx, fp0, fd))
1927 FOP_CONDNS(s, FMT_S, 32, gen_store_fpr32(ctx, fp0, fd))
1928 #undef FOP_CONDNS
1929 #undef gen_ldcmp_fpr32
1930 #undef gen_ldcmp_fpr64
1931 
1932 /* load/store instructions. */
1933 #ifdef CONFIG_USER_ONLY
1934 #define OP_LD_ATOMIC(insn, memop)                                          \
1935 static inline void op_ld_##insn(TCGv ret, TCGv arg1, int mem_idx,          \
1936                                 DisasContext *ctx)                         \
1937 {                                                                          \
1938     TCGv t0 = tcg_temp_new();                                              \
1939     tcg_gen_mov_tl(t0, arg1);                                              \
1940     tcg_gen_qemu_ld_tl(ret, arg1, ctx->mem_idx, memop);                    \
1941     tcg_gen_st_tl(t0, tcg_env, offsetof(CPUMIPSState, lladdr));            \
1942     tcg_gen_st_tl(ret, tcg_env, offsetof(CPUMIPSState, llval));            \
1943 }
1944 #else
1945 #define OP_LD_ATOMIC(insn, ignored_memop)                                  \
1946 static inline void op_ld_##insn(TCGv ret, TCGv arg1, int mem_idx,          \
1947                                 DisasContext *ctx)                         \
1948 {                                                                          \
1949     gen_helper_##insn(ret, tcg_env, arg1, tcg_constant_i32(mem_idx));      \
1950 }
1951 #endif
1952 OP_LD_ATOMIC(ll, mo_endian(ctx) | MO_SL);
1953 #if defined(TARGET_MIPS64)
1954 OP_LD_ATOMIC(lld, mo_endian(ctx) | MO_UQ);
1955 #endif
1956 #undef OP_LD_ATOMIC
1957 
1958 void gen_base_offset_addr(DisasContext *ctx, TCGv addr, int base, int offset)
1959 {
1960     if (base == 0) {
1961         tcg_gen_movi_tl(addr, offset);
1962     } else if (offset == 0) {
1963         gen_load_gpr(addr, base);
1964     } else {
1965         tcg_gen_movi_tl(addr, offset);
1966         gen_op_addr_add(ctx, addr, cpu_gpr[base], addr);
1967     }
1968 }
1969 
1970 static target_ulong pc_relative_pc(DisasContext *ctx)
1971 {
1972     target_ulong pc = ctx->base.pc_next;
1973 
1974     if (ctx->hflags & MIPS_HFLAG_BMASK) {
1975         int branch_bytes = ctx->hflags & MIPS_HFLAG_BDS16 ? 2 : 4;
1976 
1977         pc -= branch_bytes;
1978     }
1979 
1980     pc &= ~(target_ulong)3;
1981     return pc;
1982 }
1983 
1984 /* LWL or LDL, depending on MemOp. */
1985 static void gen_lxl(DisasContext *ctx, TCGv reg, TCGv addr,
1986                      int mem_idx, MemOp mop)
1987 {
1988     int sizem1 = memop_size(mop) - 1;
1989     TCGv t0 = tcg_temp_new();
1990     TCGv t1 = tcg_temp_new();
1991 
1992     /*
1993      * Do a byte access to possibly trigger a page
1994      * fault with the unaligned address.
1995      */
1996     tcg_gen_qemu_ld_tl(t1, addr, mem_idx, MO_UB);
1997     tcg_gen_andi_tl(t1, addr, sizem1);
1998     if (!disas_is_bigendian(ctx)) {
1999         tcg_gen_xori_tl(t1, t1, sizem1);
2000     }
2001     tcg_gen_shli_tl(t1, t1, 3);
2002     tcg_gen_andi_tl(t0, addr, ~sizem1);
2003     tcg_gen_qemu_ld_tl(t0, t0, mem_idx, mop);
2004     tcg_gen_shl_tl(t0, t0, t1);
2005     tcg_gen_shl_tl(t1, tcg_constant_tl(-1), t1);
2006     tcg_gen_andc_tl(t1, reg, t1);
2007     tcg_gen_or_tl(reg, t0, t1);
2008 }
2009 
2010 /* LWR or LDR, depending on MemOp. */
2011 static void gen_lxr(DisasContext *ctx, TCGv reg, TCGv addr,
2012                      int mem_idx, MemOp mop)
2013 {
2014     int size = memop_size(mop);
2015     int sizem1 = size - 1;
2016     TCGv t0 = tcg_temp_new();
2017     TCGv t1 = tcg_temp_new();
2018 
2019     /*
2020      * Do a byte access to possibly trigger a page
2021      * fault with the unaligned address.
2022      */
2023     tcg_gen_qemu_ld_tl(t1, addr, mem_idx, MO_UB);
2024     tcg_gen_andi_tl(t1, addr, sizem1);
2025     if (disas_is_bigendian(ctx)) {
2026         tcg_gen_xori_tl(t1, t1, sizem1);
2027     }
2028     tcg_gen_shli_tl(t1, t1, 3);
2029     tcg_gen_andi_tl(t0, addr, ~sizem1);
2030     tcg_gen_qemu_ld_tl(t0, t0, mem_idx, mop);
2031     tcg_gen_shr_tl(t0, t0, t1);
2032     tcg_gen_xori_tl(t1, t1, size * 8 - 1);
2033     tcg_gen_shl_tl(t1, tcg_constant_tl(~1), t1);
2034     tcg_gen_and_tl(t1, reg, t1);
2035     tcg_gen_or_tl(reg, t0, t1);
2036 }
2037 
2038 /* Load */
2039 static void gen_ld(DisasContext *ctx, uint32_t opc,
2040                    int rt, int base, int offset)
2041 {
2042     TCGv t0, t1;
2043     int mem_idx = ctx->mem_idx;
2044 
2045     if (rt == 0 && ctx->insn_flags & (INSN_LOONGSON2E | INSN_LOONGSON2F |
2046                                       INSN_LOONGSON3A)) {
2047         /*
2048          * Loongson CPU uses a load to zero register for prefetch.
2049          * We emulate it as a NOP. On other CPU we must perform the
2050          * actual memory access.
2051          */
2052         return;
2053     }
2054 
2055     t0 = tcg_temp_new();
2056     gen_base_offset_addr(ctx, t0, base, offset);
2057 
2058     switch (opc) {
2059 #if defined(TARGET_MIPS64)
2060     case OPC_LWU:
2061         tcg_gen_qemu_ld_tl(t0, t0, mem_idx, mo_endian(ctx) | MO_UL |
2062                            ctx->default_tcg_memop_mask);
2063         gen_store_gpr(t0, rt);
2064         break;
2065     case OPC_LD:
2066         tcg_gen_qemu_ld_tl(t0, t0, mem_idx, mo_endian(ctx) | MO_UQ |
2067                            ctx->default_tcg_memop_mask);
2068         gen_store_gpr(t0, rt);
2069         break;
2070     case OPC_LLD:
2071     case R6_OPC_LLD:
2072         op_ld_lld(t0, t0, mem_idx, ctx);
2073         gen_store_gpr(t0, rt);
2074         break;
2075     case OPC_LDL:
2076         t1 = tcg_temp_new();
2077         gen_load_gpr(t1, rt);
2078         gen_lxl(ctx, t1, t0, mem_idx, mo_endian(ctx) | MO_UQ);
2079         gen_store_gpr(t1, rt);
2080         break;
2081     case OPC_LDR:
2082         t1 = tcg_temp_new();
2083         gen_load_gpr(t1, rt);
2084         gen_lxr(ctx, t1, t0, mem_idx, mo_endian(ctx) | MO_UQ);
2085         gen_store_gpr(t1, rt);
2086         break;
2087     case OPC_LDPC:
2088         t1 = tcg_constant_tl(pc_relative_pc(ctx));
2089         gen_op_addr_add(ctx, t0, t0, t1);
2090         tcg_gen_qemu_ld_tl(t0, t0, mem_idx, mo_endian(ctx) | MO_UQ);
2091         gen_store_gpr(t0, rt);
2092         break;
2093 #endif
2094     case OPC_LWPC:
2095         t1 = tcg_constant_tl(pc_relative_pc(ctx));
2096         gen_op_addr_add(ctx, t0, t0, t1);
2097         tcg_gen_qemu_ld_tl(t0, t0, mem_idx, mo_endian(ctx) | MO_SL);
2098         gen_store_gpr(t0, rt);
2099         break;
2100     case OPC_LWE:
2101         mem_idx = MIPS_HFLAG_UM;
2102         /* fall through */
2103     case OPC_LW:
2104         tcg_gen_qemu_ld_tl(t0, t0, mem_idx, mo_endian(ctx) | MO_SL |
2105                            ctx->default_tcg_memop_mask);
2106         gen_store_gpr(t0, rt);
2107         break;
2108     case OPC_LHE:
2109         mem_idx = MIPS_HFLAG_UM;
2110         /* fall through */
2111     case OPC_LH:
2112         tcg_gen_qemu_ld_tl(t0, t0, mem_idx, mo_endian(ctx) | MO_SW |
2113                            ctx->default_tcg_memop_mask);
2114         gen_store_gpr(t0, rt);
2115         break;
2116     case OPC_LHUE:
2117         mem_idx = MIPS_HFLAG_UM;
2118         /* fall through */
2119     case OPC_LHU:
2120         tcg_gen_qemu_ld_tl(t0, t0, mem_idx, mo_endian(ctx) | MO_UW |
2121                            ctx->default_tcg_memop_mask);
2122         gen_store_gpr(t0, rt);
2123         break;
2124     case OPC_LBE:
2125         mem_idx = MIPS_HFLAG_UM;
2126         /* fall through */
2127     case OPC_LB:
2128         tcg_gen_qemu_ld_tl(t0, t0, mem_idx, MO_SB);
2129         gen_store_gpr(t0, rt);
2130         break;
2131     case OPC_LBUE:
2132         mem_idx = MIPS_HFLAG_UM;
2133         /* fall through */
2134     case OPC_LBU:
2135         tcg_gen_qemu_ld_tl(t0, t0, mem_idx, MO_UB);
2136         gen_store_gpr(t0, rt);
2137         break;
2138     case OPC_LWLE:
2139         mem_idx = MIPS_HFLAG_UM;
2140         /* fall through */
2141     case OPC_LWL:
2142         t1 = tcg_temp_new();
2143         gen_load_gpr(t1, rt);
2144         gen_lxl(ctx, t1, t0, mem_idx, mo_endian(ctx) | MO_UL);
2145         tcg_gen_ext32s_tl(t1, t1);
2146         gen_store_gpr(t1, rt);
2147         break;
2148     case OPC_LWRE:
2149         mem_idx = MIPS_HFLAG_UM;
2150         /* fall through */
2151     case OPC_LWR:
2152         t1 = tcg_temp_new();
2153         gen_load_gpr(t1, rt);
2154         gen_lxr(ctx, t1, t0, mem_idx, mo_endian(ctx) | MO_UL);
2155         tcg_gen_ext32s_tl(t1, t1);
2156         gen_store_gpr(t1, rt);
2157         break;
2158     case OPC_LLE:
2159         mem_idx = MIPS_HFLAG_UM;
2160         /* fall through */
2161     case OPC_LL:
2162     case R6_OPC_LL:
2163         op_ld_ll(t0, t0, mem_idx, ctx);
2164         gen_store_gpr(t0, rt);
2165         break;
2166     }
2167 }
2168 
2169 /* Store */
2170 static void gen_st(DisasContext *ctx, uint32_t opc, int rt,
2171                    int base, int offset)
2172 {
2173     TCGv t0 = tcg_temp_new();
2174     TCGv t1 = tcg_temp_new();
2175     int mem_idx = ctx->mem_idx;
2176 
2177     gen_base_offset_addr(ctx, t0, base, offset);
2178     gen_load_gpr(t1, rt);
2179     switch (opc) {
2180 #if defined(TARGET_MIPS64)
2181     case OPC_SD:
2182         tcg_gen_qemu_st_tl(t1, t0, mem_idx, mo_endian(ctx) | MO_UQ |
2183                            ctx->default_tcg_memop_mask);
2184         break;
2185     case OPC_SDL:
2186         gen_helper_0e2i(sdl, t1, t0, mem_idx);
2187         break;
2188     case OPC_SDR:
2189         gen_helper_0e2i(sdr, t1, t0, mem_idx);
2190         break;
2191 #endif
2192     case OPC_SWE:
2193         mem_idx = MIPS_HFLAG_UM;
2194         /* fall through */
2195     case OPC_SW:
2196         tcg_gen_qemu_st_tl(t1, t0, mem_idx, mo_endian(ctx) | MO_UL |
2197                            ctx->default_tcg_memop_mask);
2198         break;
2199     case OPC_SHE:
2200         mem_idx = MIPS_HFLAG_UM;
2201         /* fall through */
2202     case OPC_SH:
2203         tcg_gen_qemu_st_tl(t1, t0, mem_idx, mo_endian(ctx) | MO_UW |
2204                            ctx->default_tcg_memop_mask);
2205         break;
2206     case OPC_SBE:
2207         mem_idx = MIPS_HFLAG_UM;
2208         /* fall through */
2209     case OPC_SB:
2210         tcg_gen_qemu_st_tl(t1, t0, mem_idx, MO_8);
2211         break;
2212     case OPC_SWLE:
2213         mem_idx = MIPS_HFLAG_UM;
2214         /* fall through */
2215     case OPC_SWL:
2216         gen_helper_0e2i(swl, t1, t0, mem_idx);
2217         break;
2218     case OPC_SWRE:
2219         mem_idx = MIPS_HFLAG_UM;
2220         /* fall through */
2221     case OPC_SWR:
2222         gen_helper_0e2i(swr, t1, t0, mem_idx);
2223         break;
2224     }
2225 }
2226 
2227 
2228 /* Store conditional */
2229 static void gen_st_cond(DisasContext *ctx, int rt, int base, int offset,
2230                         MemOp tcg_mo, bool eva)
2231 {
2232     TCGv addr, t0, val;
2233     TCGLabel *l1 = gen_new_label();
2234     TCGLabel *done = gen_new_label();
2235 
2236     t0 = tcg_temp_new();
2237     addr = tcg_temp_new();
2238     /* compare the address against that of the preceding LL */
2239     gen_base_offset_addr(ctx, addr, base, offset);
2240     tcg_gen_brcond_tl(TCG_COND_EQ, addr, cpu_lladdr, l1);
2241     gen_store_gpr(tcg_constant_tl(0), rt);
2242     tcg_gen_br(done);
2243 
2244     gen_set_label(l1);
2245     /* generate cmpxchg */
2246     val = tcg_temp_new();
2247     gen_load_gpr(val, rt);
2248     tcg_gen_atomic_cmpxchg_tl(t0, cpu_lladdr, cpu_llval, val,
2249                               eva ? MIPS_HFLAG_UM : ctx->mem_idx, tcg_mo);
2250     tcg_gen_setcond_tl(TCG_COND_EQ, t0, t0, cpu_llval);
2251     gen_store_gpr(t0, rt);
2252 
2253     gen_set_label(done);
2254 }
2255 
2256 /* Load and store */
2257 static void gen_flt_ldst(DisasContext *ctx, uint32_t opc, int ft,
2258                          TCGv t0)
2259 {
2260     /*
2261      * Don't do NOP if destination is zero: we must perform the actual
2262      * memory access.
2263      */
2264     switch (opc) {
2265     case OPC_LWC1:
2266         {
2267             TCGv_i32 fp0 = tcg_temp_new_i32();
2268             tcg_gen_qemu_ld_i32(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_SL |
2269                                 ctx->default_tcg_memop_mask);
2270             gen_store_fpr32(ctx, fp0, ft);
2271         }
2272         break;
2273     case OPC_SWC1:
2274         {
2275             TCGv_i32 fp0 = tcg_temp_new_i32();
2276             gen_load_fpr32(ctx, fp0, ft);
2277             tcg_gen_qemu_st_i32(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UL |
2278                                 ctx->default_tcg_memop_mask);
2279         }
2280         break;
2281     case OPC_LDC1:
2282         {
2283             TCGv_i64 fp0 = tcg_temp_new_i64();
2284             tcg_gen_qemu_ld_i64(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
2285                                 ctx->default_tcg_memop_mask);
2286             gen_store_fpr64(ctx, fp0, ft);
2287         }
2288         break;
2289     case OPC_SDC1:
2290         {
2291             TCGv_i64 fp0 = tcg_temp_new_i64();
2292             gen_load_fpr64(ctx, fp0, ft);
2293             tcg_gen_qemu_st_i64(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
2294                                 ctx->default_tcg_memop_mask);
2295         }
2296         break;
2297     default:
2298         MIPS_INVAL("flt_ldst");
2299         gen_reserved_instruction(ctx);
2300         break;
2301     }
2302 }
2303 
2304 static void gen_cop1_ldst(DisasContext *ctx, uint32_t op, int rt,
2305                           int rs, int16_t imm)
2306 {
2307     TCGv t0 = tcg_temp_new();
2308 
2309     if (ctx->CP0_Config1 & (1 << CP0C1_FP)) {
2310         check_cp1_enabled(ctx);
2311         switch (op) {
2312         case OPC_LDC1:
2313         case OPC_SDC1:
2314             check_insn(ctx, ISA_MIPS2);
2315             /* Fallthrough */
2316         default:
2317             gen_base_offset_addr(ctx, t0, rs, imm);
2318             gen_flt_ldst(ctx, op, rt, t0);
2319         }
2320     } else {
2321         generate_exception_err(ctx, EXCP_CpU, 1);
2322     }
2323 }
2324 
2325 /* Arithmetic with immediate operand */
2326 static void gen_arith_imm(DisasContext *ctx, uint32_t opc,
2327                           int rt, int rs, int imm)
2328 {
2329     target_ulong uimm = (target_long)imm; /* Sign extend to 32/64 bits */
2330 
2331     if (rt == 0 && opc != OPC_ADDI && opc != OPC_DADDI) {
2332         /*
2333          * If no destination, treat it as a NOP.
2334          * For addi, we must generate the overflow exception when needed.
2335          */
2336         return;
2337     }
2338     switch (opc) {
2339     case OPC_ADDI:
2340         {
2341             TCGv t0 = tcg_temp_new();
2342             TCGv t1 = tcg_temp_new();
2343             TCGv t2 = tcg_temp_new();
2344             TCGLabel *l1 = gen_new_label();
2345 
2346             gen_load_gpr(t1, rs);
2347             tcg_gen_addi_tl(t0, t1, uimm);
2348             tcg_gen_ext32s_tl(t0, t0);
2349 
2350             tcg_gen_xori_tl(t1, t1, ~uimm);
2351             tcg_gen_xori_tl(t2, t0, uimm);
2352             tcg_gen_and_tl(t1, t1, t2);
2353             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
2354             /* operands of same sign, result different sign */
2355             generate_exception(ctx, EXCP_OVERFLOW);
2356             gen_set_label(l1);
2357             tcg_gen_ext32s_tl(t0, t0);
2358             gen_store_gpr(t0, rt);
2359         }
2360         break;
2361     case OPC_ADDIU:
2362         if (rs != 0) {
2363             tcg_gen_addi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
2364             tcg_gen_ext32s_tl(cpu_gpr[rt], cpu_gpr[rt]);
2365         } else {
2366             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
2367         }
2368         break;
2369 #if defined(TARGET_MIPS64)
2370     case OPC_DADDI:
2371         {
2372             TCGv t0 = tcg_temp_new();
2373             TCGv t1 = tcg_temp_new();
2374             TCGv t2 = tcg_temp_new();
2375             TCGLabel *l1 = gen_new_label();
2376 
2377             gen_load_gpr(t1, rs);
2378             tcg_gen_addi_tl(t0, t1, uimm);
2379 
2380             tcg_gen_xori_tl(t1, t1, ~uimm);
2381             tcg_gen_xori_tl(t2, t0, uimm);
2382             tcg_gen_and_tl(t1, t1, t2);
2383             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
2384             /* operands of same sign, result different sign */
2385             generate_exception(ctx, EXCP_OVERFLOW);
2386             gen_set_label(l1);
2387             gen_store_gpr(t0, rt);
2388         }
2389         break;
2390     case OPC_DADDIU:
2391         if (rs != 0) {
2392             tcg_gen_addi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
2393         } else {
2394             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
2395         }
2396         break;
2397 #endif
2398     }
2399 }
2400 
2401 /* Logic with immediate operand */
2402 static void gen_logic_imm(DisasContext *ctx, uint32_t opc,
2403                           int rt, int rs, int16_t imm)
2404 {
2405     target_ulong uimm;
2406 
2407     if (rt == 0) {
2408         /* If no destination, treat it as a NOP. */
2409         return;
2410     }
2411     uimm = (uint16_t)imm;
2412     switch (opc) {
2413     case OPC_ANDI:
2414         if (likely(rs != 0)) {
2415             tcg_gen_andi_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
2416         } else {
2417             tcg_gen_movi_tl(cpu_gpr[rt], 0);
2418         }
2419         break;
2420     case OPC_ORI:
2421         if (rs != 0) {
2422             tcg_gen_ori_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
2423         } else {
2424             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
2425         }
2426         break;
2427     case OPC_XORI:
2428         if (likely(rs != 0)) {
2429             tcg_gen_xori_tl(cpu_gpr[rt], cpu_gpr[rs], uimm);
2430         } else {
2431             tcg_gen_movi_tl(cpu_gpr[rt], uimm);
2432         }
2433         break;
2434     case OPC_LUI:
2435         if (rs != 0 && (ctx->insn_flags & ISA_MIPS_R6)) {
2436             /* OPC_AUI */
2437             tcg_gen_addi_tl(cpu_gpr[rt], cpu_gpr[rs], imm << 16);
2438             tcg_gen_ext32s_tl(cpu_gpr[rt], cpu_gpr[rt]);
2439         } else {
2440             tcg_gen_movi_tl(cpu_gpr[rt], imm << 16);
2441         }
2442         break;
2443 
2444     default:
2445         break;
2446     }
2447 }
2448 
2449 /* Set on less than with immediate operand */
2450 static void gen_slt_imm(DisasContext *ctx, uint32_t opc,
2451                         int rt, int rs, int16_t imm)
2452 {
2453     target_ulong uimm = (target_long)imm; /* Sign extend to 32/64 bits */
2454     TCGv t0;
2455 
2456     if (rt == 0) {
2457         /* If no destination, treat it as a NOP. */
2458         return;
2459     }
2460     t0 = tcg_temp_new();
2461     gen_load_gpr(t0, rs);
2462     switch (opc) {
2463     case OPC_SLTI:
2464         tcg_gen_setcondi_tl(TCG_COND_LT, cpu_gpr[rt], t0, uimm);
2465         break;
2466     case OPC_SLTIU:
2467         tcg_gen_setcondi_tl(TCG_COND_LTU, cpu_gpr[rt], t0, uimm);
2468         break;
2469     }
2470 }
2471 
2472 /* Shifts with immediate operand */
2473 static void gen_shift_imm(DisasContext *ctx, uint32_t opc,
2474                           int rt, int rs, int16_t imm)
2475 {
2476     target_ulong uimm = ((uint16_t)imm) & 0x1f;
2477     TCGv t0;
2478 
2479     if (rt == 0) {
2480         /* If no destination, treat it as a NOP. */
2481         return;
2482     }
2483 
2484     t0 = tcg_temp_new();
2485     gen_load_gpr(t0, rs);
2486     switch (opc) {
2487     case OPC_SLL:
2488         tcg_gen_shli_tl(t0, t0, uimm);
2489         tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
2490         break;
2491     case OPC_SRA:
2492         tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm);
2493         break;
2494     case OPC_SRL:
2495         if (uimm != 0) {
2496             tcg_gen_ext32u_tl(t0, t0);
2497             tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm);
2498         } else {
2499             tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
2500         }
2501         break;
2502     case OPC_ROTR:
2503         if (uimm != 0) {
2504             TCGv_i32 t1 = tcg_temp_new_i32();
2505 
2506             tcg_gen_trunc_tl_i32(t1, t0);
2507             tcg_gen_rotri_i32(t1, t1, uimm);
2508             tcg_gen_ext_i32_tl(cpu_gpr[rt], t1);
2509         } else {
2510             tcg_gen_ext32s_tl(cpu_gpr[rt], t0);
2511         }
2512         break;
2513 #if defined(TARGET_MIPS64)
2514     case OPC_DSLL:
2515         tcg_gen_shli_tl(cpu_gpr[rt], t0, uimm);
2516         break;
2517     case OPC_DSRA:
2518         tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm);
2519         break;
2520     case OPC_DSRL:
2521         tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm);
2522         break;
2523     case OPC_DROTR:
2524         if (uimm != 0) {
2525             tcg_gen_rotri_tl(cpu_gpr[rt], t0, uimm);
2526         } else {
2527             tcg_gen_mov_tl(cpu_gpr[rt], t0);
2528         }
2529         break;
2530     case OPC_DSLL32:
2531         tcg_gen_shli_tl(cpu_gpr[rt], t0, uimm + 32);
2532         break;
2533     case OPC_DSRA32:
2534         tcg_gen_sari_tl(cpu_gpr[rt], t0, uimm + 32);
2535         break;
2536     case OPC_DSRL32:
2537         tcg_gen_shri_tl(cpu_gpr[rt], t0, uimm + 32);
2538         break;
2539     case OPC_DROTR32:
2540         tcg_gen_rotri_tl(cpu_gpr[rt], t0, uimm + 32);
2541         break;
2542 #endif
2543     }
2544 }
2545 
2546 /* Arithmetic */
2547 static void gen_arith(DisasContext *ctx, uint32_t opc,
2548                       int rd, int rs, int rt)
2549 {
2550     if (rd == 0 && opc != OPC_ADD && opc != OPC_SUB
2551        && opc != OPC_DADD && opc != OPC_DSUB) {
2552         /*
2553          * If no destination, treat it as a NOP.
2554          * For add & sub, we must generate the overflow exception when needed.
2555          */
2556         return;
2557     }
2558 
2559     switch (opc) {
2560     case OPC_ADD:
2561         {
2562             TCGv t0 = tcg_temp_new();
2563             TCGv t1 = tcg_temp_new();
2564             TCGv t2 = tcg_temp_new();
2565             TCGLabel *l1 = gen_new_label();
2566 
2567             gen_load_gpr(t1, rs);
2568             gen_load_gpr(t2, rt);
2569             tcg_gen_add_tl(t0, t1, t2);
2570             tcg_gen_ext32s_tl(t0, t0);
2571             tcg_gen_xor_tl(t1, t1, t2);
2572             tcg_gen_xor_tl(t2, t0, t2);
2573             tcg_gen_andc_tl(t1, t2, t1);
2574             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
2575             /* operands of same sign, result different sign */
2576             generate_exception(ctx, EXCP_OVERFLOW);
2577             gen_set_label(l1);
2578             gen_store_gpr(t0, rd);
2579         }
2580         break;
2581     case OPC_ADDU:
2582         if (rs != 0 && rt != 0) {
2583             tcg_gen_add_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
2584             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2585         } else if (rs == 0 && rt != 0) {
2586             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
2587         } else if (rs != 0 && rt == 0) {
2588             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
2589         } else {
2590             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2591         }
2592         break;
2593     case OPC_SUB:
2594         {
2595             TCGv t0 = tcg_temp_new();
2596             TCGv t1 = tcg_temp_new();
2597             TCGv t2 = tcg_temp_new();
2598             TCGLabel *l1 = gen_new_label();
2599 
2600             gen_load_gpr(t1, rs);
2601             gen_load_gpr(t2, rt);
2602             tcg_gen_sub_tl(t0, t1, t2);
2603             tcg_gen_ext32s_tl(t0, t0);
2604             tcg_gen_xor_tl(t2, t1, t2);
2605             tcg_gen_xor_tl(t1, t0, t1);
2606             tcg_gen_and_tl(t1, t1, t2);
2607             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
2608             /*
2609              * operands of different sign, first operand and the result
2610              * of different sign
2611              */
2612             generate_exception(ctx, EXCP_OVERFLOW);
2613             gen_set_label(l1);
2614             gen_store_gpr(t0, rd);
2615         }
2616         break;
2617     case OPC_SUBU:
2618         if (rs != 0 && rt != 0) {
2619             tcg_gen_sub_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
2620             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2621         } else if (rs == 0 && rt != 0) {
2622             tcg_gen_neg_tl(cpu_gpr[rd], cpu_gpr[rt]);
2623             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2624         } else if (rs != 0 && rt == 0) {
2625             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
2626         } else {
2627             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2628         }
2629         break;
2630 #if defined(TARGET_MIPS64)
2631     case OPC_DADD:
2632         {
2633             TCGv t0 = tcg_temp_new();
2634             TCGv t1 = tcg_temp_new();
2635             TCGv t2 = tcg_temp_new();
2636             TCGLabel *l1 = gen_new_label();
2637 
2638             gen_load_gpr(t1, rs);
2639             gen_load_gpr(t2, rt);
2640             tcg_gen_add_tl(t0, t1, t2);
2641             tcg_gen_xor_tl(t1, t1, t2);
2642             tcg_gen_xor_tl(t2, t0, t2);
2643             tcg_gen_andc_tl(t1, t2, t1);
2644             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
2645             /* operands of same sign, result different sign */
2646             generate_exception(ctx, EXCP_OVERFLOW);
2647             gen_set_label(l1);
2648             gen_store_gpr(t0, rd);
2649         }
2650         break;
2651     case OPC_DADDU:
2652         if (rs != 0 && rt != 0) {
2653             tcg_gen_add_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
2654         } else if (rs == 0 && rt != 0) {
2655             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
2656         } else if (rs != 0 && rt == 0) {
2657             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
2658         } else {
2659             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2660         }
2661         break;
2662     case OPC_DSUB:
2663         {
2664             TCGv t0 = tcg_temp_new();
2665             TCGv t1 = tcg_temp_new();
2666             TCGv t2 = tcg_temp_new();
2667             TCGLabel *l1 = gen_new_label();
2668 
2669             gen_load_gpr(t1, rs);
2670             gen_load_gpr(t2, rt);
2671             tcg_gen_sub_tl(t0, t1, t2);
2672             tcg_gen_xor_tl(t2, t1, t2);
2673             tcg_gen_xor_tl(t1, t0, t1);
2674             tcg_gen_and_tl(t1, t1, t2);
2675             tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
2676             /*
2677              * Operands of different sign, first operand and result different
2678              * sign.
2679              */
2680             generate_exception(ctx, EXCP_OVERFLOW);
2681             gen_set_label(l1);
2682             gen_store_gpr(t0, rd);
2683         }
2684         break;
2685     case OPC_DSUBU:
2686         if (rs != 0 && rt != 0) {
2687             tcg_gen_sub_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
2688         } else if (rs == 0 && rt != 0) {
2689             tcg_gen_neg_tl(cpu_gpr[rd], cpu_gpr[rt]);
2690         } else if (rs != 0 && rt == 0) {
2691             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
2692         } else {
2693             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2694         }
2695         break;
2696 #endif
2697     case OPC_MUL:
2698         if (likely(rs != 0 && rt != 0)) {
2699             tcg_gen_mul_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
2700             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
2701         } else {
2702             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2703         }
2704         break;
2705     }
2706 }
2707 
2708 /* Conditional move */
2709 static void gen_cond_move(DisasContext *ctx, uint32_t opc,
2710                           int rd, int rs, int rt)
2711 {
2712     TCGv t0, t1, t2;
2713 
2714     if (rd == 0) {
2715         /* If no destination, treat it as a NOP. */
2716         return;
2717     }
2718 
2719     t0 = tcg_temp_new();
2720     gen_load_gpr(t0, rt);
2721     t1 = tcg_constant_tl(0);
2722     t2 = tcg_temp_new();
2723     gen_load_gpr(t2, rs);
2724     switch (opc) {
2725     case OPC_MOVN:
2726         tcg_gen_movcond_tl(TCG_COND_NE, cpu_gpr[rd], t0, t1, t2, cpu_gpr[rd]);
2727         break;
2728     case OPC_MOVZ:
2729         tcg_gen_movcond_tl(TCG_COND_EQ, cpu_gpr[rd], t0, t1, t2, cpu_gpr[rd]);
2730         break;
2731     case OPC_SELNEZ:
2732         tcg_gen_movcond_tl(TCG_COND_NE, cpu_gpr[rd], t0, t1, t2, t1);
2733         break;
2734     case OPC_SELEQZ:
2735         tcg_gen_movcond_tl(TCG_COND_EQ, cpu_gpr[rd], t0, t1, t2, t1);
2736         break;
2737     }
2738 }
2739 
2740 /* Logic */
2741 static void gen_logic(DisasContext *ctx, uint32_t opc,
2742                       int rd, int rs, int rt)
2743 {
2744     if (rd == 0) {
2745         /* If no destination, treat it as a NOP. */
2746         return;
2747     }
2748 
2749     switch (opc) {
2750     case OPC_AND:
2751         if (likely(rs != 0 && rt != 0)) {
2752             tcg_gen_and_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
2753         } else {
2754             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2755         }
2756         break;
2757     case OPC_NOR:
2758         if (rs != 0 && rt != 0) {
2759             tcg_gen_nor_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
2760         } else if (rs == 0 && rt != 0) {
2761             tcg_gen_not_tl(cpu_gpr[rd], cpu_gpr[rt]);
2762         } else if (rs != 0 && rt == 0) {
2763             tcg_gen_not_tl(cpu_gpr[rd], cpu_gpr[rs]);
2764         } else {
2765             tcg_gen_movi_tl(cpu_gpr[rd], ~((target_ulong)0));
2766         }
2767         break;
2768     case OPC_OR:
2769         if (likely(rs != 0 && rt != 0)) {
2770             tcg_gen_or_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
2771         } else if (rs == 0 && rt != 0) {
2772             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
2773         } else if (rs != 0 && rt == 0) {
2774             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
2775         } else {
2776             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2777         }
2778         break;
2779     case OPC_XOR:
2780         if (likely(rs != 0 && rt != 0)) {
2781             tcg_gen_xor_tl(cpu_gpr[rd], cpu_gpr[rs], cpu_gpr[rt]);
2782         } else if (rs == 0 && rt != 0) {
2783             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rt]);
2784         } else if (rs != 0 && rt == 0) {
2785             tcg_gen_mov_tl(cpu_gpr[rd], cpu_gpr[rs]);
2786         } else {
2787             tcg_gen_movi_tl(cpu_gpr[rd], 0);
2788         }
2789         break;
2790     }
2791 }
2792 
2793 /* Set on lower than */
2794 static void gen_slt(DisasContext *ctx, uint32_t opc,
2795                     int rd, int rs, int rt)
2796 {
2797     TCGv t0, t1;
2798 
2799     if (rd == 0) {
2800         /* If no destination, treat it as a NOP. */
2801         return;
2802     }
2803 
2804     t0 = tcg_temp_new();
2805     t1 = tcg_temp_new();
2806     gen_load_gpr(t0, rs);
2807     gen_load_gpr(t1, rt);
2808     switch (opc) {
2809     case OPC_SLT:
2810         tcg_gen_setcond_tl(TCG_COND_LT, cpu_gpr[rd], t0, t1);
2811         break;
2812     case OPC_SLTU:
2813         tcg_gen_setcond_tl(TCG_COND_LTU, cpu_gpr[rd], t0, t1);
2814         break;
2815     }
2816 }
2817 
2818 /* Shifts */
2819 static void gen_shift(DisasContext *ctx, uint32_t opc,
2820                       int rd, int rs, int rt)
2821 {
2822     TCGv t0, t1;
2823 
2824     if (rd == 0) {
2825         /*
2826          * If no destination, treat it as a NOP.
2827          * For add & sub, we must generate the overflow exception when needed.
2828          */
2829         return;
2830     }
2831 
2832     t0 = tcg_temp_new();
2833     t1 = tcg_temp_new();
2834     gen_load_gpr(t0, rs);
2835     gen_load_gpr(t1, rt);
2836     switch (opc) {
2837     case OPC_SLLV:
2838         tcg_gen_andi_tl(t0, t0, 0x1f);
2839         tcg_gen_shl_tl(t0, t1, t0);
2840         tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
2841         break;
2842     case OPC_SRAV:
2843         tcg_gen_andi_tl(t0, t0, 0x1f);
2844         tcg_gen_sar_tl(cpu_gpr[rd], t1, t0);
2845         break;
2846     case OPC_SRLV:
2847         tcg_gen_ext32u_tl(t1, t1);
2848         tcg_gen_andi_tl(t0, t0, 0x1f);
2849         tcg_gen_shr_tl(t0, t1, t0);
2850         tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
2851         break;
2852     case OPC_ROTRV:
2853         {
2854             TCGv_i32 t2 = tcg_temp_new_i32();
2855             TCGv_i32 t3 = tcg_temp_new_i32();
2856 
2857             tcg_gen_trunc_tl_i32(t2, t0);
2858             tcg_gen_trunc_tl_i32(t3, t1);
2859             tcg_gen_andi_i32(t2, t2, 0x1f);
2860             tcg_gen_rotr_i32(t2, t3, t2);
2861             tcg_gen_ext_i32_tl(cpu_gpr[rd], t2);
2862         }
2863         break;
2864 #if defined(TARGET_MIPS64)
2865     case OPC_DSLLV:
2866         tcg_gen_andi_tl(t0, t0, 0x3f);
2867         tcg_gen_shl_tl(cpu_gpr[rd], t1, t0);
2868         break;
2869     case OPC_DSRAV:
2870         tcg_gen_andi_tl(t0, t0, 0x3f);
2871         tcg_gen_sar_tl(cpu_gpr[rd], t1, t0);
2872         break;
2873     case OPC_DSRLV:
2874         tcg_gen_andi_tl(t0, t0, 0x3f);
2875         tcg_gen_shr_tl(cpu_gpr[rd], t1, t0);
2876         break;
2877     case OPC_DROTRV:
2878         tcg_gen_andi_tl(t0, t0, 0x3f);
2879         tcg_gen_rotr_tl(cpu_gpr[rd], t1, t0);
2880         break;
2881 #endif
2882     }
2883 }
2884 
2885 /* Arithmetic on HI/LO registers */
2886 static void gen_HILO(DisasContext *ctx, uint32_t opc, int acc, int reg)
2887 {
2888     if (reg == 0 && (opc == OPC_MFHI || opc == OPC_MFLO)) {
2889         /* Treat as NOP. */
2890         return;
2891     }
2892 
2893     if (acc != 0) {
2894         check_dsp(ctx);
2895     }
2896 
2897     switch (opc) {
2898     case OPC_MFHI:
2899 #if defined(TARGET_MIPS64)
2900         if (acc != 0) {
2901             tcg_gen_ext32s_tl(cpu_gpr[reg], cpu_HI[acc]);
2902         } else
2903 #endif
2904         {
2905             tcg_gen_mov_tl(cpu_gpr[reg], cpu_HI[acc]);
2906         }
2907         break;
2908     case OPC_MFLO:
2909 #if defined(TARGET_MIPS64)
2910         if (acc != 0) {
2911             tcg_gen_ext32s_tl(cpu_gpr[reg], cpu_LO[acc]);
2912         } else
2913 #endif
2914         {
2915             tcg_gen_mov_tl(cpu_gpr[reg], cpu_LO[acc]);
2916         }
2917         break;
2918     case OPC_MTHI:
2919         if (reg != 0) {
2920 #if defined(TARGET_MIPS64)
2921             if (acc != 0) {
2922                 tcg_gen_ext32s_tl(cpu_HI[acc], cpu_gpr[reg]);
2923             } else
2924 #endif
2925             {
2926                 tcg_gen_mov_tl(cpu_HI[acc], cpu_gpr[reg]);
2927             }
2928         } else {
2929             tcg_gen_movi_tl(cpu_HI[acc], 0);
2930         }
2931         break;
2932     case OPC_MTLO:
2933         if (reg != 0) {
2934 #if defined(TARGET_MIPS64)
2935             if (acc != 0) {
2936                 tcg_gen_ext32s_tl(cpu_LO[acc], cpu_gpr[reg]);
2937             } else
2938 #endif
2939             {
2940                 tcg_gen_mov_tl(cpu_LO[acc], cpu_gpr[reg]);
2941             }
2942         } else {
2943             tcg_gen_movi_tl(cpu_LO[acc], 0);
2944         }
2945         break;
2946     }
2947 }
2948 
2949 static inline void gen_r6_ld(target_long addr, int reg, int memidx,
2950                              MemOp memop)
2951 {
2952     TCGv t0 = tcg_temp_new();
2953     tcg_gen_qemu_ld_tl(t0, tcg_constant_tl(addr), memidx, memop);
2954     gen_store_gpr(t0, reg);
2955 }
2956 
2957 static inline void gen_pcrel(DisasContext *ctx, int opc, target_ulong pc,
2958                              int rs)
2959 {
2960     target_long offset;
2961     target_long addr;
2962 
2963     switch (MASK_OPC_PCREL_TOP2BITS(opc)) {
2964     case OPC_ADDIUPC:
2965         if (rs != 0) {
2966             offset = sextract32(ctx->opcode << 2, 0, 21);
2967             addr = addr_add(ctx, pc, offset);
2968             tcg_gen_movi_tl(cpu_gpr[rs], addr);
2969         }
2970         break;
2971     case R6_OPC_LWPC:
2972         offset = sextract32(ctx->opcode << 2, 0, 21);
2973         addr = addr_add(ctx, pc, offset);
2974         gen_r6_ld(addr, rs, ctx->mem_idx, mo_endian(ctx) | MO_SL);
2975         break;
2976 #if defined(TARGET_MIPS64)
2977     case OPC_LWUPC:
2978         check_mips_64(ctx);
2979         offset = sextract32(ctx->opcode << 2, 0, 21);
2980         addr = addr_add(ctx, pc, offset);
2981         gen_r6_ld(addr, rs, ctx->mem_idx, mo_endian(ctx) | MO_UL);
2982         break;
2983 #endif
2984     default:
2985         switch (MASK_OPC_PCREL_TOP5BITS(opc)) {
2986         case OPC_AUIPC:
2987             if (rs != 0) {
2988                 offset = sextract32(ctx->opcode, 0, 16) << 16;
2989                 addr = addr_add(ctx, pc, offset);
2990                 tcg_gen_movi_tl(cpu_gpr[rs], addr);
2991             }
2992             break;
2993         case OPC_ALUIPC:
2994             if (rs != 0) {
2995                 offset = sextract32(ctx->opcode, 0, 16) << 16;
2996                 addr = ~0xFFFF & addr_add(ctx, pc, offset);
2997                 tcg_gen_movi_tl(cpu_gpr[rs], addr);
2998             }
2999             break;
3000 #if defined(TARGET_MIPS64)
3001         case R6_OPC_LDPC: /* bits 16 and 17 are part of immediate */
3002         case R6_OPC_LDPC + (1 << 16):
3003         case R6_OPC_LDPC + (2 << 16):
3004         case R6_OPC_LDPC + (3 << 16):
3005             check_mips_64(ctx);
3006             offset = sextract32(ctx->opcode << 3, 0, 21);
3007             addr = addr_add(ctx, (pc & ~0x7), offset);
3008             gen_r6_ld(addr, rs, ctx->mem_idx, mo_endian(ctx) | MO_UQ);
3009             break;
3010 #endif
3011         default:
3012             MIPS_INVAL("OPC_PCREL");
3013             gen_reserved_instruction(ctx);
3014             break;
3015         }
3016         break;
3017     }
3018 }
3019 
3020 static void gen_r6_muldiv(DisasContext *ctx, int opc, int rd, int rs, int rt)
3021 {
3022     TCGv t0, t1;
3023 
3024     if (rd == 0) {
3025         /* Treat as NOP. */
3026         return;
3027     }
3028 
3029     t0 = tcg_temp_new();
3030     t1 = tcg_temp_new();
3031 
3032     gen_load_gpr(t0, rs);
3033     gen_load_gpr(t1, rt);
3034 
3035     switch (opc) {
3036     case R6_OPC_DIV:
3037         {
3038             TCGv t2 = tcg_temp_new();
3039             TCGv t3 = tcg_temp_new();
3040             tcg_gen_ext32s_tl(t0, t0);
3041             tcg_gen_ext32s_tl(t1, t1);
3042             tcg_gen_setcondi_tl(TCG_COND_EQ, t2, t0, INT_MIN);
3043             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, -1);
3044             tcg_gen_and_tl(t2, t2, t3);
3045             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, 0);
3046             tcg_gen_or_tl(t2, t2, t3);
3047             tcg_gen_movcond_tl(TCG_COND_NE, t1, t2, tcg_constant_tl(0), t2, t1);
3048             tcg_gen_div_tl(cpu_gpr[rd], t0, t1);
3049             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
3050         }
3051         break;
3052     case R6_OPC_MOD:
3053         {
3054             TCGv t2 = tcg_temp_new();
3055             TCGv t3 = tcg_temp_new();
3056             tcg_gen_ext32s_tl(t0, t0);
3057             tcg_gen_ext32s_tl(t1, t1);
3058             tcg_gen_setcondi_tl(TCG_COND_EQ, t2, t0, INT_MIN);
3059             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, -1);
3060             tcg_gen_and_tl(t2, t2, t3);
3061             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, 0);
3062             tcg_gen_or_tl(t2, t2, t3);
3063             tcg_gen_movcond_tl(TCG_COND_NE, t1, t2, tcg_constant_tl(0), t2, t1);
3064             tcg_gen_rem_tl(cpu_gpr[rd], t0, t1);
3065             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
3066         }
3067         break;
3068     case R6_OPC_DIVU:
3069         {
3070             tcg_gen_ext32u_tl(t0, t0);
3071             tcg_gen_ext32u_tl(t1, t1);
3072             tcg_gen_movcond_tl(TCG_COND_EQ, t1, t1,
3073                                tcg_constant_tl(0), tcg_constant_tl(1), t1);
3074             tcg_gen_divu_tl(cpu_gpr[rd], t0, t1);
3075             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
3076         }
3077         break;
3078     case R6_OPC_MODU:
3079         {
3080             tcg_gen_ext32u_tl(t0, t0);
3081             tcg_gen_ext32u_tl(t1, t1);
3082             tcg_gen_movcond_tl(TCG_COND_EQ, t1, t1,
3083                                tcg_constant_tl(0), tcg_constant_tl(1), t1);
3084             tcg_gen_remu_tl(cpu_gpr[rd], t0, t1);
3085             tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
3086         }
3087         break;
3088     case R6_OPC_MUL:
3089         {
3090             TCGv_i32 t2 = tcg_temp_new_i32();
3091             TCGv_i32 t3 = tcg_temp_new_i32();
3092             tcg_gen_trunc_tl_i32(t2, t0);
3093             tcg_gen_trunc_tl_i32(t3, t1);
3094             tcg_gen_mul_i32(t2, t2, t3);
3095             tcg_gen_ext_i32_tl(cpu_gpr[rd], t2);
3096         }
3097         break;
3098     case R6_OPC_MUH:
3099         {
3100             TCGv_i32 t2 = tcg_temp_new_i32();
3101             TCGv_i32 t3 = tcg_temp_new_i32();
3102             tcg_gen_trunc_tl_i32(t2, t0);
3103             tcg_gen_trunc_tl_i32(t3, t1);
3104             tcg_gen_muls2_i32(t2, t3, t2, t3);
3105             tcg_gen_ext_i32_tl(cpu_gpr[rd], t3);
3106         }
3107         break;
3108     case R6_OPC_MULU:
3109         {
3110             TCGv_i32 t2 = tcg_temp_new_i32();
3111             TCGv_i32 t3 = tcg_temp_new_i32();
3112             tcg_gen_trunc_tl_i32(t2, t0);
3113             tcg_gen_trunc_tl_i32(t3, t1);
3114             tcg_gen_mul_i32(t2, t2, t3);
3115             tcg_gen_ext_i32_tl(cpu_gpr[rd], t2);
3116         }
3117         break;
3118     case R6_OPC_MUHU:
3119         {
3120             TCGv_i32 t2 = tcg_temp_new_i32();
3121             TCGv_i32 t3 = tcg_temp_new_i32();
3122             tcg_gen_trunc_tl_i32(t2, t0);
3123             tcg_gen_trunc_tl_i32(t3, t1);
3124             tcg_gen_mulu2_i32(t2, t3, t2, t3);
3125             tcg_gen_ext_i32_tl(cpu_gpr[rd], t3);
3126         }
3127         break;
3128 #if defined(TARGET_MIPS64)
3129     case R6_OPC_DDIV:
3130         {
3131             TCGv t2 = tcg_temp_new();
3132             TCGv t3 = tcg_temp_new();
3133             tcg_gen_setcondi_tl(TCG_COND_EQ, t2, t0, -1LL << 63);
3134             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, -1LL);
3135             tcg_gen_and_tl(t2, t2, t3);
3136             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, 0);
3137             tcg_gen_or_tl(t2, t2, t3);
3138             tcg_gen_movcond_tl(TCG_COND_NE, t1, t2, tcg_constant_tl(0), t2, t1);
3139             tcg_gen_div_tl(cpu_gpr[rd], t0, t1);
3140         }
3141         break;
3142     case R6_OPC_DMOD:
3143         {
3144             TCGv t2 = tcg_temp_new();
3145             TCGv t3 = tcg_temp_new();
3146             tcg_gen_setcondi_tl(TCG_COND_EQ, t2, t0, -1LL << 63);
3147             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, -1LL);
3148             tcg_gen_and_tl(t2, t2, t3);
3149             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, 0);
3150             tcg_gen_or_tl(t2, t2, t3);
3151             tcg_gen_movcond_tl(TCG_COND_NE, t1, t2, tcg_constant_tl(0), t2, t1);
3152             tcg_gen_rem_tl(cpu_gpr[rd], t0, t1);
3153         }
3154         break;
3155     case R6_OPC_DDIVU:
3156         {
3157             tcg_gen_movcond_tl(TCG_COND_EQ, t1, t1,
3158                                tcg_constant_tl(0), tcg_constant_tl(1), t1);
3159             tcg_gen_divu_i64(cpu_gpr[rd], t0, t1);
3160         }
3161         break;
3162     case R6_OPC_DMODU:
3163         {
3164             tcg_gen_movcond_tl(TCG_COND_EQ, t1, t1,
3165                                tcg_constant_tl(0), tcg_constant_tl(1), t1);
3166             tcg_gen_remu_i64(cpu_gpr[rd], t0, t1);
3167         }
3168         break;
3169     case R6_OPC_DMUL:
3170         tcg_gen_mul_i64(cpu_gpr[rd], t0, t1);
3171         break;
3172     case R6_OPC_DMUH:
3173         {
3174             TCGv t2 = tcg_temp_new();
3175             tcg_gen_muls2_i64(t2, cpu_gpr[rd], t0, t1);
3176         }
3177         break;
3178     case R6_OPC_DMULU:
3179         tcg_gen_mul_i64(cpu_gpr[rd], t0, t1);
3180         break;
3181     case R6_OPC_DMUHU:
3182         {
3183             TCGv t2 = tcg_temp_new();
3184             tcg_gen_mulu2_i64(t2, cpu_gpr[rd], t0, t1);
3185         }
3186         break;
3187 #endif
3188     default:
3189         MIPS_INVAL("r6 mul/div");
3190         gen_reserved_instruction(ctx);
3191         break;
3192     }
3193 }
3194 
3195 #if defined(TARGET_MIPS64)
3196 static void gen_div1_tx79(DisasContext *ctx, uint32_t opc, int rs, int rt)
3197 {
3198     TCGv t0, t1;
3199 
3200     t0 = tcg_temp_new();
3201     t1 = tcg_temp_new();
3202 
3203     gen_load_gpr(t0, rs);
3204     gen_load_gpr(t1, rt);
3205 
3206     switch (opc) {
3207     case MMI_OPC_DIV1:
3208         {
3209             TCGv t2 = tcg_temp_new();
3210             TCGv t3 = tcg_temp_new();
3211             tcg_gen_ext32s_tl(t0, t0);
3212             tcg_gen_ext32s_tl(t1, t1);
3213             tcg_gen_setcondi_tl(TCG_COND_EQ, t2, t0, INT_MIN);
3214             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, -1);
3215             tcg_gen_and_tl(t2, t2, t3);
3216             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, 0);
3217             tcg_gen_or_tl(t2, t2, t3);
3218             tcg_gen_movcond_tl(TCG_COND_NE, t1, t2, tcg_constant_tl(0), t2, t1);
3219             tcg_gen_div_tl(cpu_LO[1], t0, t1);
3220             tcg_gen_rem_tl(cpu_HI[1], t0, t1);
3221             tcg_gen_ext32s_tl(cpu_LO[1], cpu_LO[1]);
3222             tcg_gen_ext32s_tl(cpu_HI[1], cpu_HI[1]);
3223         }
3224         break;
3225     case MMI_OPC_DIVU1:
3226         {
3227             TCGv t2 = tcg_constant_tl(0);
3228             TCGv t3 = tcg_constant_tl(1);
3229             tcg_gen_ext32u_tl(t0, t0);
3230             tcg_gen_ext32u_tl(t1, t1);
3231             tcg_gen_movcond_tl(TCG_COND_EQ, t1, t1, t2, t3, t1);
3232             tcg_gen_divu_tl(cpu_LO[1], t0, t1);
3233             tcg_gen_remu_tl(cpu_HI[1], t0, t1);
3234             tcg_gen_ext32s_tl(cpu_LO[1], cpu_LO[1]);
3235             tcg_gen_ext32s_tl(cpu_HI[1], cpu_HI[1]);
3236         }
3237         break;
3238     default:
3239         MIPS_INVAL("div1 TX79");
3240         gen_reserved_instruction(ctx);
3241         break;
3242     }
3243 }
3244 #endif
3245 
3246 static void gen_muldiv(DisasContext *ctx, uint32_t opc,
3247                        int acc, int rs, int rt)
3248 {
3249     TCGv t0, t1;
3250 
3251     t0 = tcg_temp_new();
3252     t1 = tcg_temp_new();
3253 
3254     gen_load_gpr(t0, rs);
3255     gen_load_gpr(t1, rt);
3256 
3257     if (acc != 0) {
3258         check_dsp(ctx);
3259     }
3260 
3261     switch (opc) {
3262     case OPC_DIV:
3263         {
3264             TCGv t2 = tcg_temp_new();
3265             TCGv t3 = tcg_temp_new();
3266             tcg_gen_ext32s_tl(t0, t0);
3267             tcg_gen_ext32s_tl(t1, t1);
3268             tcg_gen_setcondi_tl(TCG_COND_EQ, t2, t0, INT_MIN);
3269             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, -1);
3270             tcg_gen_and_tl(t2, t2, t3);
3271             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, 0);
3272             tcg_gen_or_tl(t2, t2, t3);
3273             tcg_gen_movcond_tl(TCG_COND_NE, t1, t2, tcg_constant_tl(0), t2, t1);
3274             tcg_gen_div_tl(cpu_LO[acc], t0, t1);
3275             tcg_gen_rem_tl(cpu_HI[acc], t0, t1);
3276             tcg_gen_ext32s_tl(cpu_LO[acc], cpu_LO[acc]);
3277             tcg_gen_ext32s_tl(cpu_HI[acc], cpu_HI[acc]);
3278         }
3279         break;
3280     case OPC_DIVU:
3281         {
3282             TCGv t2 = tcg_constant_tl(0);
3283             TCGv t3 = tcg_constant_tl(1);
3284             tcg_gen_ext32u_tl(t0, t0);
3285             tcg_gen_ext32u_tl(t1, t1);
3286             tcg_gen_movcond_tl(TCG_COND_EQ, t1, t1, t2, t3, t1);
3287             tcg_gen_divu_tl(cpu_LO[acc], t0, t1);
3288             tcg_gen_remu_tl(cpu_HI[acc], t0, t1);
3289             tcg_gen_ext32s_tl(cpu_LO[acc], cpu_LO[acc]);
3290             tcg_gen_ext32s_tl(cpu_HI[acc], cpu_HI[acc]);
3291         }
3292         break;
3293     case OPC_MULT:
3294         {
3295             TCGv_i32 t2 = tcg_temp_new_i32();
3296             TCGv_i32 t3 = tcg_temp_new_i32();
3297             tcg_gen_trunc_tl_i32(t2, t0);
3298             tcg_gen_trunc_tl_i32(t3, t1);
3299             tcg_gen_muls2_i32(t2, t3, t2, t3);
3300             tcg_gen_ext_i32_tl(cpu_LO[acc], t2);
3301             tcg_gen_ext_i32_tl(cpu_HI[acc], t3);
3302         }
3303         break;
3304     case OPC_MULTU:
3305         {
3306             TCGv_i32 t2 = tcg_temp_new_i32();
3307             TCGv_i32 t3 = tcg_temp_new_i32();
3308             tcg_gen_trunc_tl_i32(t2, t0);
3309             tcg_gen_trunc_tl_i32(t3, t1);
3310             tcg_gen_mulu2_i32(t2, t3, t2, t3);
3311             tcg_gen_ext_i32_tl(cpu_LO[acc], t2);
3312             tcg_gen_ext_i32_tl(cpu_HI[acc], t3);
3313         }
3314         break;
3315 #if defined(TARGET_MIPS64)
3316     case OPC_DDIV:
3317         {
3318             TCGv t2 = tcg_temp_new();
3319             TCGv t3 = tcg_temp_new();
3320             tcg_gen_setcondi_tl(TCG_COND_EQ, t2, t0, -1LL << 63);
3321             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, -1LL);
3322             tcg_gen_and_tl(t2, t2, t3);
3323             tcg_gen_setcondi_tl(TCG_COND_EQ, t3, t1, 0);
3324             tcg_gen_or_tl(t2, t2, t3);
3325             tcg_gen_movcond_tl(TCG_COND_NE, t1, t2, tcg_constant_tl(0), t2, t1);
3326             tcg_gen_div_tl(cpu_LO[acc], t0, t1);
3327             tcg_gen_rem_tl(cpu_HI[acc], t0, t1);
3328         }
3329         break;
3330     case OPC_DDIVU:
3331         {
3332             tcg_gen_movcond_tl(TCG_COND_EQ, t1, t1,
3333                                tcg_constant_tl(0), tcg_constant_tl(1), t1);
3334             tcg_gen_divu_i64(cpu_LO[acc], t0, t1);
3335             tcg_gen_remu_i64(cpu_HI[acc], t0, t1);
3336         }
3337         break;
3338     case OPC_DMULT:
3339         tcg_gen_muls2_i64(cpu_LO[acc], cpu_HI[acc], t0, t1);
3340         break;
3341     case OPC_DMULTU:
3342         tcg_gen_mulu2_i64(cpu_LO[acc], cpu_HI[acc], t0, t1);
3343         break;
3344 #endif
3345     case OPC_MADD:
3346         {
3347             TCGv_i64 t2 = tcg_temp_new_i64();
3348             TCGv_i64 t3 = tcg_temp_new_i64();
3349 
3350             tcg_gen_ext_tl_i64(t2, t0);
3351             tcg_gen_ext_tl_i64(t3, t1);
3352             tcg_gen_mul_i64(t2, t2, t3);
3353             tcg_gen_concat_tl_i64(t3, cpu_LO[acc], cpu_HI[acc]);
3354             tcg_gen_add_i64(t2, t2, t3);
3355             gen_move_low32(cpu_LO[acc], t2);
3356             gen_move_high32(cpu_HI[acc], t2);
3357         }
3358         break;
3359     case OPC_MADDU:
3360         {
3361             TCGv_i64 t2 = tcg_temp_new_i64();
3362             TCGv_i64 t3 = tcg_temp_new_i64();
3363 
3364             tcg_gen_ext32u_tl(t0, t0);
3365             tcg_gen_ext32u_tl(t1, t1);
3366             tcg_gen_extu_tl_i64(t2, t0);
3367             tcg_gen_extu_tl_i64(t3, t1);
3368             tcg_gen_mul_i64(t2, t2, t3);
3369             tcg_gen_concat_tl_i64(t3, cpu_LO[acc], cpu_HI[acc]);
3370             tcg_gen_add_i64(t2, t2, t3);
3371             gen_move_low32(cpu_LO[acc], t2);
3372             gen_move_high32(cpu_HI[acc], t2);
3373         }
3374         break;
3375     case OPC_MSUB:
3376         {
3377             TCGv_i64 t2 = tcg_temp_new_i64();
3378             TCGv_i64 t3 = tcg_temp_new_i64();
3379 
3380             tcg_gen_ext_tl_i64(t2, t0);
3381             tcg_gen_ext_tl_i64(t3, t1);
3382             tcg_gen_mul_i64(t2, t2, t3);
3383             tcg_gen_concat_tl_i64(t3, cpu_LO[acc], cpu_HI[acc]);
3384             tcg_gen_sub_i64(t2, t3, t2);
3385             gen_move_low32(cpu_LO[acc], t2);
3386             gen_move_high32(cpu_HI[acc], t2);
3387         }
3388         break;
3389     case OPC_MSUBU:
3390         {
3391             TCGv_i64 t2 = tcg_temp_new_i64();
3392             TCGv_i64 t3 = tcg_temp_new_i64();
3393 
3394             tcg_gen_ext32u_tl(t0, t0);
3395             tcg_gen_ext32u_tl(t1, t1);
3396             tcg_gen_extu_tl_i64(t2, t0);
3397             tcg_gen_extu_tl_i64(t3, t1);
3398             tcg_gen_mul_i64(t2, t2, t3);
3399             tcg_gen_concat_tl_i64(t3, cpu_LO[acc], cpu_HI[acc]);
3400             tcg_gen_sub_i64(t2, t3, t2);
3401             gen_move_low32(cpu_LO[acc], t2);
3402             gen_move_high32(cpu_HI[acc], t2);
3403         }
3404         break;
3405     default:
3406         MIPS_INVAL("mul/div");
3407         gen_reserved_instruction(ctx);
3408         break;
3409     }
3410 }
3411 
3412 /*
3413  * These MULT[U] and MADD[U] instructions implemented in for example
3414  * the Toshiba/Sony R5900 and the Toshiba TX19, TX39 and TX79 core
3415  * architectures are special three-operand variants with the syntax
3416  *
3417  *     MULT[U][1] rd, rs, rt
3418  *
3419  * such that
3420  *
3421  *     (rd, LO, HI) <- rs * rt
3422  *
3423  * and
3424  *
3425  *     MADD[U][1] rd, rs, rt
3426  *
3427  * such that
3428  *
3429  *     (rd, LO, HI) <- (LO, HI) + rs * rt
3430  *
3431  * where the low-order 32-bits of the result is placed into both the
3432  * GPR rd and the special register LO. The high-order 32-bits of the
3433  * result is placed into the special register HI.
3434  *
3435  * If the GPR rd is omitted in assembly language, it is taken to be 0,
3436  * which is the zero register that always reads as 0.
3437  */
3438 static void gen_mul_txx9(DisasContext *ctx, uint32_t opc,
3439                          int rd, int rs, int rt)
3440 {
3441     TCGv t0 = tcg_temp_new();
3442     TCGv t1 = tcg_temp_new();
3443     int acc = 0;
3444 
3445     gen_load_gpr(t0, rs);
3446     gen_load_gpr(t1, rt);
3447 
3448     switch (opc) {
3449     case MMI_OPC_MULT1:
3450         acc = 1;
3451         /* Fall through */
3452     case OPC_MULT:
3453         {
3454             TCGv_i32 t2 = tcg_temp_new_i32();
3455             TCGv_i32 t3 = tcg_temp_new_i32();
3456             tcg_gen_trunc_tl_i32(t2, t0);
3457             tcg_gen_trunc_tl_i32(t3, t1);
3458             tcg_gen_muls2_i32(t2, t3, t2, t3);
3459             if (rd) {
3460                 tcg_gen_ext_i32_tl(cpu_gpr[rd], t2);
3461             }
3462             tcg_gen_ext_i32_tl(cpu_LO[acc], t2);
3463             tcg_gen_ext_i32_tl(cpu_HI[acc], t3);
3464         }
3465         break;
3466     case MMI_OPC_MULTU1:
3467         acc = 1;
3468         /* Fall through */
3469     case OPC_MULTU:
3470         {
3471             TCGv_i32 t2 = tcg_temp_new_i32();
3472             TCGv_i32 t3 = tcg_temp_new_i32();
3473             tcg_gen_trunc_tl_i32(t2, t0);
3474             tcg_gen_trunc_tl_i32(t3, t1);
3475             tcg_gen_mulu2_i32(t2, t3, t2, t3);
3476             if (rd) {
3477                 tcg_gen_ext_i32_tl(cpu_gpr[rd], t2);
3478             }
3479             tcg_gen_ext_i32_tl(cpu_LO[acc], t2);
3480             tcg_gen_ext_i32_tl(cpu_HI[acc], t3);
3481         }
3482         break;
3483     case MMI_OPC_MADD1:
3484         acc = 1;
3485         /* Fall through */
3486     case MMI_OPC_MADD:
3487         {
3488             TCGv_i64 t2 = tcg_temp_new_i64();
3489             TCGv_i64 t3 = tcg_temp_new_i64();
3490 
3491             tcg_gen_ext_tl_i64(t2, t0);
3492             tcg_gen_ext_tl_i64(t3, t1);
3493             tcg_gen_mul_i64(t2, t2, t3);
3494             tcg_gen_concat_tl_i64(t3, cpu_LO[acc], cpu_HI[acc]);
3495             tcg_gen_add_i64(t2, t2, t3);
3496             gen_move_low32(cpu_LO[acc], t2);
3497             gen_move_high32(cpu_HI[acc], t2);
3498             if (rd) {
3499                 gen_move_low32(cpu_gpr[rd], t2);
3500             }
3501         }
3502         break;
3503     case MMI_OPC_MADDU1:
3504         acc = 1;
3505         /* Fall through */
3506     case MMI_OPC_MADDU:
3507         {
3508             TCGv_i64 t2 = tcg_temp_new_i64();
3509             TCGv_i64 t3 = tcg_temp_new_i64();
3510 
3511             tcg_gen_ext32u_tl(t0, t0);
3512             tcg_gen_ext32u_tl(t1, t1);
3513             tcg_gen_extu_tl_i64(t2, t0);
3514             tcg_gen_extu_tl_i64(t3, t1);
3515             tcg_gen_mul_i64(t2, t2, t3);
3516             tcg_gen_concat_tl_i64(t3, cpu_LO[acc], cpu_HI[acc]);
3517             tcg_gen_add_i64(t2, t2, t3);
3518             gen_move_low32(cpu_LO[acc], t2);
3519             gen_move_high32(cpu_HI[acc], t2);
3520             if (rd) {
3521                 gen_move_low32(cpu_gpr[rd], t2);
3522             }
3523         }
3524         break;
3525     default:
3526         MIPS_INVAL("mul/madd TXx9");
3527         gen_reserved_instruction(ctx);
3528         break;
3529     }
3530 }
3531 
3532 static void gen_cl(DisasContext *ctx, uint32_t opc,
3533                    int rd, int rs)
3534 {
3535     TCGv t0;
3536 
3537     if (rd == 0) {
3538         /* Treat as NOP. */
3539         return;
3540     }
3541     t0 = cpu_gpr[rd];
3542     gen_load_gpr(t0, rs);
3543 
3544     switch (opc) {
3545     case OPC_CLO:
3546     case R6_OPC_CLO:
3547 #if defined(TARGET_MIPS64)
3548     case OPC_DCLO:
3549     case R6_OPC_DCLO:
3550 #endif
3551         tcg_gen_not_tl(t0, t0);
3552         break;
3553     }
3554 
3555     switch (opc) {
3556     case OPC_CLO:
3557     case R6_OPC_CLO:
3558     case OPC_CLZ:
3559     case R6_OPC_CLZ:
3560         tcg_gen_ext32u_tl(t0, t0);
3561         tcg_gen_clzi_tl(t0, t0, TARGET_LONG_BITS);
3562         tcg_gen_subi_tl(t0, t0, TARGET_LONG_BITS - 32);
3563         break;
3564 #if defined(TARGET_MIPS64)
3565     case OPC_DCLO:
3566     case R6_OPC_DCLO:
3567     case OPC_DCLZ:
3568     case R6_OPC_DCLZ:
3569         tcg_gen_clzi_i64(t0, t0, 64);
3570         break;
3571 #endif
3572     }
3573 }
3574 
3575 /* Godson integer instructions */
3576 static void gen_loongson_integer(DisasContext *ctx, uint32_t opc,
3577                                  int rd, int rs, int rt)
3578 {
3579     TCGv t0, t1;
3580 
3581     if (rd == 0) {
3582         /* Treat as NOP. */
3583         return;
3584     }
3585 
3586     t0 = tcg_temp_new();
3587     t1 = tcg_temp_new();
3588     gen_load_gpr(t0, rs);
3589     gen_load_gpr(t1, rt);
3590 
3591     switch (opc) {
3592     case OPC_MULT_G_2E:
3593     case OPC_MULT_G_2F:
3594         tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
3595         tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
3596         break;
3597     case OPC_MULTU_G_2E:
3598     case OPC_MULTU_G_2F:
3599         tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
3600         tcg_gen_ext32s_tl(cpu_gpr[rd], cpu_gpr[rd]);
3601         break;
3602 #if defined(TARGET_MIPS64)
3603     case OPC_DMULT_G_2E:
3604     case OPC_DMULT_G_2F:
3605         tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
3606         break;
3607     case OPC_DMULTU_G_2E:
3608     case OPC_DMULTU_G_2F:
3609         tcg_gen_mul_tl(cpu_gpr[rd], t0, t1);
3610         break;
3611 #endif
3612     }
3613 }
3614 
3615 /* Loongson multimedia instructions */
3616 static void gen_loongson_multimedia(DisasContext *ctx, int rd, int rs, int rt)
3617 {
3618     uint32_t opc, shift_max;
3619     TCGv_i64 t0, t1;
3620     TCGCond cond;
3621 
3622     opc = MASK_LMMI(ctx->opcode);
3623     check_cp1_enabled(ctx);
3624 
3625     t0 = tcg_temp_new_i64();
3626     t1 = tcg_temp_new_i64();
3627     gen_load_fpr64(ctx, t0, rs);
3628     gen_load_fpr64(ctx, t1, rt);
3629 
3630     switch (opc) {
3631     case OPC_PADDSH:
3632         gen_helper_paddsh(t0, t0, t1);
3633         break;
3634     case OPC_PADDUSH:
3635         gen_helper_paddush(t0, t0, t1);
3636         break;
3637     case OPC_PADDH:
3638         gen_helper_paddh(t0, t0, t1);
3639         break;
3640     case OPC_PADDW:
3641         gen_helper_paddw(t0, t0, t1);
3642         break;
3643     case OPC_PADDSB:
3644         gen_helper_paddsb(t0, t0, t1);
3645         break;
3646     case OPC_PADDUSB:
3647         gen_helper_paddusb(t0, t0, t1);
3648         break;
3649     case OPC_PADDB:
3650         gen_helper_paddb(t0, t0, t1);
3651         break;
3652 
3653     case OPC_PSUBSH:
3654         gen_helper_psubsh(t0, t0, t1);
3655         break;
3656     case OPC_PSUBUSH:
3657         gen_helper_psubush(t0, t0, t1);
3658         break;
3659     case OPC_PSUBH:
3660         gen_helper_psubh(t0, t0, t1);
3661         break;
3662     case OPC_PSUBW:
3663         gen_helper_psubw(t0, t0, t1);
3664         break;
3665     case OPC_PSUBSB:
3666         gen_helper_psubsb(t0, t0, t1);
3667         break;
3668     case OPC_PSUBUSB:
3669         gen_helper_psubusb(t0, t0, t1);
3670         break;
3671     case OPC_PSUBB:
3672         gen_helper_psubb(t0, t0, t1);
3673         break;
3674 
3675     case OPC_PSHUFH:
3676         gen_helper_pshufh(t0, t0, t1);
3677         break;
3678     case OPC_PACKSSWH:
3679         gen_helper_packsswh(t0, t0, t1);
3680         break;
3681     case OPC_PACKSSHB:
3682         gen_helper_packsshb(t0, t0, t1);
3683         break;
3684     case OPC_PACKUSHB:
3685         gen_helper_packushb(t0, t0, t1);
3686         break;
3687 
3688     case OPC_PUNPCKLHW:
3689         gen_helper_punpcklhw(t0, t0, t1);
3690         break;
3691     case OPC_PUNPCKHHW:
3692         gen_helper_punpckhhw(t0, t0, t1);
3693         break;
3694     case OPC_PUNPCKLBH:
3695         gen_helper_punpcklbh(t0, t0, t1);
3696         break;
3697     case OPC_PUNPCKHBH:
3698         gen_helper_punpckhbh(t0, t0, t1);
3699         break;
3700     case OPC_PUNPCKLWD:
3701         gen_helper_punpcklwd(t0, t0, t1);
3702         break;
3703     case OPC_PUNPCKHWD:
3704         gen_helper_punpckhwd(t0, t0, t1);
3705         break;
3706 
3707     case OPC_PAVGH:
3708         gen_helper_pavgh(t0, t0, t1);
3709         break;
3710     case OPC_PAVGB:
3711         gen_helper_pavgb(t0, t0, t1);
3712         break;
3713     case OPC_PMAXSH:
3714         gen_helper_pmaxsh(t0, t0, t1);
3715         break;
3716     case OPC_PMINSH:
3717         gen_helper_pminsh(t0, t0, t1);
3718         break;
3719     case OPC_PMAXUB:
3720         gen_helper_pmaxub(t0, t0, t1);
3721         break;
3722     case OPC_PMINUB:
3723         gen_helper_pminub(t0, t0, t1);
3724         break;
3725 
3726     case OPC_PCMPEQW:
3727         gen_helper_pcmpeqw(t0, t0, t1);
3728         break;
3729     case OPC_PCMPGTW:
3730         gen_helper_pcmpgtw(t0, t0, t1);
3731         break;
3732     case OPC_PCMPEQH:
3733         gen_helper_pcmpeqh(t0, t0, t1);
3734         break;
3735     case OPC_PCMPGTH:
3736         gen_helper_pcmpgth(t0, t0, t1);
3737         break;
3738     case OPC_PCMPEQB:
3739         gen_helper_pcmpeqb(t0, t0, t1);
3740         break;
3741     case OPC_PCMPGTB:
3742         gen_helper_pcmpgtb(t0, t0, t1);
3743         break;
3744 
3745     case OPC_PSLLW:
3746         gen_helper_psllw(t0, t0, t1);
3747         break;
3748     case OPC_PSLLH:
3749         gen_helper_psllh(t0, t0, t1);
3750         break;
3751     case OPC_PSRLW:
3752         gen_helper_psrlw(t0, t0, t1);
3753         break;
3754     case OPC_PSRLH:
3755         gen_helper_psrlh(t0, t0, t1);
3756         break;
3757     case OPC_PSRAW:
3758         gen_helper_psraw(t0, t0, t1);
3759         break;
3760     case OPC_PSRAH:
3761         gen_helper_psrah(t0, t0, t1);
3762         break;
3763 
3764     case OPC_PMULLH:
3765         gen_helper_pmullh(t0, t0, t1);
3766         break;
3767     case OPC_PMULHH:
3768         gen_helper_pmulhh(t0, t0, t1);
3769         break;
3770     case OPC_PMULHUH:
3771         gen_helper_pmulhuh(t0, t0, t1);
3772         break;
3773     case OPC_PMADDHW:
3774         gen_helper_pmaddhw(t0, t0, t1);
3775         break;
3776 
3777     case OPC_PASUBUB:
3778         gen_helper_pasubub(t0, t0, t1);
3779         break;
3780     case OPC_BIADD:
3781         gen_helper_biadd(t0, t0);
3782         break;
3783     case OPC_PMOVMSKB:
3784         gen_helper_pmovmskb(t0, t0);
3785         break;
3786 
3787     case OPC_PADDD:
3788         tcg_gen_add_i64(t0, t0, t1);
3789         break;
3790     case OPC_PSUBD:
3791         tcg_gen_sub_i64(t0, t0, t1);
3792         break;
3793     case OPC_XOR_CP2:
3794         tcg_gen_xor_i64(t0, t0, t1);
3795         break;
3796     case OPC_NOR_CP2:
3797         tcg_gen_nor_i64(t0, t0, t1);
3798         break;
3799     case OPC_AND_CP2:
3800         tcg_gen_and_i64(t0, t0, t1);
3801         break;
3802     case OPC_OR_CP2:
3803         tcg_gen_or_i64(t0, t0, t1);
3804         break;
3805 
3806     case OPC_PANDN:
3807         tcg_gen_andc_i64(t0, t1, t0);
3808         break;
3809 
3810     case OPC_PINSRH_0:
3811         tcg_gen_deposit_i64(t0, t0, t1, 0, 16);
3812         break;
3813     case OPC_PINSRH_1:
3814         tcg_gen_deposit_i64(t0, t0, t1, 16, 16);
3815         break;
3816     case OPC_PINSRH_2:
3817         tcg_gen_deposit_i64(t0, t0, t1, 32, 16);
3818         break;
3819     case OPC_PINSRH_3:
3820         tcg_gen_deposit_i64(t0, t0, t1, 48, 16);
3821         break;
3822 
3823     case OPC_PEXTRH:
3824         tcg_gen_andi_i64(t1, t1, 3);
3825         tcg_gen_shli_i64(t1, t1, 4);
3826         tcg_gen_shr_i64(t0, t0, t1);
3827         tcg_gen_ext16u_i64(t0, t0);
3828         break;
3829 
3830     case OPC_ADDU_CP2:
3831         tcg_gen_add_i64(t0, t0, t1);
3832         tcg_gen_ext32s_i64(t0, t0);
3833         break;
3834     case OPC_SUBU_CP2:
3835         tcg_gen_sub_i64(t0, t0, t1);
3836         tcg_gen_ext32s_i64(t0, t0);
3837         break;
3838 
3839     case OPC_SLL_CP2:
3840         shift_max = 32;
3841         goto do_shift;
3842     case OPC_SRL_CP2:
3843         shift_max = 32;
3844         goto do_shift;
3845     case OPC_SRA_CP2:
3846         shift_max = 32;
3847         goto do_shift;
3848     case OPC_DSLL_CP2:
3849         shift_max = 64;
3850         goto do_shift;
3851     case OPC_DSRL_CP2:
3852         shift_max = 64;
3853         goto do_shift;
3854     case OPC_DSRA_CP2:
3855         shift_max = 64;
3856         goto do_shift;
3857     do_shift:
3858         /* Make sure shift count isn't TCG undefined behaviour.  */
3859         tcg_gen_andi_i64(t1, t1, shift_max - 1);
3860 
3861         switch (opc) {
3862         case OPC_SLL_CP2:
3863         case OPC_DSLL_CP2:
3864             tcg_gen_shl_i64(t0, t0, t1);
3865             break;
3866         case OPC_SRA_CP2:
3867         case OPC_DSRA_CP2:
3868             /*
3869              * Since SRA is UndefinedResult without sign-extended inputs,
3870              * we can treat SRA and DSRA the same.
3871              */
3872             tcg_gen_sar_i64(t0, t0, t1);
3873             break;
3874         case OPC_SRL_CP2:
3875             /* We want to shift in zeros for SRL; zero-extend first.  */
3876             tcg_gen_ext32u_i64(t0, t0);
3877             /* FALLTHRU */
3878         case OPC_DSRL_CP2:
3879             tcg_gen_shr_i64(t0, t0, t1);
3880             break;
3881         }
3882 
3883         if (shift_max == 32) {
3884             tcg_gen_ext32s_i64(t0, t0);
3885         }
3886 
3887         /* Shifts larger than MAX produce zero.  */
3888         tcg_gen_setcondi_i64(TCG_COND_LTU, t1, t1, shift_max);
3889         tcg_gen_neg_i64(t1, t1);
3890         tcg_gen_and_i64(t0, t0, t1);
3891         break;
3892 
3893     case OPC_ADD_CP2:
3894     case OPC_DADD_CP2:
3895         {
3896             TCGv_i64 t2 = tcg_temp_new_i64();
3897             TCGLabel *lab = gen_new_label();
3898 
3899             tcg_gen_mov_i64(t2, t0);
3900             tcg_gen_add_i64(t0, t1, t2);
3901             if (opc == OPC_ADD_CP2) {
3902                 tcg_gen_ext32s_i64(t0, t0);
3903             }
3904             tcg_gen_xor_i64(t1, t1, t2);
3905             tcg_gen_xor_i64(t2, t2, t0);
3906             tcg_gen_andc_i64(t1, t2, t1);
3907             tcg_gen_brcondi_i64(TCG_COND_GE, t1, 0, lab);
3908             generate_exception(ctx, EXCP_OVERFLOW);
3909             gen_set_label(lab);
3910             break;
3911         }
3912 
3913     case OPC_SUB_CP2:
3914     case OPC_DSUB_CP2:
3915         {
3916             TCGv_i64 t2 = tcg_temp_new_i64();
3917             TCGLabel *lab = gen_new_label();
3918 
3919             tcg_gen_mov_i64(t2, t0);
3920             tcg_gen_sub_i64(t0, t1, t2);
3921             if (opc == OPC_SUB_CP2) {
3922                 tcg_gen_ext32s_i64(t0, t0);
3923             }
3924             tcg_gen_xor_i64(t1, t1, t2);
3925             tcg_gen_xor_i64(t2, t2, t0);
3926             tcg_gen_and_i64(t1, t1, t2);
3927             tcg_gen_brcondi_i64(TCG_COND_GE, t1, 0, lab);
3928             generate_exception(ctx, EXCP_OVERFLOW);
3929             gen_set_label(lab);
3930             break;
3931         }
3932 
3933     case OPC_PMULUW:
3934         tcg_gen_ext32u_i64(t0, t0);
3935         tcg_gen_ext32u_i64(t1, t1);
3936         tcg_gen_mul_i64(t0, t0, t1);
3937         break;
3938 
3939     case OPC_SEQU_CP2:
3940     case OPC_SEQ_CP2:
3941         cond = TCG_COND_EQ;
3942         goto do_cc_cond;
3943         break;
3944     case OPC_SLTU_CP2:
3945         cond = TCG_COND_LTU;
3946         goto do_cc_cond;
3947         break;
3948     case OPC_SLT_CP2:
3949         cond = TCG_COND_LT;
3950         goto do_cc_cond;
3951         break;
3952     case OPC_SLEU_CP2:
3953         cond = TCG_COND_LEU;
3954         goto do_cc_cond;
3955         break;
3956     case OPC_SLE_CP2:
3957         cond = TCG_COND_LE;
3958     do_cc_cond:
3959         {
3960             int cc = (ctx->opcode >> 8) & 0x7;
3961             TCGv_i64 t64 = tcg_temp_new_i64();
3962             TCGv_i32 t32 = tcg_temp_new_i32();
3963 
3964             tcg_gen_setcond_i64(cond, t64, t0, t1);
3965             tcg_gen_extrl_i64_i32(t32, t64);
3966             tcg_gen_deposit_i32(fpu_fcr31, fpu_fcr31, t32,
3967                                 get_fp_bit(cc), 1);
3968         }
3969         return;
3970     default:
3971         MIPS_INVAL("loongson_cp2");
3972         gen_reserved_instruction(ctx);
3973         return;
3974     }
3975 
3976     gen_store_fpr64(ctx, t0, rd);
3977 }
3978 
3979 static void gen_loongson_lswc2(DisasContext *ctx, int rt,
3980                                int rs, int rd)
3981 {
3982     TCGv t0, t1;
3983     TCGv_i32 fp0;
3984 #if defined(TARGET_MIPS64)
3985     int lsq_rt1 = ctx->opcode & 0x1f;
3986     int lsq_offset = sextract32(ctx->opcode, 6, 9) << 4;
3987 #endif
3988     int shf_offset = sextract32(ctx->opcode, 6, 8);
3989 
3990     t0 = tcg_temp_new();
3991 
3992     switch (MASK_LOONGSON_GSLSQ(ctx->opcode)) {
3993 #if defined(TARGET_MIPS64)
3994     case OPC_GSLQ:
3995         t1 = tcg_temp_new();
3996         gen_base_offset_addr(ctx, t0, rs, lsq_offset);
3997         tcg_gen_qemu_ld_tl(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
3998                            ctx->default_tcg_memop_mask);
3999         gen_base_offset_addr(ctx, t0, rs, lsq_offset + 8);
4000         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4001                            ctx->default_tcg_memop_mask);
4002         gen_store_gpr(t1, rt);
4003         gen_store_gpr(t0, lsq_rt1);
4004         break;
4005     case OPC_GSLQC1:
4006         check_cp1_enabled(ctx);
4007         t1 = tcg_temp_new();
4008         gen_base_offset_addr(ctx, t0, rs, lsq_offset);
4009         tcg_gen_qemu_ld_tl(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4010                            ctx->default_tcg_memop_mask);
4011         gen_base_offset_addr(ctx, t0, rs, lsq_offset + 8);
4012         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4013                            ctx->default_tcg_memop_mask);
4014         gen_store_fpr64(ctx, t1, rt);
4015         gen_store_fpr64(ctx, t0, lsq_rt1);
4016         break;
4017     case OPC_GSSQ:
4018         t1 = tcg_temp_new();
4019         gen_base_offset_addr(ctx, t0, rs, lsq_offset);
4020         gen_load_gpr(t1, rt);
4021         tcg_gen_qemu_st_tl(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4022                            ctx->default_tcg_memop_mask);
4023         gen_base_offset_addr(ctx, t0, rs, lsq_offset + 8);
4024         gen_load_gpr(t1, lsq_rt1);
4025         tcg_gen_qemu_st_tl(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4026                            ctx->default_tcg_memop_mask);
4027         break;
4028     case OPC_GSSQC1:
4029         check_cp1_enabled(ctx);
4030         t1 = tcg_temp_new();
4031         gen_base_offset_addr(ctx, t0, rs, lsq_offset);
4032         gen_load_fpr64(ctx, t1, rt);
4033         tcg_gen_qemu_st_tl(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4034                            ctx->default_tcg_memop_mask);
4035         gen_base_offset_addr(ctx, t0, rs, lsq_offset + 8);
4036         gen_load_fpr64(ctx, t1, lsq_rt1);
4037         tcg_gen_qemu_st_tl(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4038                            ctx->default_tcg_memop_mask);
4039         break;
4040 #endif
4041     case OPC_GSSHFL:
4042         switch (MASK_LOONGSON_GSSHFLS(ctx->opcode)) {
4043         case OPC_GSLWLC1:
4044             check_cp1_enabled(ctx);
4045             gen_base_offset_addr(ctx, t0, rs, shf_offset);
4046             fp0 = tcg_temp_new_i32();
4047             gen_load_fpr32(ctx, fp0, rt);
4048             t1 = tcg_temp_new();
4049             tcg_gen_ext_i32_tl(t1, fp0);
4050             gen_lxl(ctx, t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UL);
4051             tcg_gen_trunc_tl_i32(fp0, t1);
4052             gen_store_fpr32(ctx, fp0, rt);
4053             break;
4054         case OPC_GSLWRC1:
4055             check_cp1_enabled(ctx);
4056             gen_base_offset_addr(ctx, t0, rs, shf_offset);
4057             fp0 = tcg_temp_new_i32();
4058             gen_load_fpr32(ctx, fp0, rt);
4059             t1 = tcg_temp_new();
4060             tcg_gen_ext_i32_tl(t1, fp0);
4061             gen_lxr(ctx, t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UL);
4062             tcg_gen_trunc_tl_i32(fp0, t1);
4063             gen_store_fpr32(ctx, fp0, rt);
4064             break;
4065 #if defined(TARGET_MIPS64)
4066         case OPC_GSLDLC1:
4067             check_cp1_enabled(ctx);
4068             gen_base_offset_addr(ctx, t0, rs, shf_offset);
4069             t1 = tcg_temp_new();
4070             gen_load_fpr64(ctx, t1, rt);
4071             gen_lxl(ctx, t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ);
4072             gen_store_fpr64(ctx, t1, rt);
4073             break;
4074         case OPC_GSLDRC1:
4075             check_cp1_enabled(ctx);
4076             gen_base_offset_addr(ctx, t0, rs, shf_offset);
4077             t1 = tcg_temp_new();
4078             gen_load_fpr64(ctx, t1, rt);
4079             gen_lxr(ctx, t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ);
4080             gen_store_fpr64(ctx, t1, rt);
4081             break;
4082 #endif
4083         default:
4084             MIPS_INVAL("loongson_gsshfl");
4085             gen_reserved_instruction(ctx);
4086             break;
4087         }
4088         break;
4089     case OPC_GSSHFS:
4090         switch (MASK_LOONGSON_GSSHFLS(ctx->opcode)) {
4091         case OPC_GSSWLC1:
4092             check_cp1_enabled(ctx);
4093             t1 = tcg_temp_new();
4094             gen_base_offset_addr(ctx, t0, rs, shf_offset);
4095             fp0 = tcg_temp_new_i32();
4096             gen_load_fpr32(ctx, fp0, rt);
4097             tcg_gen_ext_i32_tl(t1, fp0);
4098             gen_helper_0e2i(swl, t1, t0, ctx->mem_idx);
4099             break;
4100         case OPC_GSSWRC1:
4101             check_cp1_enabled(ctx);
4102             t1 = tcg_temp_new();
4103             gen_base_offset_addr(ctx, t0, rs, shf_offset);
4104             fp0 = tcg_temp_new_i32();
4105             gen_load_fpr32(ctx, fp0, rt);
4106             tcg_gen_ext_i32_tl(t1, fp0);
4107             gen_helper_0e2i(swr, t1, t0, ctx->mem_idx);
4108             break;
4109 #if defined(TARGET_MIPS64)
4110         case OPC_GSSDLC1:
4111             check_cp1_enabled(ctx);
4112             t1 = tcg_temp_new();
4113             gen_base_offset_addr(ctx, t0, rs, shf_offset);
4114             gen_load_fpr64(ctx, t1, rt);
4115             gen_helper_0e2i(sdl, t1, t0, ctx->mem_idx);
4116             break;
4117         case OPC_GSSDRC1:
4118             check_cp1_enabled(ctx);
4119             t1 = tcg_temp_new();
4120             gen_base_offset_addr(ctx, t0, rs, shf_offset);
4121             gen_load_fpr64(ctx, t1, rt);
4122             gen_helper_0e2i(sdr, t1, t0, ctx->mem_idx);
4123             break;
4124 #endif
4125         default:
4126             MIPS_INVAL("loongson_gsshfs");
4127             gen_reserved_instruction(ctx);
4128             break;
4129         }
4130         break;
4131     default:
4132         MIPS_INVAL("loongson_gslsq");
4133         gen_reserved_instruction(ctx);
4134         break;
4135     }
4136 }
4137 
4138 /* Loongson EXT LDC2/SDC2 */
4139 static void gen_loongson_lsdc2(DisasContext *ctx, int rt,
4140                                int rs, int rd)
4141 {
4142     int offset = sextract32(ctx->opcode, 3, 8);
4143     uint32_t opc = MASK_LOONGSON_LSDC2(ctx->opcode);
4144     TCGv t0, t1;
4145     TCGv_i32 fp0;
4146 
4147     /* Pre-conditions */
4148     switch (opc) {
4149     case OPC_GSLBX:
4150     case OPC_GSLHX:
4151     case OPC_GSLWX:
4152     case OPC_GSLDX:
4153         /* prefetch, implement as NOP */
4154         if (rt == 0) {
4155             return;
4156         }
4157         break;
4158     case OPC_GSSBX:
4159     case OPC_GSSHX:
4160     case OPC_GSSWX:
4161     case OPC_GSSDX:
4162         break;
4163     case OPC_GSLWXC1:
4164 #if defined(TARGET_MIPS64)
4165     case OPC_GSLDXC1:
4166 #endif
4167         check_cp1_enabled(ctx);
4168         /* prefetch, implement as NOP */
4169         if (rt == 0) {
4170             return;
4171         }
4172         break;
4173     case OPC_GSSWXC1:
4174 #if defined(TARGET_MIPS64)
4175     case OPC_GSSDXC1:
4176 #endif
4177         check_cp1_enabled(ctx);
4178         break;
4179     default:
4180         MIPS_INVAL("loongson_lsdc2");
4181         gen_reserved_instruction(ctx);
4182         return;
4183         break;
4184     }
4185 
4186     t0 = tcg_temp_new();
4187 
4188     gen_base_offset_addr(ctx, t0, rs, offset);
4189     gen_op_addr_add(ctx, t0, cpu_gpr[rd], t0);
4190 
4191     switch (opc) {
4192     case OPC_GSLBX:
4193         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, MO_SB);
4194         gen_store_gpr(t0, rt);
4195         break;
4196     case OPC_GSLHX:
4197         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, mo_endian(ctx) | MO_SW |
4198                            ctx->default_tcg_memop_mask);
4199         gen_store_gpr(t0, rt);
4200         break;
4201     case OPC_GSLWX:
4202         gen_base_offset_addr(ctx, t0, rs, offset);
4203         if (rd) {
4204             gen_op_addr_add(ctx, t0, cpu_gpr[rd], t0);
4205         }
4206         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, mo_endian(ctx) | MO_SL |
4207                            ctx->default_tcg_memop_mask);
4208         gen_store_gpr(t0, rt);
4209         break;
4210 #if defined(TARGET_MIPS64)
4211     case OPC_GSLDX:
4212         gen_base_offset_addr(ctx, t0, rs, offset);
4213         if (rd) {
4214             gen_op_addr_add(ctx, t0, cpu_gpr[rd], t0);
4215         }
4216         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4217                            ctx->default_tcg_memop_mask);
4218         gen_store_gpr(t0, rt);
4219         break;
4220 #endif
4221     case OPC_GSLWXC1:
4222         gen_base_offset_addr(ctx, t0, rs, offset);
4223         if (rd) {
4224             gen_op_addr_add(ctx, t0, cpu_gpr[rd], t0);
4225         }
4226         fp0 = tcg_temp_new_i32();
4227         tcg_gen_qemu_ld_i32(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_SL |
4228                             ctx->default_tcg_memop_mask);
4229         gen_store_fpr32(ctx, fp0, rt);
4230         break;
4231 #if defined(TARGET_MIPS64)
4232     case OPC_GSLDXC1:
4233         gen_base_offset_addr(ctx, t0, rs, offset);
4234         if (rd) {
4235             gen_op_addr_add(ctx, t0, cpu_gpr[rd], t0);
4236         }
4237         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4238                            ctx->default_tcg_memop_mask);
4239         gen_store_fpr64(ctx, t0, rt);
4240         break;
4241 #endif
4242     case OPC_GSSBX:
4243         t1 = tcg_temp_new();
4244         gen_load_gpr(t1, rt);
4245         tcg_gen_qemu_st_tl(t1, t0, ctx->mem_idx, MO_SB);
4246         break;
4247     case OPC_GSSHX:
4248         t1 = tcg_temp_new();
4249         gen_load_gpr(t1, rt);
4250         tcg_gen_qemu_st_tl(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UW |
4251                            ctx->default_tcg_memop_mask);
4252         break;
4253     case OPC_GSSWX:
4254         t1 = tcg_temp_new();
4255         gen_load_gpr(t1, rt);
4256         tcg_gen_qemu_st_tl(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UL |
4257                            ctx->default_tcg_memop_mask);
4258         break;
4259 #if defined(TARGET_MIPS64)
4260     case OPC_GSSDX:
4261         t1 = tcg_temp_new();
4262         gen_load_gpr(t1, rt);
4263         tcg_gen_qemu_st_tl(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4264                            ctx->default_tcg_memop_mask);
4265         break;
4266 #endif
4267     case OPC_GSSWXC1:
4268         fp0 = tcg_temp_new_i32();
4269         gen_load_fpr32(ctx, fp0, rt);
4270         tcg_gen_qemu_st_i32(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UL |
4271                             ctx->default_tcg_memop_mask);
4272         break;
4273 #if defined(TARGET_MIPS64)
4274     case OPC_GSSDXC1:
4275         t1 = tcg_temp_new();
4276         gen_load_fpr64(ctx, t1, rt);
4277         tcg_gen_qemu_st_i64(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ |
4278                             ctx->default_tcg_memop_mask);
4279         break;
4280 #endif
4281     default:
4282         break;
4283     }
4284 }
4285 
4286 /* Traps */
4287 static void gen_trap(DisasContext *ctx, uint32_t opc,
4288                      int rs, int rt, int16_t imm, int code)
4289 {
4290     int cond;
4291     TCGv t0 = tcg_temp_new();
4292     TCGv t1 = tcg_temp_new();
4293 
4294     cond = 0;
4295     /* Load needed operands */
4296     switch (opc) {
4297     case OPC_TEQ:
4298     case OPC_TGE:
4299     case OPC_TGEU:
4300     case OPC_TLT:
4301     case OPC_TLTU:
4302     case OPC_TNE:
4303         /* Compare two registers */
4304         if (rs != rt) {
4305             gen_load_gpr(t0, rs);
4306             gen_load_gpr(t1, rt);
4307             cond = 1;
4308         }
4309         break;
4310     case OPC_TEQI:
4311     case OPC_TGEI:
4312     case OPC_TGEIU:
4313     case OPC_TLTI:
4314     case OPC_TLTIU:
4315     case OPC_TNEI:
4316         /* Compare register to immediate */
4317         if (rs != 0 || imm != 0) {
4318             gen_load_gpr(t0, rs);
4319             tcg_gen_movi_tl(t1, (int32_t)imm);
4320             cond = 1;
4321         }
4322         break;
4323     }
4324     if (cond == 0) {
4325         switch (opc) {
4326         case OPC_TEQ:   /* rs == rs */
4327         case OPC_TEQI:  /* r0 == 0  */
4328         case OPC_TGE:   /* rs >= rs */
4329         case OPC_TGEI:  /* r0 >= 0  */
4330         case OPC_TGEU:  /* rs >= rs unsigned */
4331         case OPC_TGEIU: /* r0 >= 0  unsigned */
4332             /* Always trap */
4333 #ifdef CONFIG_USER_ONLY
4334             /* Pass the break code along to cpu_loop. */
4335             tcg_gen_st_i32(tcg_constant_i32(code), tcg_env,
4336                            offsetof(CPUMIPSState, error_code));
4337 #endif
4338             generate_exception_end(ctx, EXCP_TRAP);
4339             break;
4340         case OPC_TLT:   /* rs < rs           */
4341         case OPC_TLTI:  /* r0 < 0            */
4342         case OPC_TLTU:  /* rs < rs unsigned  */
4343         case OPC_TLTIU: /* r0 < 0  unsigned  */
4344         case OPC_TNE:   /* rs != rs          */
4345         case OPC_TNEI:  /* r0 != 0           */
4346             /* Never trap: treat as NOP. */
4347             break;
4348         }
4349     } else {
4350         TCGLabel *l1 = gen_new_label();
4351 
4352         switch (opc) {
4353         case OPC_TEQ:
4354         case OPC_TEQI:
4355             tcg_gen_brcond_tl(TCG_COND_NE, t0, t1, l1);
4356             break;
4357         case OPC_TGE:
4358         case OPC_TGEI:
4359             tcg_gen_brcond_tl(TCG_COND_LT, t0, t1, l1);
4360             break;
4361         case OPC_TGEU:
4362         case OPC_TGEIU:
4363             tcg_gen_brcond_tl(TCG_COND_LTU, t0, t1, l1);
4364             break;
4365         case OPC_TLT:
4366         case OPC_TLTI:
4367             tcg_gen_brcond_tl(TCG_COND_GE, t0, t1, l1);
4368             break;
4369         case OPC_TLTU:
4370         case OPC_TLTIU:
4371             tcg_gen_brcond_tl(TCG_COND_GEU, t0, t1, l1);
4372             break;
4373         case OPC_TNE:
4374         case OPC_TNEI:
4375             tcg_gen_brcond_tl(TCG_COND_EQ, t0, t1, l1);
4376             break;
4377         }
4378 #ifdef CONFIG_USER_ONLY
4379         /* Pass the break code along to cpu_loop. */
4380         tcg_gen_st_i32(tcg_constant_i32(code), tcg_env,
4381                        offsetof(CPUMIPSState, error_code));
4382 #endif
4383         /* Like save_cpu_state, only don't update saved values. */
4384         if (ctx->base.pc_next != ctx->saved_pc) {
4385             gen_save_pc(ctx->base.pc_next);
4386         }
4387         if (ctx->hflags != ctx->saved_hflags) {
4388             tcg_gen_movi_i32(hflags, ctx->hflags);
4389         }
4390         generate_exception(ctx, EXCP_TRAP);
4391         gen_set_label(l1);
4392     }
4393 }
4394 
4395 static void gen_goto_tb(DisasContext *ctx, int n, target_ulong dest)
4396 {
4397     if (translator_use_goto_tb(&ctx->base, dest)) {
4398         tcg_gen_goto_tb(n);
4399         gen_save_pc(dest);
4400         tcg_gen_exit_tb(ctx->base.tb, n);
4401     } else {
4402         gen_save_pc(dest);
4403         tcg_gen_lookup_and_goto_ptr();
4404     }
4405 }
4406 
4407 /* Branches (before delay slot) */
4408 static void gen_compute_branch(DisasContext *ctx, uint32_t opc,
4409                                int insn_bytes,
4410                                int rs, int rt, int32_t offset,
4411                                int delayslot_size)
4412 {
4413     target_ulong btgt = -1;
4414     int blink = 0;
4415     int bcond_compute = 0;
4416     TCGv t0 = tcg_temp_new();
4417     TCGv t1 = tcg_temp_new();
4418 
4419     if (ctx->hflags & MIPS_HFLAG_BMASK) {
4420 #ifdef MIPS_DEBUG_DISAS
4421         LOG_DISAS("Branch in delay / forbidden slot at PC 0x%016"
4422                   VADDR_PRIx "\n", ctx->base.pc_next);
4423 #endif
4424         gen_reserved_instruction(ctx);
4425         goto out;
4426     }
4427 
4428     /* Load needed operands */
4429     switch (opc) {
4430     case OPC_BEQ:
4431     case OPC_BEQL:
4432     case OPC_BNE:
4433     case OPC_BNEL:
4434         /* Compare two registers */
4435         if (rs != rt) {
4436             gen_load_gpr(t0, rs);
4437             gen_load_gpr(t1, rt);
4438             bcond_compute = 1;
4439         }
4440         btgt = ctx->base.pc_next + insn_bytes + offset;
4441         break;
4442     case OPC_BGEZ:
4443     case OPC_BGEZAL:
4444     case OPC_BGEZALL:
4445     case OPC_BGEZL:
4446     case OPC_BGTZ:
4447     case OPC_BGTZL:
4448     case OPC_BLEZ:
4449     case OPC_BLEZL:
4450     case OPC_BLTZ:
4451     case OPC_BLTZAL:
4452     case OPC_BLTZALL:
4453     case OPC_BLTZL:
4454         /* Compare to zero */
4455         if (rs != 0) {
4456             gen_load_gpr(t0, rs);
4457             bcond_compute = 1;
4458         }
4459         btgt = ctx->base.pc_next + insn_bytes + offset;
4460         break;
4461     case OPC_BPOSGE32:
4462 #if defined(TARGET_MIPS64)
4463     case OPC_BPOSGE64:
4464         tcg_gen_andi_tl(t0, cpu_dspctrl, 0x7F);
4465 #else
4466         tcg_gen_andi_tl(t0, cpu_dspctrl, 0x3F);
4467 #endif
4468         bcond_compute = 1;
4469         btgt = ctx->base.pc_next + insn_bytes + offset;
4470         break;
4471     case OPC_J:
4472     case OPC_JAL:
4473         {
4474             /* Jump to immediate */
4475             int jal_mask = ctx->hflags & MIPS_HFLAG_M16 ? 0xF8000000
4476                                                         : 0xF0000000;
4477             btgt = ((ctx->base.pc_next + insn_bytes) & jal_mask)
4478                    | (uint32_t)offset;
4479             break;
4480         }
4481     case OPC_JALX:
4482         /* Jump to immediate */
4483         btgt = ((ctx->base.pc_next + insn_bytes) & (int32_t)0xF0000000) |
4484             (uint32_t)offset;
4485         break;
4486     case OPC_JR:
4487     case OPC_JALR:
4488         /* Jump to register */
4489         if (offset != 0 && offset != 16) {
4490             /*
4491              * Hint = 0 is JR/JALR, hint 16 is JR.HB/JALR.HB, the
4492              * others are reserved.
4493              */
4494             MIPS_INVAL("jump hint");
4495             gen_reserved_instruction(ctx);
4496             goto out;
4497         }
4498         gen_load_gpr(btarget, rs);
4499         break;
4500     default:
4501         MIPS_INVAL("branch/jump");
4502         gen_reserved_instruction(ctx);
4503         goto out;
4504     }
4505     if (bcond_compute == 0) {
4506         /* No condition to be computed */
4507         switch (opc) {
4508         case OPC_BEQ:     /* rx == rx        */
4509         case OPC_BEQL:    /* rx == rx likely */
4510         case OPC_BGEZ:    /* 0 >= 0          */
4511         case OPC_BGEZL:   /* 0 >= 0 likely   */
4512         case OPC_BLEZ:    /* 0 <= 0          */
4513         case OPC_BLEZL:   /* 0 <= 0 likely   */
4514             /* Always take */
4515             ctx->hflags |= MIPS_HFLAG_B;
4516             break;
4517         case OPC_BGEZAL:  /* 0 >= 0          */
4518         case OPC_BGEZALL: /* 0 >= 0 likely   */
4519             /* Always take and link */
4520             blink = 31;
4521             ctx->hflags |= MIPS_HFLAG_B;
4522             break;
4523         case OPC_BNE:     /* rx != rx        */
4524         case OPC_BGTZ:    /* 0 > 0           */
4525         case OPC_BLTZ:    /* 0 < 0           */
4526             /* Treat as NOP. */
4527             goto out;
4528         case OPC_BLTZAL:  /* 0 < 0           */
4529             /*
4530              * Handle as an unconditional branch to get correct delay
4531              * slot checking.
4532              */
4533             blink = 31;
4534             btgt = ctx->base.pc_next + insn_bytes + delayslot_size;
4535             ctx->hflags |= MIPS_HFLAG_B;
4536             break;
4537         case OPC_BLTZALL: /* 0 < 0 likely */
4538             tcg_gen_movi_tl(cpu_gpr[31], ctx->base.pc_next + 8);
4539             /* Skip the instruction in the delay slot */
4540             ctx->base.pc_next += 4;
4541             goto out;
4542         case OPC_BNEL:    /* rx != rx likely */
4543         case OPC_BGTZL:   /* 0 > 0 likely */
4544         case OPC_BLTZL:   /* 0 < 0 likely */
4545             /* Skip the instruction in the delay slot */
4546             ctx->base.pc_next += 4;
4547             goto out;
4548         case OPC_J:
4549             ctx->hflags |= MIPS_HFLAG_B;
4550             break;
4551         case OPC_JALX:
4552             ctx->hflags |= MIPS_HFLAG_BX;
4553             /* Fallthrough */
4554         case OPC_JAL:
4555             blink = 31;
4556             ctx->hflags |= MIPS_HFLAG_B;
4557             break;
4558         case OPC_JR:
4559             ctx->hflags |= MIPS_HFLAG_BR;
4560             break;
4561         case OPC_JALR:
4562             blink = rt;
4563             ctx->hflags |= MIPS_HFLAG_BR;
4564             break;
4565         default:
4566             MIPS_INVAL("branch/jump");
4567             gen_reserved_instruction(ctx);
4568             goto out;
4569         }
4570     } else {
4571         switch (opc) {
4572         case OPC_BEQ:
4573             tcg_gen_setcond_tl(TCG_COND_EQ, bcond, t0, t1);
4574             goto not_likely;
4575         case OPC_BEQL:
4576             tcg_gen_setcond_tl(TCG_COND_EQ, bcond, t0, t1);
4577             goto likely;
4578         case OPC_BNE:
4579             tcg_gen_setcond_tl(TCG_COND_NE, bcond, t0, t1);
4580             goto not_likely;
4581         case OPC_BNEL:
4582             tcg_gen_setcond_tl(TCG_COND_NE, bcond, t0, t1);
4583             goto likely;
4584         case OPC_BGEZ:
4585             tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
4586             goto not_likely;
4587         case OPC_BGEZL:
4588             tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
4589             goto likely;
4590         case OPC_BGEZAL:
4591             tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
4592             blink = 31;
4593             goto not_likely;
4594         case OPC_BGEZALL:
4595             tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 0);
4596             blink = 31;
4597             goto likely;
4598         case OPC_BGTZ:
4599             tcg_gen_setcondi_tl(TCG_COND_GT, bcond, t0, 0);
4600             goto not_likely;
4601         case OPC_BGTZL:
4602             tcg_gen_setcondi_tl(TCG_COND_GT, bcond, t0, 0);
4603             goto likely;
4604         case OPC_BLEZ:
4605             tcg_gen_setcondi_tl(TCG_COND_LE, bcond, t0, 0);
4606             goto not_likely;
4607         case OPC_BLEZL:
4608             tcg_gen_setcondi_tl(TCG_COND_LE, bcond, t0, 0);
4609             goto likely;
4610         case OPC_BLTZ:
4611             tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
4612             goto not_likely;
4613         case OPC_BLTZL:
4614             tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
4615             goto likely;
4616         case OPC_BPOSGE32:
4617             tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 32);
4618             goto not_likely;
4619 #if defined(TARGET_MIPS64)
4620         case OPC_BPOSGE64:
4621             tcg_gen_setcondi_tl(TCG_COND_GE, bcond, t0, 64);
4622             goto not_likely;
4623 #endif
4624         case OPC_BLTZAL:
4625             tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
4626             blink = 31;
4627         not_likely:
4628             ctx->hflags |= MIPS_HFLAG_BC;
4629             break;
4630         case OPC_BLTZALL:
4631             tcg_gen_setcondi_tl(TCG_COND_LT, bcond, t0, 0);
4632             blink = 31;
4633         likely:
4634             ctx->hflags |= MIPS_HFLAG_BL;
4635             break;
4636         default:
4637             MIPS_INVAL("conditional branch/jump");
4638             gen_reserved_instruction(ctx);
4639             goto out;
4640         }
4641     }
4642 
4643     ctx->btarget = btgt;
4644 
4645     switch (delayslot_size) {
4646     case 2:
4647         ctx->hflags |= MIPS_HFLAG_BDS16;
4648         break;
4649     case 4:
4650         ctx->hflags |= MIPS_HFLAG_BDS32;
4651         break;
4652     }
4653 
4654     if (blink > 0) {
4655         int post_delay = insn_bytes + delayslot_size;
4656         int lowbit = !!(ctx->hflags & MIPS_HFLAG_M16);
4657 
4658         tcg_gen_movi_tl(cpu_gpr[blink],
4659                         ctx->base.pc_next + post_delay + lowbit);
4660     }
4661 
4662  out:
4663     if (insn_bytes == 2) {
4664         ctx->hflags |= MIPS_HFLAG_B16;
4665     }
4666 }
4667 
4668 
4669 /* special3 bitfield operations */
4670 static void gen_bitops(DisasContext *ctx, uint32_t opc, int rt,
4671                        int rs, int lsb, int msb)
4672 {
4673     TCGv t0 = tcg_temp_new();
4674     TCGv t1 = tcg_temp_new();
4675 
4676     gen_load_gpr(t1, rs);
4677     switch (opc) {
4678     case OPC_EXT:
4679         if (lsb + msb > 31) {
4680             goto fail;
4681         }
4682         if (msb != 31) {
4683             tcg_gen_extract_tl(t0, t1, lsb, msb + 1);
4684         } else {
4685             /*
4686              * The two checks together imply that lsb == 0,
4687              * so this is a simple sign-extension.
4688              */
4689             tcg_gen_ext32s_tl(t0, t1);
4690         }
4691         break;
4692 #if defined(TARGET_MIPS64)
4693     case OPC_DEXTU:
4694         lsb += 32;
4695         goto do_dext;
4696     case OPC_DEXTM:
4697         msb += 32;
4698         goto do_dext;
4699     case OPC_DEXT:
4700     do_dext:
4701         if (lsb + msb > 63) {
4702             goto fail;
4703         }
4704         tcg_gen_extract_tl(t0, t1, lsb, msb + 1);
4705         break;
4706 #endif
4707     case OPC_INS:
4708         if (lsb > msb) {
4709             goto fail;
4710         }
4711         gen_load_gpr(t0, rt);
4712         tcg_gen_deposit_tl(t0, t0, t1, lsb, msb - lsb + 1);
4713         tcg_gen_ext32s_tl(t0, t0);
4714         break;
4715 #if defined(TARGET_MIPS64)
4716     case OPC_DINSU:
4717         lsb += 32;
4718         /* FALLTHRU */
4719     case OPC_DINSM:
4720         msb += 32;
4721         /* FALLTHRU */
4722     case OPC_DINS:
4723         if (lsb > msb) {
4724             goto fail;
4725         }
4726         gen_load_gpr(t0, rt);
4727         tcg_gen_deposit_tl(t0, t0, t1, lsb, msb - lsb + 1);
4728         break;
4729 #endif
4730     default:
4731 fail:
4732         MIPS_INVAL("bitops");
4733         gen_reserved_instruction(ctx);
4734         return;
4735     }
4736     gen_store_gpr(t0, rt);
4737 }
4738 
4739 static void gen_bshfl(DisasContext *ctx, uint32_t op2, int rt, int rd)
4740 {
4741     TCGv t0;
4742 
4743     if (rd == 0) {
4744         /* If no destination, treat it as a NOP. */
4745         return;
4746     }
4747 
4748     t0 = tcg_temp_new();
4749     gen_load_gpr(t0, rt);
4750     switch (op2) {
4751     case OPC_WSBH:
4752         {
4753             TCGv t1 = tcg_temp_new();
4754             TCGv t2 = tcg_constant_tl(0x00FF00FF);
4755 
4756             tcg_gen_shri_tl(t1, t0, 8);
4757             tcg_gen_and_tl(t1, t1, t2);
4758             tcg_gen_and_tl(t0, t0, t2);
4759             tcg_gen_shli_tl(t0, t0, 8);
4760             tcg_gen_or_tl(t0, t0, t1);
4761             tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
4762         }
4763         break;
4764     case OPC_SEB:
4765         tcg_gen_ext8s_tl(cpu_gpr[rd], t0);
4766         break;
4767     case OPC_SEH:
4768         tcg_gen_ext16s_tl(cpu_gpr[rd], t0);
4769         break;
4770 #if defined(TARGET_MIPS64)
4771     case OPC_DSBH:
4772         {
4773             TCGv t1 = tcg_temp_new();
4774             TCGv t2 = tcg_constant_tl(0x00FF00FF00FF00FFULL);
4775 
4776             tcg_gen_shri_tl(t1, t0, 8);
4777             tcg_gen_and_tl(t1, t1, t2);
4778             tcg_gen_and_tl(t0, t0, t2);
4779             tcg_gen_shli_tl(t0, t0, 8);
4780             tcg_gen_or_tl(cpu_gpr[rd], t0, t1);
4781         }
4782         break;
4783     case OPC_DSHD:
4784         {
4785             TCGv t1 = tcg_temp_new();
4786             TCGv t2 = tcg_constant_tl(0x0000FFFF0000FFFFULL);
4787 
4788             tcg_gen_shri_tl(t1, t0, 16);
4789             tcg_gen_and_tl(t1, t1, t2);
4790             tcg_gen_and_tl(t0, t0, t2);
4791             tcg_gen_shli_tl(t0, t0, 16);
4792             tcg_gen_or_tl(t0, t0, t1);
4793             tcg_gen_shri_tl(t1, t0, 32);
4794             tcg_gen_shli_tl(t0, t0, 32);
4795             tcg_gen_or_tl(cpu_gpr[rd], t0, t1);
4796         }
4797         break;
4798 #endif
4799     default:
4800         MIPS_INVAL("bsfhl");
4801         gen_reserved_instruction(ctx);
4802         return;
4803     }
4804 }
4805 
4806 static void gen_align_bits(DisasContext *ctx, int wordsz, int rd, int rs,
4807                            int rt, int bits)
4808 {
4809     TCGv t0;
4810     if (rd == 0) {
4811         /* Treat as NOP. */
4812         return;
4813     }
4814     t0 = tcg_temp_new();
4815     if (bits == 0 || bits == wordsz) {
4816         if (bits == 0) {
4817             gen_load_gpr(t0, rt);
4818         } else {
4819             gen_load_gpr(t0, rs);
4820         }
4821         switch (wordsz) {
4822         case 32:
4823             tcg_gen_ext32s_tl(cpu_gpr[rd], t0);
4824             break;
4825 #if defined(TARGET_MIPS64)
4826         case 64:
4827             tcg_gen_mov_tl(cpu_gpr[rd], t0);
4828             break;
4829 #endif
4830         }
4831     } else {
4832         TCGv t1 = tcg_temp_new();
4833         gen_load_gpr(t0, rt);
4834         gen_load_gpr(t1, rs);
4835         switch (wordsz) {
4836         case 32:
4837             {
4838                 TCGv_i64 t2 = tcg_temp_new_i64();
4839                 tcg_gen_concat_tl_i64(t2, t1, t0);
4840                 tcg_gen_shri_i64(t2, t2, 32 - bits);
4841                 gen_move_low32(cpu_gpr[rd], t2);
4842             }
4843             break;
4844 #if defined(TARGET_MIPS64)
4845         case 64:
4846             tcg_gen_shli_tl(t0, t0, bits);
4847             tcg_gen_shri_tl(t1, t1, 64 - bits);
4848             tcg_gen_or_tl(cpu_gpr[rd], t1, t0);
4849             break;
4850 #endif
4851         }
4852     }
4853 }
4854 
4855 void gen_align(DisasContext *ctx, int wordsz, int rd, int rs, int rt, int bp)
4856 {
4857     gen_align_bits(ctx, wordsz, rd, rs, rt, bp * 8);
4858 }
4859 
4860 static void gen_bitswap(DisasContext *ctx, int opc, int rd, int rt)
4861 {
4862     TCGv t0;
4863     if (rd == 0) {
4864         /* Treat as NOP. */
4865         return;
4866     }
4867     t0 = tcg_temp_new();
4868     gen_load_gpr(t0, rt);
4869     switch (opc) {
4870     case OPC_BITSWAP:
4871         gen_helper_bitswap(cpu_gpr[rd], t0);
4872         break;
4873 #if defined(TARGET_MIPS64)
4874     case OPC_DBITSWAP:
4875         gen_helper_dbitswap(cpu_gpr[rd], t0);
4876         break;
4877 #endif
4878     }
4879 }
4880 
4881 #ifndef CONFIG_USER_ONLY
4882 /* CP0 (MMU and control) */
4883 static inline void gen_mthc0_entrylo(TCGv arg, target_ulong off)
4884 {
4885     TCGv_i64 t0 = tcg_temp_new_i64();
4886     TCGv_i64 t1 = tcg_temp_new_i64();
4887 
4888     tcg_gen_ext_tl_i64(t0, arg);
4889     tcg_gen_ld_i64(t1, tcg_env, off);
4890 #if defined(TARGET_MIPS64)
4891     tcg_gen_deposit_i64(t1, t1, t0, 30, 32);
4892 #else
4893     tcg_gen_concat32_i64(t1, t1, t0);
4894 #endif
4895     tcg_gen_st_i64(t1, tcg_env, off);
4896 }
4897 
4898 static inline void gen_mthc0_store64(TCGv arg, target_ulong off)
4899 {
4900     TCGv_i64 t0 = tcg_temp_new_i64();
4901     TCGv_i64 t1 = tcg_temp_new_i64();
4902 
4903     tcg_gen_ext_tl_i64(t0, arg);
4904     tcg_gen_ld_i64(t1, tcg_env, off);
4905     tcg_gen_concat32_i64(t1, t1, t0);
4906     tcg_gen_st_i64(t1, tcg_env, off);
4907 }
4908 
4909 static inline void gen_mfhc0_entrylo(TCGv arg, target_ulong off)
4910 {
4911     TCGv_i64 t0 = tcg_temp_new_i64();
4912 
4913     tcg_gen_ld_i64(t0, tcg_env, off);
4914 #if defined(TARGET_MIPS64)
4915     tcg_gen_shri_i64(t0, t0, 30);
4916 #else
4917     tcg_gen_shri_i64(t0, t0, 32);
4918 #endif
4919     gen_move_low32(arg, t0);
4920 }
4921 
4922 static inline void gen_mfhc0_load64(TCGv arg, target_ulong off, int shift)
4923 {
4924     TCGv_i64 t0 = tcg_temp_new_i64();
4925 
4926     tcg_gen_ld_i64(t0, tcg_env, off);
4927     tcg_gen_shri_i64(t0, t0, 32 + shift);
4928     gen_move_low32(arg, t0);
4929 }
4930 
4931 static inline void gen_mfc0_load32(TCGv arg, target_ulong off)
4932 {
4933     TCGv_i32 t0 = tcg_temp_new_i32();
4934 
4935     tcg_gen_ld_i32(t0, tcg_env, off);
4936     tcg_gen_ext_i32_tl(arg, t0);
4937 }
4938 
4939 static inline void gen_mfc0_load64(TCGv arg, target_ulong off)
4940 {
4941     tcg_gen_ld_tl(arg, tcg_env, off);
4942     tcg_gen_ext32s_tl(arg, arg);
4943 }
4944 
4945 static inline void gen_mtc0_store32(TCGv arg, target_ulong off)
4946 {
4947     TCGv_i32 t0 = tcg_temp_new_i32();
4948 
4949     tcg_gen_trunc_tl_i32(t0, arg);
4950     tcg_gen_st_i32(t0, tcg_env, off);
4951 }
4952 
4953 #define CP0_CHECK(c)                            \
4954     do {                                        \
4955         if (!(c)) {                             \
4956             goto cp0_unimplemented;             \
4957         }                                       \
4958     } while (0)
4959 
4960 static void gen_mfhc0(DisasContext *ctx, TCGv arg, int reg, int sel)
4961 {
4962     const char *register_name = "invalid";
4963 
4964     switch (reg) {
4965     case CP0_REGISTER_02:
4966         switch (sel) {
4967         case 0:
4968             CP0_CHECK(ctx->hflags & MIPS_HFLAG_ELPA);
4969             gen_mfhc0_entrylo(arg, offsetof(CPUMIPSState, CP0_EntryLo0));
4970             register_name = "EntryLo0";
4971             break;
4972         default:
4973             goto cp0_unimplemented;
4974         }
4975         break;
4976     case CP0_REGISTER_03:
4977         switch (sel) {
4978         case CP0_REG03__ENTRYLO1:
4979             CP0_CHECK(ctx->hflags & MIPS_HFLAG_ELPA);
4980             gen_mfhc0_entrylo(arg, offsetof(CPUMIPSState, CP0_EntryLo1));
4981             register_name = "EntryLo1";
4982             break;
4983         default:
4984             goto cp0_unimplemented;
4985         }
4986         break;
4987     case CP0_REGISTER_17:
4988         switch (sel) {
4989         case CP0_REG17__LLADDR:
4990             gen_mfhc0_load64(arg, offsetof(CPUMIPSState, CP0_LLAddr),
4991                              ctx->CP0_LLAddr_shift);
4992             register_name = "LLAddr";
4993             break;
4994         case CP0_REG17__MAAR:
4995             CP0_CHECK(ctx->mrp);
4996             gen_helper_mfhc0_maar(arg, tcg_env);
4997             register_name = "MAAR";
4998             break;
4999         default:
5000             goto cp0_unimplemented;
5001         }
5002         break;
5003     case CP0_REGISTER_19:
5004         switch (sel) {
5005         case CP0_REG19__WATCHHI0:
5006         case CP0_REG19__WATCHHI1:
5007         case CP0_REG19__WATCHHI2:
5008         case CP0_REG19__WATCHHI3:
5009         case CP0_REG19__WATCHHI4:
5010         case CP0_REG19__WATCHHI5:
5011         case CP0_REG19__WATCHHI6:
5012         case CP0_REG19__WATCHHI7:
5013             /* upper 32 bits are only available when Config5MI != 0 */
5014             CP0_CHECK(ctx->mi);
5015             gen_mfhc0_load64(arg, offsetof(CPUMIPSState, CP0_WatchHi[sel]), 0);
5016             register_name = "WatchHi";
5017             break;
5018         default:
5019             goto cp0_unimplemented;
5020         }
5021         break;
5022     case CP0_REGISTER_28:
5023         switch (sel) {
5024         case 0:
5025         case 2:
5026         case 4:
5027         case 6:
5028             gen_mfhc0_load64(arg, offsetof(CPUMIPSState, CP0_TagLo), 0);
5029             register_name = "TagLo";
5030             break;
5031         default:
5032             goto cp0_unimplemented;
5033         }
5034         break;
5035     default:
5036         goto cp0_unimplemented;
5037     }
5038     trace_mips_translate_c0("mfhc0", register_name, reg, sel);
5039     return;
5040 
5041 cp0_unimplemented:
5042     qemu_log_mask(LOG_UNIMP, "mfhc0 %s (reg %d sel %d)\n",
5043                   register_name, reg, sel);
5044     tcg_gen_movi_tl(arg, 0);
5045 }
5046 
5047 static void gen_mthc0(DisasContext *ctx, TCGv arg, int reg, int sel)
5048 {
5049     const char *register_name = "invalid";
5050     uint64_t mask = ctx->PAMask >> 36;
5051 
5052     switch (reg) {
5053     case CP0_REGISTER_02:
5054         switch (sel) {
5055         case 0:
5056             CP0_CHECK(ctx->hflags & MIPS_HFLAG_ELPA);
5057             tcg_gen_andi_tl(arg, arg, mask);
5058             gen_mthc0_entrylo(arg, offsetof(CPUMIPSState, CP0_EntryLo0));
5059             register_name = "EntryLo0";
5060             break;
5061         default:
5062             goto cp0_unimplemented;
5063         }
5064         break;
5065     case CP0_REGISTER_03:
5066         switch (sel) {
5067         case CP0_REG03__ENTRYLO1:
5068             CP0_CHECK(ctx->hflags & MIPS_HFLAG_ELPA);
5069             tcg_gen_andi_tl(arg, arg, mask);
5070             gen_mthc0_entrylo(arg, offsetof(CPUMIPSState, CP0_EntryLo1));
5071             register_name = "EntryLo1";
5072             break;
5073         default:
5074             goto cp0_unimplemented;
5075         }
5076         break;
5077     case CP0_REGISTER_17:
5078         switch (sel) {
5079         case CP0_REG17__LLADDR:
5080             /*
5081              * LLAddr is read-only (the only exception is bit 0 if LLB is
5082              * supported); the CP0_LLAddr_rw_bitmask does not seem to be
5083              * relevant for modern MIPS cores supporting MTHC0, therefore
5084              * treating MTHC0 to LLAddr as NOP.
5085              */
5086             register_name = "LLAddr";
5087             break;
5088         case CP0_REG17__MAAR:
5089             CP0_CHECK(ctx->mrp);
5090             gen_helper_mthc0_maar(tcg_env, arg);
5091             register_name = "MAAR";
5092             break;
5093         default:
5094             goto cp0_unimplemented;
5095         }
5096         break;
5097     case CP0_REGISTER_19:
5098         switch (sel) {
5099         case CP0_REG19__WATCHHI0:
5100         case CP0_REG19__WATCHHI1:
5101         case CP0_REG19__WATCHHI2:
5102         case CP0_REG19__WATCHHI3:
5103         case CP0_REG19__WATCHHI4:
5104         case CP0_REG19__WATCHHI5:
5105         case CP0_REG19__WATCHHI6:
5106         case CP0_REG19__WATCHHI7:
5107             /* upper 32 bits are only available when Config5MI != 0 */
5108             CP0_CHECK(ctx->mi);
5109             gen_helper_0e1i(mthc0_watchhi, arg, sel);
5110             register_name = "WatchHi";
5111             break;
5112         default:
5113             goto cp0_unimplemented;
5114         }
5115         break;
5116     case CP0_REGISTER_28:
5117         switch (sel) {
5118         case 0:
5119         case 2:
5120         case 4:
5121         case 6:
5122             tcg_gen_andi_tl(arg, arg, mask);
5123             gen_mthc0_store64(arg, offsetof(CPUMIPSState, CP0_TagLo));
5124             register_name = "TagLo";
5125             break;
5126         default:
5127             goto cp0_unimplemented;
5128         }
5129         break;
5130     default:
5131         goto cp0_unimplemented;
5132     }
5133     trace_mips_translate_c0("mthc0", register_name, reg, sel);
5134     return;
5135 
5136 cp0_unimplemented:
5137     qemu_log_mask(LOG_UNIMP, "mthc0 %s (reg %d sel %d)\n",
5138                   register_name, reg, sel);
5139 }
5140 
5141 static inline void gen_mfc0_unimplemented(DisasContext *ctx, TCGv arg)
5142 {
5143     if (ctx->insn_flags & ISA_MIPS_R6) {
5144         tcg_gen_movi_tl(arg, 0);
5145     } else {
5146         tcg_gen_movi_tl(arg, ~0);
5147     }
5148 }
5149 
5150 static void gen_mfc0(DisasContext *ctx, TCGv arg, int reg, int sel)
5151 {
5152     const char *register_name = "invalid";
5153 
5154     if (sel != 0) {
5155         check_insn(ctx, ISA_MIPS_R1);
5156     }
5157 
5158     switch (reg) {
5159     case CP0_REGISTER_00:
5160         switch (sel) {
5161         case CP0_REG00__INDEX:
5162             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Index));
5163             register_name = "Index";
5164             break;
5165         case CP0_REG00__MVPCONTROL:
5166             CP0_CHECK(ctx->insn_flags & ASE_MT);
5167             gen_helper_mfc0_mvpcontrol(arg, tcg_env);
5168             register_name = "MVPControl";
5169             break;
5170         case CP0_REG00__MVPCONF0:
5171             CP0_CHECK(ctx->insn_flags & ASE_MT);
5172             gen_helper_mfc0_mvpconf0(arg, tcg_env);
5173             register_name = "MVPConf0";
5174             break;
5175         case CP0_REG00__MVPCONF1:
5176             CP0_CHECK(ctx->insn_flags & ASE_MT);
5177             gen_helper_mfc0_mvpconf1(arg, tcg_env);
5178             register_name = "MVPConf1";
5179             break;
5180         case CP0_REG00__VPCONTROL:
5181             CP0_CHECK(ctx->vp);
5182             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPControl));
5183             register_name = "VPControl";
5184             break;
5185         default:
5186             goto cp0_unimplemented;
5187         }
5188         break;
5189     case CP0_REGISTER_01:
5190         switch (sel) {
5191         case CP0_REG01__RANDOM:
5192             CP0_CHECK(!(ctx->insn_flags & ISA_MIPS_R6));
5193             gen_helper_mfc0_random(arg, tcg_env);
5194             register_name = "Random";
5195             break;
5196         case CP0_REG01__VPECONTROL:
5197             CP0_CHECK(ctx->insn_flags & ASE_MT);
5198             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEControl));
5199             register_name = "VPEControl";
5200             break;
5201         case CP0_REG01__VPECONF0:
5202             CP0_CHECK(ctx->insn_flags & ASE_MT);
5203             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEConf0));
5204             register_name = "VPEConf0";
5205             break;
5206         case CP0_REG01__VPECONF1:
5207             CP0_CHECK(ctx->insn_flags & ASE_MT);
5208             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEConf1));
5209             register_name = "VPEConf1";
5210             break;
5211         case CP0_REG01__YQMASK:
5212             CP0_CHECK(ctx->insn_flags & ASE_MT);
5213             gen_mfc0_load64(arg, offsetof(CPUMIPSState, CP0_YQMask));
5214             register_name = "YQMask";
5215             break;
5216         case CP0_REG01__VPESCHEDULE:
5217             CP0_CHECK(ctx->insn_flags & ASE_MT);
5218             gen_mfc0_load64(arg, offsetof(CPUMIPSState, CP0_VPESchedule));
5219             register_name = "VPESchedule";
5220             break;
5221         case CP0_REG01__VPESCHEFBACK:
5222             CP0_CHECK(ctx->insn_flags & ASE_MT);
5223             gen_mfc0_load64(arg, offsetof(CPUMIPSState, CP0_VPEScheFBack));
5224             register_name = "VPEScheFBack";
5225             break;
5226         case CP0_REG01__VPEOPT:
5227             CP0_CHECK(ctx->insn_flags & ASE_MT);
5228             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEOpt));
5229             register_name = "VPEOpt";
5230             break;
5231         default:
5232             goto cp0_unimplemented;
5233         }
5234         break;
5235     case CP0_REGISTER_02:
5236         switch (sel) {
5237         case CP0_REG02__ENTRYLO0:
5238             {
5239                 TCGv_i64 tmp = tcg_temp_new_i64();
5240                 tcg_gen_ld_i64(tmp, tcg_env,
5241                                offsetof(CPUMIPSState, CP0_EntryLo0));
5242 #if defined(TARGET_MIPS64)
5243                 if (ctx->rxi) {
5244                     /* Move RI/XI fields to bits 31:30 */
5245                     tcg_gen_shri_tl(arg, tmp, CP0EnLo_XI);
5246                     tcg_gen_deposit_tl(tmp, tmp, arg, 30, 2);
5247                 }
5248 #endif
5249                 gen_move_low32(arg, tmp);
5250             }
5251             register_name = "EntryLo0";
5252             break;
5253         case CP0_REG02__TCSTATUS:
5254             CP0_CHECK(ctx->insn_flags & ASE_MT);
5255             gen_helper_mfc0_tcstatus(arg, tcg_env);
5256             register_name = "TCStatus";
5257             break;
5258         case CP0_REG02__TCBIND:
5259             CP0_CHECK(ctx->insn_flags & ASE_MT);
5260             gen_helper_mfc0_tcbind(arg, tcg_env);
5261             register_name = "TCBind";
5262             break;
5263         case CP0_REG02__TCRESTART:
5264             CP0_CHECK(ctx->insn_flags & ASE_MT);
5265             gen_helper_mfc0_tcrestart(arg, tcg_env);
5266             register_name = "TCRestart";
5267             break;
5268         case CP0_REG02__TCHALT:
5269             CP0_CHECK(ctx->insn_flags & ASE_MT);
5270             gen_helper_mfc0_tchalt(arg, tcg_env);
5271             register_name = "TCHalt";
5272             break;
5273         case CP0_REG02__TCCONTEXT:
5274             CP0_CHECK(ctx->insn_flags & ASE_MT);
5275             gen_helper_mfc0_tccontext(arg, tcg_env);
5276             register_name = "TCContext";
5277             break;
5278         case CP0_REG02__TCSCHEDULE:
5279             CP0_CHECK(ctx->insn_flags & ASE_MT);
5280             gen_helper_mfc0_tcschedule(arg, tcg_env);
5281             register_name = "TCSchedule";
5282             break;
5283         case CP0_REG02__TCSCHEFBACK:
5284             CP0_CHECK(ctx->insn_flags & ASE_MT);
5285             gen_helper_mfc0_tcschefback(arg, tcg_env);
5286             register_name = "TCScheFBack";
5287             break;
5288         default:
5289             goto cp0_unimplemented;
5290         }
5291         break;
5292     case CP0_REGISTER_03:
5293         switch (sel) {
5294         case CP0_REG03__ENTRYLO1:
5295             {
5296                 TCGv_i64 tmp = tcg_temp_new_i64();
5297                 tcg_gen_ld_i64(tmp, tcg_env,
5298                                offsetof(CPUMIPSState, CP0_EntryLo1));
5299 #if defined(TARGET_MIPS64)
5300                 if (ctx->rxi) {
5301                     /* Move RI/XI fields to bits 31:30 */
5302                     tcg_gen_shri_tl(arg, tmp, CP0EnLo_XI);
5303                     tcg_gen_deposit_tl(tmp, tmp, arg, 30, 2);
5304                 }
5305 #endif
5306                 gen_move_low32(arg, tmp);
5307             }
5308             register_name = "EntryLo1";
5309             break;
5310         case CP0_REG03__GLOBALNUM:
5311             CP0_CHECK(ctx->vp);
5312             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_GlobalNumber));
5313             register_name = "GlobalNumber";
5314             break;
5315         default:
5316             goto cp0_unimplemented;
5317         }
5318         break;
5319     case CP0_REGISTER_04:
5320         switch (sel) {
5321         case CP0_REG04__CONTEXT:
5322             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_Context));
5323             tcg_gen_ext32s_tl(arg, arg);
5324             register_name = "Context";
5325             break;
5326         case CP0_REG04__CONTEXTCONFIG:
5327             /* SmartMIPS ASE */
5328             /* gen_helper_mfc0_contextconfig(arg); */
5329             register_name = "ContextConfig";
5330             goto cp0_unimplemented;
5331         case CP0_REG04__USERLOCAL:
5332             CP0_CHECK(ctx->ulri);
5333             tcg_gen_ld_tl(arg, tcg_env,
5334                           offsetof(CPUMIPSState, active_tc.CP0_UserLocal));
5335             tcg_gen_ext32s_tl(arg, arg);
5336             register_name = "UserLocal";
5337             break;
5338         case CP0_REG04__MMID:
5339             CP0_CHECK(ctx->mi);
5340             gen_helper_mtc0_memorymapid(tcg_env, arg);
5341             register_name = "MMID";
5342             break;
5343         default:
5344             goto cp0_unimplemented;
5345         }
5346         break;
5347     case CP0_REGISTER_05:
5348         switch (sel) {
5349         case CP0_REG05__PAGEMASK:
5350             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PageMask));
5351             register_name = "PageMask";
5352             break;
5353         case CP0_REG05__PAGEGRAIN:
5354             check_insn(ctx, ISA_MIPS_R2);
5355             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PageGrain));
5356             register_name = "PageGrain";
5357             break;
5358         case CP0_REG05__SEGCTL0:
5359             CP0_CHECK(ctx->sc);
5360             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_SegCtl0));
5361             tcg_gen_ext32s_tl(arg, arg);
5362             register_name = "SegCtl0";
5363             break;
5364         case CP0_REG05__SEGCTL1:
5365             CP0_CHECK(ctx->sc);
5366             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_SegCtl1));
5367             tcg_gen_ext32s_tl(arg, arg);
5368             register_name = "SegCtl1";
5369             break;
5370         case CP0_REG05__SEGCTL2:
5371             CP0_CHECK(ctx->sc);
5372             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_SegCtl2));
5373             tcg_gen_ext32s_tl(arg, arg);
5374             register_name = "SegCtl2";
5375             break;
5376         case CP0_REG05__PWBASE:
5377             check_pw(ctx);
5378             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PWBase));
5379             register_name = "PWBase";
5380             break;
5381         case CP0_REG05__PWFIELD:
5382             check_pw(ctx);
5383             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PWField));
5384             register_name = "PWField";
5385             break;
5386         case CP0_REG05__PWSIZE:
5387             check_pw(ctx);
5388             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PWSize));
5389             register_name = "PWSize";
5390             break;
5391         default:
5392             goto cp0_unimplemented;
5393         }
5394         break;
5395     case CP0_REGISTER_06:
5396         switch (sel) {
5397         case CP0_REG06__WIRED:
5398             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Wired));
5399             register_name = "Wired";
5400             break;
5401         case CP0_REG06__SRSCONF0:
5402             check_insn(ctx, ISA_MIPS_R2);
5403             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf0));
5404             register_name = "SRSConf0";
5405             break;
5406         case CP0_REG06__SRSCONF1:
5407             check_insn(ctx, ISA_MIPS_R2);
5408             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf1));
5409             register_name = "SRSConf1";
5410             break;
5411         case CP0_REG06__SRSCONF2:
5412             check_insn(ctx, ISA_MIPS_R2);
5413             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf2));
5414             register_name = "SRSConf2";
5415             break;
5416         case CP0_REG06__SRSCONF3:
5417             check_insn(ctx, ISA_MIPS_R2);
5418             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf3));
5419             register_name = "SRSConf3";
5420             break;
5421         case CP0_REG06__SRSCONF4:
5422             check_insn(ctx, ISA_MIPS_R2);
5423             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf4));
5424             register_name = "SRSConf4";
5425             break;
5426         case CP0_REG06__PWCTL:
5427             check_pw(ctx);
5428             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PWCtl));
5429             register_name = "PWCtl";
5430             break;
5431         default:
5432             goto cp0_unimplemented;
5433         }
5434         break;
5435     case CP0_REGISTER_07:
5436         switch (sel) {
5437         case CP0_REG07__HWRENA:
5438             check_insn(ctx, ISA_MIPS_R2);
5439             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_HWREna));
5440             register_name = "HWREna";
5441             break;
5442         default:
5443             goto cp0_unimplemented;
5444         }
5445         break;
5446     case CP0_REGISTER_08:
5447         switch (sel) {
5448         case CP0_REG08__BADVADDR:
5449             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_BadVAddr));
5450             tcg_gen_ext32s_tl(arg, arg);
5451             register_name = "BadVAddr";
5452             break;
5453         case CP0_REG08__BADINSTR:
5454             CP0_CHECK(ctx->bi);
5455             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_BadInstr));
5456             register_name = "BadInstr";
5457             break;
5458         case CP0_REG08__BADINSTRP:
5459             CP0_CHECK(ctx->bp);
5460             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_BadInstrP));
5461             register_name = "BadInstrP";
5462             break;
5463         case CP0_REG08__BADINSTRX:
5464             CP0_CHECK(ctx->bi);
5465             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_BadInstrX));
5466             tcg_gen_andi_tl(arg, arg, ~0xffff);
5467             register_name = "BadInstrX";
5468             break;
5469         default:
5470             goto cp0_unimplemented;
5471         }
5472         break;
5473     case CP0_REGISTER_09:
5474         switch (sel) {
5475         case CP0_REG09__COUNT:
5476             /* Mark as an IO operation because we read the time.  */
5477             translator_io_start(&ctx->base);
5478 
5479             gen_helper_mfc0_count(arg, tcg_env);
5480             /*
5481              * Break the TB to be able to take timer interrupts immediately
5482              * after reading count. DISAS_STOP isn't sufficient, we need to
5483              * ensure we break completely out of translated code.
5484              */
5485             gen_save_pc(ctx->base.pc_next + 4);
5486             ctx->base.is_jmp = DISAS_EXIT;
5487             register_name = "Count";
5488             break;
5489         default:
5490             goto cp0_unimplemented;
5491         }
5492         break;
5493     case CP0_REGISTER_10:
5494         switch (sel) {
5495         case CP0_REG10__ENTRYHI:
5496             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_EntryHi));
5497             tcg_gen_ext32s_tl(arg, arg);
5498             register_name = "EntryHi";
5499             break;
5500         default:
5501             goto cp0_unimplemented;
5502         }
5503         break;
5504     case CP0_REGISTER_11:
5505         switch (sel) {
5506         case CP0_REG11__COMPARE:
5507             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Compare));
5508             register_name = "Compare";
5509             break;
5510         /* 6,7 are implementation dependent */
5511         default:
5512             goto cp0_unimplemented;
5513         }
5514         break;
5515     case CP0_REGISTER_12:
5516         switch (sel) {
5517         case CP0_REG12__STATUS:
5518             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Status));
5519             register_name = "Status";
5520             break;
5521         case CP0_REG12__INTCTL:
5522             check_insn(ctx, ISA_MIPS_R2);
5523             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_IntCtl));
5524             register_name = "IntCtl";
5525             break;
5526         case CP0_REG12__SRSCTL:
5527             check_insn(ctx, ISA_MIPS_R2);
5528             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSCtl));
5529             register_name = "SRSCtl";
5530             break;
5531         case CP0_REG12__SRSMAP:
5532             check_insn(ctx, ISA_MIPS_R2);
5533             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSMap));
5534             register_name = "SRSMap";
5535             break;
5536         default:
5537             goto cp0_unimplemented;
5538        }
5539         break;
5540     case CP0_REGISTER_13:
5541         switch (sel) {
5542         case CP0_REG13__CAUSE:
5543             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Cause));
5544             register_name = "Cause";
5545             break;
5546         default:
5547             goto cp0_unimplemented;
5548        }
5549         break;
5550     case CP0_REGISTER_14:
5551         switch (sel) {
5552         case CP0_REG14__EPC:
5553             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_EPC));
5554             tcg_gen_ext32s_tl(arg, arg);
5555             register_name = "EPC";
5556             break;
5557         default:
5558             goto cp0_unimplemented;
5559         }
5560         break;
5561     case CP0_REGISTER_15:
5562         switch (sel) {
5563         case CP0_REG15__PRID:
5564             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PRid));
5565             register_name = "PRid";
5566             break;
5567         case CP0_REG15__EBASE:
5568             check_insn(ctx, ISA_MIPS_R2);
5569             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_EBase));
5570             tcg_gen_ext32s_tl(arg, arg);
5571             register_name = "EBase";
5572             break;
5573         case CP0_REG15__CMGCRBASE:
5574             check_insn(ctx, ISA_MIPS_R2);
5575             CP0_CHECK(ctx->cmgcr);
5576             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_CMGCRBase));
5577             tcg_gen_ext32s_tl(arg, arg);
5578             register_name = "CMGCRBase";
5579             break;
5580         default:
5581             goto cp0_unimplemented;
5582        }
5583         break;
5584     case CP0_REGISTER_16:
5585         switch (sel) {
5586         case CP0_REG16__CONFIG:
5587             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config0));
5588             register_name = "Config";
5589             break;
5590         case CP0_REG16__CONFIG1:
5591             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config1));
5592             register_name = "Config1";
5593             break;
5594         case CP0_REG16__CONFIG2:
5595             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config2));
5596             register_name = "Config2";
5597             break;
5598         case CP0_REG16__CONFIG3:
5599             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config3));
5600             register_name = "Config3";
5601             break;
5602         case CP0_REG16__CONFIG4:
5603             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config4));
5604             register_name = "Config4";
5605             break;
5606         case CP0_REG16__CONFIG5:
5607             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config5));
5608             register_name = "Config5";
5609             break;
5610         /* 6,7 are implementation dependent */
5611         case CP0_REG16__CONFIG6:
5612             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config6));
5613             register_name = "Config6";
5614             break;
5615         case CP0_REG16__CONFIG7:
5616             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config7));
5617             register_name = "Config7";
5618             break;
5619         default:
5620             goto cp0_unimplemented;
5621         }
5622         break;
5623     case CP0_REGISTER_17:
5624         switch (sel) {
5625         case CP0_REG17__LLADDR:
5626             gen_helper_mfc0_lladdr(arg, tcg_env);
5627             register_name = "LLAddr";
5628             break;
5629         case CP0_REG17__MAAR:
5630             CP0_CHECK(ctx->mrp);
5631             gen_helper_mfc0_maar(arg, tcg_env);
5632             register_name = "MAAR";
5633             break;
5634         case CP0_REG17__MAARI:
5635             CP0_CHECK(ctx->mrp);
5636             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_MAARI));
5637             register_name = "MAARI";
5638             break;
5639         default:
5640             goto cp0_unimplemented;
5641         }
5642         break;
5643     case CP0_REGISTER_18:
5644         switch (sel) {
5645         case CP0_REG18__WATCHLO0:
5646         case CP0_REG18__WATCHLO1:
5647         case CP0_REG18__WATCHLO2:
5648         case CP0_REG18__WATCHLO3:
5649         case CP0_REG18__WATCHLO4:
5650         case CP0_REG18__WATCHLO5:
5651         case CP0_REG18__WATCHLO6:
5652         case CP0_REG18__WATCHLO7:
5653             CP0_CHECK(ctx->CP0_Config1 & (1 << CP0C1_WR));
5654             gen_helper_1e0i(mfc0_watchlo, arg, sel);
5655             register_name = "WatchLo";
5656             break;
5657         default:
5658             goto cp0_unimplemented;
5659         }
5660         break;
5661     case CP0_REGISTER_19:
5662         switch (sel) {
5663         case CP0_REG19__WATCHHI0:
5664         case CP0_REG19__WATCHHI1:
5665         case CP0_REG19__WATCHHI2:
5666         case CP0_REG19__WATCHHI3:
5667         case CP0_REG19__WATCHHI4:
5668         case CP0_REG19__WATCHHI5:
5669         case CP0_REG19__WATCHHI6:
5670         case CP0_REG19__WATCHHI7:
5671             CP0_CHECK(ctx->CP0_Config1 & (1 << CP0C1_WR));
5672             gen_helper_1e0i(mfc0_watchhi, arg, sel);
5673             register_name = "WatchHi";
5674             break;
5675         default:
5676             goto cp0_unimplemented;
5677         }
5678         break;
5679     case CP0_REGISTER_20:
5680         switch (sel) {
5681         case CP0_REG20__XCONTEXT:
5682 #if defined(TARGET_MIPS64)
5683             check_insn(ctx, ISA_MIPS3);
5684             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_XContext));
5685             tcg_gen_ext32s_tl(arg, arg);
5686             register_name = "XContext";
5687             break;
5688 #endif
5689         default:
5690             goto cp0_unimplemented;
5691         }
5692         break;
5693     case CP0_REGISTER_21:
5694        /* Officially reserved, but sel 0 is used for R1x000 framemask */
5695         CP0_CHECK(!(ctx->insn_flags & ISA_MIPS_R6));
5696         switch (sel) {
5697         case 0:
5698             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Framemask));
5699             register_name = "Framemask";
5700             break;
5701         default:
5702             goto cp0_unimplemented;
5703         }
5704         break;
5705     case CP0_REGISTER_22:
5706         tcg_gen_movi_tl(arg, 0); /* unimplemented */
5707         register_name = "'Diagnostic"; /* implementation dependent */
5708         break;
5709     case CP0_REGISTER_23:
5710         switch (sel) {
5711         case CP0_REG23__DEBUG:
5712             gen_helper_mfc0_debug(arg, tcg_env); /* EJTAG support */
5713             register_name = "Debug";
5714             break;
5715         case CP0_REG23__TRACECONTROL:
5716             /* PDtrace support */
5717             /* gen_helper_mfc0_tracecontrol(arg);  */
5718             register_name = "TraceControl";
5719             goto cp0_unimplemented;
5720         case CP0_REG23__TRACECONTROL2:
5721             /* PDtrace support */
5722             /* gen_helper_mfc0_tracecontrol2(arg); */
5723             register_name = "TraceControl2";
5724             goto cp0_unimplemented;
5725         case CP0_REG23__USERTRACEDATA1:
5726             /* PDtrace support */
5727             /* gen_helper_mfc0_usertracedata1(arg);*/
5728             register_name = "UserTraceData1";
5729             goto cp0_unimplemented;
5730         case CP0_REG23__TRACEIBPC:
5731             /* PDtrace support */
5732             /* gen_helper_mfc0_traceibpc(arg);     */
5733             register_name = "TraceIBPC";
5734             goto cp0_unimplemented;
5735         case CP0_REG23__TRACEDBPC:
5736             /* PDtrace support */
5737             /* gen_helper_mfc0_tracedbpc(arg);     */
5738             register_name = "TraceDBPC";
5739             goto cp0_unimplemented;
5740         default:
5741             goto cp0_unimplemented;
5742         }
5743         break;
5744     case CP0_REGISTER_24:
5745         switch (sel) {
5746         case CP0_REG24__DEPC:
5747             /* EJTAG support */
5748             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_DEPC));
5749             tcg_gen_ext32s_tl(arg, arg);
5750             register_name = "DEPC";
5751             break;
5752         default:
5753             goto cp0_unimplemented;
5754         }
5755         break;
5756     case CP0_REGISTER_25:
5757         switch (sel) {
5758         case CP0_REG25__PERFCTL0:
5759             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Performance0));
5760             register_name = "Performance0";
5761             break;
5762         case CP0_REG25__PERFCNT0:
5763             /* gen_helper_mfc0_performance1(arg); */
5764             register_name = "Performance1";
5765             goto cp0_unimplemented;
5766         case CP0_REG25__PERFCTL1:
5767             /* gen_helper_mfc0_performance2(arg); */
5768             register_name = "Performance2";
5769             goto cp0_unimplemented;
5770         case CP0_REG25__PERFCNT1:
5771             /* gen_helper_mfc0_performance3(arg); */
5772             register_name = "Performance3";
5773             goto cp0_unimplemented;
5774         case CP0_REG25__PERFCTL2:
5775             /* gen_helper_mfc0_performance4(arg); */
5776             register_name = "Performance4";
5777             goto cp0_unimplemented;
5778         case CP0_REG25__PERFCNT2:
5779             /* gen_helper_mfc0_performance5(arg); */
5780             register_name = "Performance5";
5781             goto cp0_unimplemented;
5782         case CP0_REG25__PERFCTL3:
5783             /* gen_helper_mfc0_performance6(arg); */
5784             register_name = "Performance6";
5785             goto cp0_unimplemented;
5786         case CP0_REG25__PERFCNT3:
5787             /* gen_helper_mfc0_performance7(arg); */
5788             register_name = "Performance7";
5789             goto cp0_unimplemented;
5790         default:
5791             goto cp0_unimplemented;
5792         }
5793         break;
5794     case CP0_REGISTER_26:
5795         switch (sel) {
5796         case CP0_REG26__ERRCTL:
5797             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_ErrCtl));
5798             register_name = "ErrCtl";
5799             break;
5800         default:
5801             goto cp0_unimplemented;
5802         }
5803         break;
5804     case CP0_REGISTER_27:
5805         switch (sel) {
5806         case CP0_REG27__CACHERR:
5807             tcg_gen_movi_tl(arg, 0); /* unimplemented */
5808             register_name = "CacheErr";
5809             break;
5810         default:
5811             goto cp0_unimplemented;
5812         }
5813         break;
5814     case CP0_REGISTER_28:
5815         switch (sel) {
5816         case CP0_REG28__TAGLO:
5817         case CP0_REG28__TAGLO1:
5818         case CP0_REG28__TAGLO2:
5819         case CP0_REG28__TAGLO3:
5820             {
5821                 TCGv_i64 tmp = tcg_temp_new_i64();
5822                 tcg_gen_ld_i64(tmp, tcg_env, offsetof(CPUMIPSState, CP0_TagLo));
5823                 gen_move_low32(arg, tmp);
5824             }
5825             register_name = "TagLo";
5826             break;
5827         case CP0_REG28__DATALO:
5828         case CP0_REG28__DATALO1:
5829         case CP0_REG28__DATALO2:
5830         case CP0_REG28__DATALO3:
5831             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DataLo));
5832             register_name = "DataLo";
5833             break;
5834         default:
5835             goto cp0_unimplemented;
5836         }
5837         break;
5838     case CP0_REGISTER_29:
5839         switch (sel) {
5840         case CP0_REG29__TAGHI:
5841         case CP0_REG29__TAGHI1:
5842         case CP0_REG29__TAGHI2:
5843         case CP0_REG29__TAGHI3:
5844             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_TagHi));
5845             register_name = "TagHi";
5846             break;
5847         case CP0_REG29__DATAHI:
5848         case CP0_REG29__DATAHI1:
5849         case CP0_REG29__DATAHI2:
5850         case CP0_REG29__DATAHI3:
5851             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DataHi));
5852             register_name = "DataHi";
5853             break;
5854         default:
5855             goto cp0_unimplemented;
5856         }
5857         break;
5858     case CP0_REGISTER_30:
5859         switch (sel) {
5860         case CP0_REG30__ERROREPC:
5861             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_ErrorEPC));
5862             tcg_gen_ext32s_tl(arg, arg);
5863             register_name = "ErrorEPC";
5864             break;
5865         default:
5866             goto cp0_unimplemented;
5867         }
5868         break;
5869     case CP0_REGISTER_31:
5870         switch (sel) {
5871         case CP0_REG31__DESAVE:
5872             /* EJTAG support */
5873             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DESAVE));
5874             register_name = "DESAVE";
5875             break;
5876         case CP0_REG31__KSCRATCH1:
5877         case CP0_REG31__KSCRATCH2:
5878         case CP0_REG31__KSCRATCH3:
5879         case CP0_REG31__KSCRATCH4:
5880         case CP0_REG31__KSCRATCH5:
5881         case CP0_REG31__KSCRATCH6:
5882             CP0_CHECK(ctx->kscrexist & (1 << sel));
5883             tcg_gen_ld_tl(arg, tcg_env,
5884                           offsetof(CPUMIPSState, CP0_KScratch[sel - 2]));
5885             tcg_gen_ext32s_tl(arg, arg);
5886             register_name = "KScratch";
5887             break;
5888         default:
5889             goto cp0_unimplemented;
5890         }
5891         break;
5892     default:
5893        goto cp0_unimplemented;
5894     }
5895     trace_mips_translate_c0("mfc0", register_name, reg, sel);
5896     return;
5897 
5898 cp0_unimplemented:
5899     qemu_log_mask(LOG_UNIMP, "mfc0 %s (reg %d sel %d)\n",
5900                   register_name, reg, sel);
5901     gen_mfc0_unimplemented(ctx, arg);
5902 }
5903 
5904 static void gen_mtc0(DisasContext *ctx, TCGv arg, int reg, int sel)
5905 {
5906     const char *register_name = "invalid";
5907     bool icount;
5908 
5909     if (sel != 0) {
5910         check_insn(ctx, ISA_MIPS_R1);
5911     }
5912 
5913     icount = translator_io_start(&ctx->base);
5914 
5915     switch (reg) {
5916     case CP0_REGISTER_00:
5917         switch (sel) {
5918         case CP0_REG00__INDEX:
5919             gen_helper_mtc0_index(tcg_env, arg);
5920             register_name = "Index";
5921             break;
5922         case CP0_REG00__MVPCONTROL:
5923             CP0_CHECK(ctx->insn_flags & ASE_MT);
5924             gen_helper_mtc0_mvpcontrol(tcg_env, arg);
5925             register_name = "MVPControl";
5926             break;
5927         case CP0_REG00__MVPCONF0:
5928             CP0_CHECK(ctx->insn_flags & ASE_MT);
5929             /* ignored */
5930             register_name = "MVPConf0";
5931             break;
5932         case CP0_REG00__MVPCONF1:
5933             CP0_CHECK(ctx->insn_flags & ASE_MT);
5934             /* ignored */
5935             register_name = "MVPConf1";
5936             break;
5937         case CP0_REG00__VPCONTROL:
5938             CP0_CHECK(ctx->vp);
5939             /* ignored */
5940             register_name = "VPControl";
5941             break;
5942         default:
5943             goto cp0_unimplemented;
5944         }
5945         break;
5946     case CP0_REGISTER_01:
5947         switch (sel) {
5948         case CP0_REG01__RANDOM:
5949             /* ignored */
5950             register_name = "Random";
5951             break;
5952         case CP0_REG01__VPECONTROL:
5953             CP0_CHECK(ctx->insn_flags & ASE_MT);
5954             gen_helper_mtc0_vpecontrol(tcg_env, arg);
5955             register_name = "VPEControl";
5956             break;
5957         case CP0_REG01__VPECONF0:
5958             CP0_CHECK(ctx->insn_flags & ASE_MT);
5959             gen_helper_mtc0_vpeconf0(tcg_env, arg);
5960             register_name = "VPEConf0";
5961             break;
5962         case CP0_REG01__VPECONF1:
5963             CP0_CHECK(ctx->insn_flags & ASE_MT);
5964             gen_helper_mtc0_vpeconf1(tcg_env, arg);
5965             register_name = "VPEConf1";
5966             break;
5967         case CP0_REG01__YQMASK:
5968             CP0_CHECK(ctx->insn_flags & ASE_MT);
5969             gen_helper_mtc0_yqmask(tcg_env, arg);
5970             register_name = "YQMask";
5971             break;
5972         case CP0_REG01__VPESCHEDULE:
5973             CP0_CHECK(ctx->insn_flags & ASE_MT);
5974             tcg_gen_st_tl(arg, tcg_env,
5975                           offsetof(CPUMIPSState, CP0_VPESchedule));
5976             register_name = "VPESchedule";
5977             break;
5978         case CP0_REG01__VPESCHEFBACK:
5979             CP0_CHECK(ctx->insn_flags & ASE_MT);
5980             tcg_gen_st_tl(arg, tcg_env,
5981                           offsetof(CPUMIPSState, CP0_VPEScheFBack));
5982             register_name = "VPEScheFBack";
5983             break;
5984         case CP0_REG01__VPEOPT:
5985             CP0_CHECK(ctx->insn_flags & ASE_MT);
5986             gen_helper_mtc0_vpeopt(tcg_env, arg);
5987             register_name = "VPEOpt";
5988             break;
5989         default:
5990             goto cp0_unimplemented;
5991         }
5992         break;
5993     case CP0_REGISTER_02:
5994         switch (sel) {
5995         case CP0_REG02__ENTRYLO0:
5996             gen_helper_mtc0_entrylo0(tcg_env, arg);
5997             register_name = "EntryLo0";
5998             break;
5999         case CP0_REG02__TCSTATUS:
6000             CP0_CHECK(ctx->insn_flags & ASE_MT);
6001             gen_helper_mtc0_tcstatus(tcg_env, arg);
6002             register_name = "TCStatus";
6003             break;
6004         case CP0_REG02__TCBIND:
6005             CP0_CHECK(ctx->insn_flags & ASE_MT);
6006             gen_helper_mtc0_tcbind(tcg_env, arg);
6007             register_name = "TCBind";
6008             break;
6009         case CP0_REG02__TCRESTART:
6010             CP0_CHECK(ctx->insn_flags & ASE_MT);
6011             gen_helper_mtc0_tcrestart(tcg_env, arg);
6012             register_name = "TCRestart";
6013             break;
6014         case CP0_REG02__TCHALT:
6015             CP0_CHECK(ctx->insn_flags & ASE_MT);
6016             gen_helper_mtc0_tchalt(tcg_env, arg);
6017             register_name = "TCHalt";
6018             break;
6019         case CP0_REG02__TCCONTEXT:
6020             CP0_CHECK(ctx->insn_flags & ASE_MT);
6021             gen_helper_mtc0_tccontext(tcg_env, arg);
6022             register_name = "TCContext";
6023             break;
6024         case CP0_REG02__TCSCHEDULE:
6025             CP0_CHECK(ctx->insn_flags & ASE_MT);
6026             gen_helper_mtc0_tcschedule(tcg_env, arg);
6027             register_name = "TCSchedule";
6028             break;
6029         case CP0_REG02__TCSCHEFBACK:
6030             CP0_CHECK(ctx->insn_flags & ASE_MT);
6031             gen_helper_mtc0_tcschefback(tcg_env, arg);
6032             register_name = "TCScheFBack";
6033             break;
6034         default:
6035             goto cp0_unimplemented;
6036         }
6037         break;
6038     case CP0_REGISTER_03:
6039         switch (sel) {
6040         case CP0_REG03__ENTRYLO1:
6041             gen_helper_mtc0_entrylo1(tcg_env, arg);
6042             register_name = "EntryLo1";
6043             break;
6044         case CP0_REG03__GLOBALNUM:
6045             CP0_CHECK(ctx->vp);
6046             /* ignored */
6047             register_name = "GlobalNumber";
6048             break;
6049         default:
6050             goto cp0_unimplemented;
6051         }
6052         break;
6053     case CP0_REGISTER_04:
6054         switch (sel) {
6055         case CP0_REG04__CONTEXT:
6056             gen_helper_mtc0_context(tcg_env, arg);
6057             register_name = "Context";
6058             break;
6059         case CP0_REG04__CONTEXTCONFIG:
6060             /* SmartMIPS ASE */
6061             /* gen_helper_mtc0_contextconfig(arg); */
6062             register_name = "ContextConfig";
6063             goto cp0_unimplemented;
6064         case CP0_REG04__USERLOCAL:
6065             CP0_CHECK(ctx->ulri);
6066             tcg_gen_st_tl(arg, tcg_env,
6067                           offsetof(CPUMIPSState, active_tc.CP0_UserLocal));
6068             register_name = "UserLocal";
6069             break;
6070         case CP0_REG04__MMID:
6071             CP0_CHECK(ctx->mi);
6072             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_MemoryMapID));
6073             register_name = "MMID";
6074             break;
6075         default:
6076             goto cp0_unimplemented;
6077         }
6078         break;
6079     case CP0_REGISTER_05:
6080         switch (sel) {
6081         case CP0_REG05__PAGEMASK:
6082             gen_helper_mtc0_pagemask(tcg_env, arg);
6083             register_name = "PageMask";
6084             break;
6085         case CP0_REG05__PAGEGRAIN:
6086             check_insn(ctx, ISA_MIPS_R2);
6087             gen_helper_mtc0_pagegrain(tcg_env, arg);
6088             register_name = "PageGrain";
6089             ctx->base.is_jmp = DISAS_STOP;
6090             break;
6091         case CP0_REG05__SEGCTL0:
6092             CP0_CHECK(ctx->sc);
6093             gen_helper_mtc0_segctl0(tcg_env, arg);
6094             register_name = "SegCtl0";
6095             break;
6096         case CP0_REG05__SEGCTL1:
6097             CP0_CHECK(ctx->sc);
6098             gen_helper_mtc0_segctl1(tcg_env, arg);
6099             register_name = "SegCtl1";
6100             break;
6101         case CP0_REG05__SEGCTL2:
6102             CP0_CHECK(ctx->sc);
6103             gen_helper_mtc0_segctl2(tcg_env, arg);
6104             register_name = "SegCtl2";
6105             break;
6106         case CP0_REG05__PWBASE:
6107             check_pw(ctx);
6108             gen_mtc0_store32(arg, offsetof(CPUMIPSState, CP0_PWBase));
6109             register_name = "PWBase";
6110             break;
6111         case CP0_REG05__PWFIELD:
6112             check_pw(ctx);
6113             gen_helper_mtc0_pwfield(tcg_env, arg);
6114             register_name = "PWField";
6115             break;
6116         case CP0_REG05__PWSIZE:
6117             check_pw(ctx);
6118             gen_helper_mtc0_pwsize(tcg_env, arg);
6119             register_name = "PWSize";
6120             break;
6121         default:
6122             goto cp0_unimplemented;
6123         }
6124         break;
6125     case CP0_REGISTER_06:
6126         switch (sel) {
6127         case CP0_REG06__WIRED:
6128             gen_helper_mtc0_wired(tcg_env, arg);
6129             register_name = "Wired";
6130             break;
6131         case CP0_REG06__SRSCONF0:
6132             check_insn(ctx, ISA_MIPS_R2);
6133             gen_helper_mtc0_srsconf0(tcg_env, arg);
6134             register_name = "SRSConf0";
6135             break;
6136         case CP0_REG06__SRSCONF1:
6137             check_insn(ctx, ISA_MIPS_R2);
6138             gen_helper_mtc0_srsconf1(tcg_env, arg);
6139             register_name = "SRSConf1";
6140             break;
6141         case CP0_REG06__SRSCONF2:
6142             check_insn(ctx, ISA_MIPS_R2);
6143             gen_helper_mtc0_srsconf2(tcg_env, arg);
6144             register_name = "SRSConf2";
6145             break;
6146         case CP0_REG06__SRSCONF3:
6147             check_insn(ctx, ISA_MIPS_R2);
6148             gen_helper_mtc0_srsconf3(tcg_env, arg);
6149             register_name = "SRSConf3";
6150             break;
6151         case CP0_REG06__SRSCONF4:
6152             check_insn(ctx, ISA_MIPS_R2);
6153             gen_helper_mtc0_srsconf4(tcg_env, arg);
6154             register_name = "SRSConf4";
6155             break;
6156         case CP0_REG06__PWCTL:
6157             check_pw(ctx);
6158             gen_helper_mtc0_pwctl(tcg_env, arg);
6159             register_name = "PWCtl";
6160             break;
6161         default:
6162             goto cp0_unimplemented;
6163         }
6164         break;
6165     case CP0_REGISTER_07:
6166         switch (sel) {
6167         case CP0_REG07__HWRENA:
6168             check_insn(ctx, ISA_MIPS_R2);
6169             gen_helper_mtc0_hwrena(tcg_env, arg);
6170             ctx->base.is_jmp = DISAS_STOP;
6171             register_name = "HWREna";
6172             break;
6173         default:
6174             goto cp0_unimplemented;
6175         }
6176         break;
6177     case CP0_REGISTER_08:
6178         switch (sel) {
6179         case CP0_REG08__BADVADDR:
6180             /* ignored */
6181             register_name = "BadVAddr";
6182             break;
6183         case CP0_REG08__BADINSTR:
6184             /* ignored */
6185             register_name = "BadInstr";
6186             break;
6187         case CP0_REG08__BADINSTRP:
6188             /* ignored */
6189             register_name = "BadInstrP";
6190             break;
6191         case CP0_REG08__BADINSTRX:
6192             /* ignored */
6193             register_name = "BadInstrX";
6194             break;
6195         default:
6196             goto cp0_unimplemented;
6197         }
6198         break;
6199     case CP0_REGISTER_09:
6200         switch (sel) {
6201         case CP0_REG09__COUNT:
6202             gen_helper_mtc0_count(tcg_env, arg);
6203             register_name = "Count";
6204             break;
6205         default:
6206             goto cp0_unimplemented;
6207         }
6208         break;
6209     case CP0_REGISTER_10:
6210         switch (sel) {
6211         case CP0_REG10__ENTRYHI:
6212             gen_helper_mtc0_entryhi(tcg_env, arg);
6213             register_name = "EntryHi";
6214             break;
6215         default:
6216             goto cp0_unimplemented;
6217         }
6218         break;
6219     case CP0_REGISTER_11:
6220         switch (sel) {
6221         case CP0_REG11__COMPARE:
6222             gen_helper_mtc0_compare(tcg_env, arg);
6223             register_name = "Compare";
6224             break;
6225         /* 6,7 are implementation dependent */
6226         default:
6227             goto cp0_unimplemented;
6228         }
6229         break;
6230     case CP0_REGISTER_12:
6231         switch (sel) {
6232         case CP0_REG12__STATUS:
6233             save_cpu_state(ctx, 1);
6234             gen_helper_mtc0_status(tcg_env, arg);
6235             /* DISAS_STOP isn't good enough here, hflags may have changed. */
6236             gen_save_pc(ctx->base.pc_next + 4);
6237             ctx->base.is_jmp = DISAS_EXIT;
6238             register_name = "Status";
6239             break;
6240         case CP0_REG12__INTCTL:
6241             check_insn(ctx, ISA_MIPS_R2);
6242             gen_helper_mtc0_intctl(tcg_env, arg);
6243             /* Stop translation as we may have switched the execution mode */
6244             ctx->base.is_jmp = DISAS_STOP;
6245             register_name = "IntCtl";
6246             break;
6247         case CP0_REG12__SRSCTL:
6248             check_insn(ctx, ISA_MIPS_R2);
6249             gen_helper_mtc0_srsctl(tcg_env, arg);
6250             /* Stop translation as we may have switched the execution mode */
6251             ctx->base.is_jmp = DISAS_STOP;
6252             register_name = "SRSCtl";
6253             break;
6254         case CP0_REG12__SRSMAP:
6255             check_insn(ctx, ISA_MIPS_R2);
6256             gen_mtc0_store32(arg, offsetof(CPUMIPSState, CP0_SRSMap));
6257             /* Stop translation as we may have switched the execution mode */
6258             ctx->base.is_jmp = DISAS_STOP;
6259             register_name = "SRSMap";
6260             break;
6261         default:
6262             goto cp0_unimplemented;
6263         }
6264         break;
6265     case CP0_REGISTER_13:
6266         switch (sel) {
6267         case CP0_REG13__CAUSE:
6268             save_cpu_state(ctx, 1);
6269             gen_helper_mtc0_cause(tcg_env, arg);
6270             /*
6271              * Stop translation as we may have triggered an interrupt.
6272              * DISAS_STOP isn't sufficient, we need to ensure we break out of
6273              * translated code to check for pending interrupts.
6274              */
6275             gen_save_pc(ctx->base.pc_next + 4);
6276             ctx->base.is_jmp = DISAS_EXIT;
6277             register_name = "Cause";
6278             break;
6279         default:
6280             goto cp0_unimplemented;
6281         }
6282         break;
6283     case CP0_REGISTER_14:
6284         switch (sel) {
6285         case CP0_REG14__EPC:
6286             tcg_gen_st_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_EPC));
6287             register_name = "EPC";
6288             break;
6289         default:
6290             goto cp0_unimplemented;
6291         }
6292         break;
6293     case CP0_REGISTER_15:
6294         switch (sel) {
6295         case CP0_REG15__PRID:
6296             /* ignored */
6297             register_name = "PRid";
6298             break;
6299         case CP0_REG15__EBASE:
6300             check_insn(ctx, ISA_MIPS_R2);
6301             gen_helper_mtc0_ebase(tcg_env, arg);
6302             register_name = "EBase";
6303             break;
6304         default:
6305             goto cp0_unimplemented;
6306         }
6307         break;
6308     case CP0_REGISTER_16:
6309         switch (sel) {
6310         case CP0_REG16__CONFIG:
6311             gen_helper_mtc0_config0(tcg_env, arg);
6312             register_name = "Config";
6313             /* Stop translation as we may have switched the execution mode */
6314             ctx->base.is_jmp = DISAS_STOP;
6315             break;
6316         case CP0_REG16__CONFIG1:
6317             /* ignored, read only */
6318             register_name = "Config1";
6319             break;
6320         case CP0_REG16__CONFIG2:
6321             gen_helper_mtc0_config2(tcg_env, arg);
6322             register_name = "Config2";
6323             /* Stop translation as we may have switched the execution mode */
6324             ctx->base.is_jmp = DISAS_STOP;
6325             break;
6326         case CP0_REG16__CONFIG3:
6327             gen_helper_mtc0_config3(tcg_env, arg);
6328             register_name = "Config3";
6329             /* Stop translation as we may have switched the execution mode */
6330             ctx->base.is_jmp = DISAS_STOP;
6331             break;
6332         case CP0_REG16__CONFIG4:
6333             gen_helper_mtc0_config4(tcg_env, arg);
6334             register_name = "Config4";
6335             ctx->base.is_jmp = DISAS_STOP;
6336             break;
6337         case CP0_REG16__CONFIG5:
6338             gen_helper_mtc0_config5(tcg_env, arg);
6339             register_name = "Config5";
6340             /* Stop translation as we may have switched the execution mode */
6341             ctx->base.is_jmp = DISAS_STOP;
6342             break;
6343         /* 6,7 are implementation dependent */
6344         case CP0_REG16__CONFIG6:
6345             /* ignored */
6346             register_name = "Config6";
6347             break;
6348         case CP0_REG16__CONFIG7:
6349             /* ignored */
6350             register_name = "Config7";
6351             break;
6352         default:
6353             register_name = "Invalid config selector";
6354             goto cp0_unimplemented;
6355         }
6356         break;
6357     case CP0_REGISTER_17:
6358         switch (sel) {
6359         case CP0_REG17__LLADDR:
6360             gen_helper_mtc0_lladdr(tcg_env, arg);
6361             register_name = "LLAddr";
6362             break;
6363         case CP0_REG17__MAAR:
6364             CP0_CHECK(ctx->mrp);
6365             gen_helper_mtc0_maar(tcg_env, arg);
6366             register_name = "MAAR";
6367             break;
6368         case CP0_REG17__MAARI:
6369             CP0_CHECK(ctx->mrp);
6370             gen_helper_mtc0_maari(tcg_env, arg);
6371             register_name = "MAARI";
6372             break;
6373         default:
6374             goto cp0_unimplemented;
6375         }
6376         break;
6377     case CP0_REGISTER_18:
6378         switch (sel) {
6379         case CP0_REG18__WATCHLO0:
6380         case CP0_REG18__WATCHLO1:
6381         case CP0_REG18__WATCHLO2:
6382         case CP0_REG18__WATCHLO3:
6383         case CP0_REG18__WATCHLO4:
6384         case CP0_REG18__WATCHLO5:
6385         case CP0_REG18__WATCHLO6:
6386         case CP0_REG18__WATCHLO7:
6387             CP0_CHECK(ctx->CP0_Config1 & (1 << CP0C1_WR));
6388             gen_helper_0e1i(mtc0_watchlo, arg, sel);
6389             register_name = "WatchLo";
6390             break;
6391         default:
6392             goto cp0_unimplemented;
6393         }
6394         break;
6395     case CP0_REGISTER_19:
6396         switch (sel) {
6397         case CP0_REG19__WATCHHI0:
6398         case CP0_REG19__WATCHHI1:
6399         case CP0_REG19__WATCHHI2:
6400         case CP0_REG19__WATCHHI3:
6401         case CP0_REG19__WATCHHI4:
6402         case CP0_REG19__WATCHHI5:
6403         case CP0_REG19__WATCHHI6:
6404         case CP0_REG19__WATCHHI7:
6405             CP0_CHECK(ctx->CP0_Config1 & (1 << CP0C1_WR));
6406             gen_helper_0e1i(mtc0_watchhi, arg, sel);
6407             register_name = "WatchHi";
6408             break;
6409         default:
6410             goto cp0_unimplemented;
6411         }
6412         break;
6413     case CP0_REGISTER_20:
6414         switch (sel) {
6415         case CP0_REG20__XCONTEXT:
6416 #if defined(TARGET_MIPS64)
6417             check_insn(ctx, ISA_MIPS3);
6418             gen_helper_mtc0_xcontext(tcg_env, arg);
6419             register_name = "XContext";
6420             break;
6421 #endif
6422         default:
6423             goto cp0_unimplemented;
6424         }
6425         break;
6426     case CP0_REGISTER_21:
6427        /* Officially reserved, but sel 0 is used for R1x000 framemask */
6428         CP0_CHECK(!(ctx->insn_flags & ISA_MIPS_R6));
6429         switch (sel) {
6430         case 0:
6431             gen_helper_mtc0_framemask(tcg_env, arg);
6432             register_name = "Framemask";
6433             break;
6434         default:
6435             goto cp0_unimplemented;
6436         }
6437         break;
6438     case CP0_REGISTER_22:
6439         /* ignored */
6440         register_name = "Diagnostic"; /* implementation dependent */
6441         break;
6442     case CP0_REGISTER_23:
6443         switch (sel) {
6444         case CP0_REG23__DEBUG:
6445             gen_helper_mtc0_debug(tcg_env, arg); /* EJTAG support */
6446             /* DISAS_STOP isn't good enough here, hflags may have changed. */
6447             gen_save_pc(ctx->base.pc_next + 4);
6448             ctx->base.is_jmp = DISAS_EXIT;
6449             register_name = "Debug";
6450             break;
6451         case CP0_REG23__TRACECONTROL:
6452             /* PDtrace support */
6453             /* gen_helper_mtc0_tracecontrol(tcg_env, arg);  */
6454             register_name = "TraceControl";
6455             /* Stop translation as we may have switched the execution mode */
6456             ctx->base.is_jmp = DISAS_STOP;
6457             goto cp0_unimplemented;
6458         case CP0_REG23__TRACECONTROL2:
6459             /* PDtrace support */
6460             /* gen_helper_mtc0_tracecontrol2(tcg_env, arg); */
6461             register_name = "TraceControl2";
6462             /* Stop translation as we may have switched the execution mode */
6463             ctx->base.is_jmp = DISAS_STOP;
6464             goto cp0_unimplemented;
6465         case CP0_REG23__USERTRACEDATA1:
6466             /* Stop translation as we may have switched the execution mode */
6467             ctx->base.is_jmp = DISAS_STOP;
6468             /* PDtrace support */
6469             /* gen_helper_mtc0_usertracedata1(tcg_env, arg);*/
6470             register_name = "UserTraceData";
6471             /* Stop translation as we may have switched the execution mode */
6472             ctx->base.is_jmp = DISAS_STOP;
6473             goto cp0_unimplemented;
6474         case CP0_REG23__TRACEIBPC:
6475             /* PDtrace support */
6476             /* gen_helper_mtc0_traceibpc(tcg_env, arg);     */
6477             /* Stop translation as we may have switched the execution mode */
6478             ctx->base.is_jmp = DISAS_STOP;
6479             register_name = "TraceIBPC";
6480             goto cp0_unimplemented;
6481         case CP0_REG23__TRACEDBPC:
6482             /* PDtrace support */
6483             /* gen_helper_mtc0_tracedbpc(tcg_env, arg);     */
6484             /* Stop translation as we may have switched the execution mode */
6485             ctx->base.is_jmp = DISAS_STOP;
6486             register_name = "TraceDBPC";
6487             goto cp0_unimplemented;
6488         default:
6489             goto cp0_unimplemented;
6490         }
6491         break;
6492     case CP0_REGISTER_24:
6493         switch (sel) {
6494         case CP0_REG24__DEPC:
6495             /* EJTAG support */
6496             tcg_gen_st_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_DEPC));
6497             register_name = "DEPC";
6498             break;
6499         default:
6500             goto cp0_unimplemented;
6501         }
6502         break;
6503     case CP0_REGISTER_25:
6504         switch (sel) {
6505         case CP0_REG25__PERFCTL0:
6506             gen_helper_mtc0_performance0(tcg_env, arg);
6507             register_name = "Performance0";
6508             break;
6509         case CP0_REG25__PERFCNT0:
6510             /* gen_helper_mtc0_performance1(arg); */
6511             register_name = "Performance1";
6512             goto cp0_unimplemented;
6513         case CP0_REG25__PERFCTL1:
6514             /* gen_helper_mtc0_performance2(arg); */
6515             register_name = "Performance2";
6516             goto cp0_unimplemented;
6517         case CP0_REG25__PERFCNT1:
6518             /* gen_helper_mtc0_performance3(arg); */
6519             register_name = "Performance3";
6520             goto cp0_unimplemented;
6521         case CP0_REG25__PERFCTL2:
6522             /* gen_helper_mtc0_performance4(arg); */
6523             register_name = "Performance4";
6524             goto cp0_unimplemented;
6525         case CP0_REG25__PERFCNT2:
6526             /* gen_helper_mtc0_performance5(arg); */
6527             register_name = "Performance5";
6528             goto cp0_unimplemented;
6529         case CP0_REG25__PERFCTL3:
6530             /* gen_helper_mtc0_performance6(arg); */
6531             register_name = "Performance6";
6532             goto cp0_unimplemented;
6533         case CP0_REG25__PERFCNT3:
6534             /* gen_helper_mtc0_performance7(arg); */
6535             register_name = "Performance7";
6536             goto cp0_unimplemented;
6537         default:
6538             goto cp0_unimplemented;
6539         }
6540        break;
6541     case CP0_REGISTER_26:
6542         switch (sel) {
6543         case CP0_REG26__ERRCTL:
6544             gen_helper_mtc0_errctl(tcg_env, arg);
6545             ctx->base.is_jmp = DISAS_STOP;
6546             register_name = "ErrCtl";
6547             break;
6548         default:
6549             goto cp0_unimplemented;
6550         }
6551         break;
6552     case CP0_REGISTER_27:
6553         switch (sel) {
6554         case CP0_REG27__CACHERR:
6555             /* ignored */
6556             register_name = "CacheErr";
6557             break;
6558         default:
6559             goto cp0_unimplemented;
6560         }
6561        break;
6562     case CP0_REGISTER_28:
6563         switch (sel) {
6564         case CP0_REG28__TAGLO:
6565         case CP0_REG28__TAGLO1:
6566         case CP0_REG28__TAGLO2:
6567         case CP0_REG28__TAGLO3:
6568             gen_helper_mtc0_taglo(tcg_env, arg);
6569             register_name = "TagLo";
6570             break;
6571         case CP0_REG28__DATALO:
6572         case CP0_REG28__DATALO1:
6573         case CP0_REG28__DATALO2:
6574         case CP0_REG28__DATALO3:
6575             gen_helper_mtc0_datalo(tcg_env, arg);
6576             register_name = "DataLo";
6577             break;
6578         default:
6579             goto cp0_unimplemented;
6580         }
6581         break;
6582     case CP0_REGISTER_29:
6583         switch (sel) {
6584         case CP0_REG29__TAGHI:
6585         case CP0_REG29__TAGHI1:
6586         case CP0_REG29__TAGHI2:
6587         case CP0_REG29__TAGHI3:
6588             gen_helper_mtc0_taghi(tcg_env, arg);
6589             register_name = "TagHi";
6590             break;
6591         case CP0_REG29__DATAHI:
6592         case CP0_REG29__DATAHI1:
6593         case CP0_REG29__DATAHI2:
6594         case CP0_REG29__DATAHI3:
6595             gen_helper_mtc0_datahi(tcg_env, arg);
6596             register_name = "DataHi";
6597             break;
6598         default:
6599             register_name = "invalid sel";
6600             goto cp0_unimplemented;
6601         }
6602        break;
6603     case CP0_REGISTER_30:
6604         switch (sel) {
6605         case CP0_REG30__ERROREPC:
6606             tcg_gen_st_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_ErrorEPC));
6607             register_name = "ErrorEPC";
6608             break;
6609         default:
6610             goto cp0_unimplemented;
6611         }
6612         break;
6613     case CP0_REGISTER_31:
6614         switch (sel) {
6615         case CP0_REG31__DESAVE:
6616             /* EJTAG support */
6617             gen_mtc0_store32(arg, offsetof(CPUMIPSState, CP0_DESAVE));
6618             register_name = "DESAVE";
6619             break;
6620         case CP0_REG31__KSCRATCH1:
6621         case CP0_REG31__KSCRATCH2:
6622         case CP0_REG31__KSCRATCH3:
6623         case CP0_REG31__KSCRATCH4:
6624         case CP0_REG31__KSCRATCH5:
6625         case CP0_REG31__KSCRATCH6:
6626             CP0_CHECK(ctx->kscrexist & (1 << sel));
6627             tcg_gen_st_tl(arg, tcg_env,
6628                           offsetof(CPUMIPSState, CP0_KScratch[sel - 2]));
6629             register_name = "KScratch";
6630             break;
6631         default:
6632             goto cp0_unimplemented;
6633         }
6634         break;
6635     default:
6636        goto cp0_unimplemented;
6637     }
6638     trace_mips_translate_c0("mtc0", register_name, reg, sel);
6639 
6640     /* For simplicity assume that all writes can cause interrupts.  */
6641     if (icount) {
6642         /*
6643          * DISAS_STOP isn't sufficient, we need to ensure we break out of
6644          * translated code to check for pending interrupts.
6645          */
6646         gen_save_pc(ctx->base.pc_next + 4);
6647         ctx->base.is_jmp = DISAS_EXIT;
6648     }
6649     return;
6650 
6651 cp0_unimplemented:
6652     qemu_log_mask(LOG_UNIMP, "mtc0 %s (reg %d sel %d)\n",
6653                   register_name, reg, sel);
6654 }
6655 
6656 #if defined(TARGET_MIPS64)
6657 static void gen_dmfc0(DisasContext *ctx, TCGv arg, int reg, int sel)
6658 {
6659     const char *register_name = "invalid";
6660 
6661     if (sel != 0) {
6662         check_insn(ctx, ISA_MIPS_R1);
6663     }
6664 
6665     switch (reg) {
6666     case CP0_REGISTER_00:
6667         switch (sel) {
6668         case CP0_REG00__INDEX:
6669             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Index));
6670             register_name = "Index";
6671             break;
6672         case CP0_REG00__MVPCONTROL:
6673             CP0_CHECK(ctx->insn_flags & ASE_MT);
6674             gen_helper_mfc0_mvpcontrol(arg, tcg_env);
6675             register_name = "MVPControl";
6676             break;
6677         case CP0_REG00__MVPCONF0:
6678             CP0_CHECK(ctx->insn_flags & ASE_MT);
6679             gen_helper_mfc0_mvpconf0(arg, tcg_env);
6680             register_name = "MVPConf0";
6681             break;
6682         case CP0_REG00__MVPCONF1:
6683             CP0_CHECK(ctx->insn_flags & ASE_MT);
6684             gen_helper_mfc0_mvpconf1(arg, tcg_env);
6685             register_name = "MVPConf1";
6686             break;
6687         case CP0_REG00__VPCONTROL:
6688             CP0_CHECK(ctx->vp);
6689             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPControl));
6690             register_name = "VPControl";
6691             break;
6692         default:
6693             goto cp0_unimplemented;
6694         }
6695         break;
6696     case CP0_REGISTER_01:
6697         switch (sel) {
6698         case CP0_REG01__RANDOM:
6699             CP0_CHECK(!(ctx->insn_flags & ISA_MIPS_R6));
6700             gen_helper_mfc0_random(arg, tcg_env);
6701             register_name = "Random";
6702             break;
6703         case CP0_REG01__VPECONTROL:
6704             CP0_CHECK(ctx->insn_flags & ASE_MT);
6705             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEControl));
6706             register_name = "VPEControl";
6707             break;
6708         case CP0_REG01__VPECONF0:
6709             CP0_CHECK(ctx->insn_flags & ASE_MT);
6710             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEConf0));
6711             register_name = "VPEConf0";
6712             break;
6713         case CP0_REG01__VPECONF1:
6714             CP0_CHECK(ctx->insn_flags & ASE_MT);
6715             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEConf1));
6716             register_name = "VPEConf1";
6717             break;
6718         case CP0_REG01__YQMASK:
6719             CP0_CHECK(ctx->insn_flags & ASE_MT);
6720             tcg_gen_ld_tl(arg, tcg_env,
6721                           offsetof(CPUMIPSState, CP0_YQMask));
6722             register_name = "YQMask";
6723             break;
6724         case CP0_REG01__VPESCHEDULE:
6725             CP0_CHECK(ctx->insn_flags & ASE_MT);
6726             tcg_gen_ld_tl(arg, tcg_env,
6727                           offsetof(CPUMIPSState, CP0_VPESchedule));
6728             register_name = "VPESchedule";
6729             break;
6730         case CP0_REG01__VPESCHEFBACK:
6731             CP0_CHECK(ctx->insn_flags & ASE_MT);
6732             tcg_gen_ld_tl(arg, tcg_env,
6733                           offsetof(CPUMIPSState, CP0_VPEScheFBack));
6734             register_name = "VPEScheFBack";
6735             break;
6736         case CP0_REG01__VPEOPT:
6737             CP0_CHECK(ctx->insn_flags & ASE_MT);
6738             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_VPEOpt));
6739             register_name = "VPEOpt";
6740             break;
6741         default:
6742             goto cp0_unimplemented;
6743         }
6744         break;
6745     case CP0_REGISTER_02:
6746         switch (sel) {
6747         case CP0_REG02__ENTRYLO0:
6748             tcg_gen_ld_tl(arg, tcg_env,
6749                           offsetof(CPUMIPSState, CP0_EntryLo0));
6750             register_name = "EntryLo0";
6751             break;
6752         case CP0_REG02__TCSTATUS:
6753             CP0_CHECK(ctx->insn_flags & ASE_MT);
6754             gen_helper_mfc0_tcstatus(arg, tcg_env);
6755             register_name = "TCStatus";
6756             break;
6757         case CP0_REG02__TCBIND:
6758             CP0_CHECK(ctx->insn_flags & ASE_MT);
6759             gen_helper_mfc0_tcbind(arg, tcg_env);
6760             register_name = "TCBind";
6761             break;
6762         case CP0_REG02__TCRESTART:
6763             CP0_CHECK(ctx->insn_flags & ASE_MT);
6764             gen_helper_dmfc0_tcrestart(arg, tcg_env);
6765             register_name = "TCRestart";
6766             break;
6767         case CP0_REG02__TCHALT:
6768             CP0_CHECK(ctx->insn_flags & ASE_MT);
6769             gen_helper_dmfc0_tchalt(arg, tcg_env);
6770             register_name = "TCHalt";
6771             break;
6772         case CP0_REG02__TCCONTEXT:
6773             CP0_CHECK(ctx->insn_flags & ASE_MT);
6774             gen_helper_dmfc0_tccontext(arg, tcg_env);
6775             register_name = "TCContext";
6776             break;
6777         case CP0_REG02__TCSCHEDULE:
6778             CP0_CHECK(ctx->insn_flags & ASE_MT);
6779             gen_helper_dmfc0_tcschedule(arg, tcg_env);
6780             register_name = "TCSchedule";
6781             break;
6782         case CP0_REG02__TCSCHEFBACK:
6783             CP0_CHECK(ctx->insn_flags & ASE_MT);
6784             gen_helper_dmfc0_tcschefback(arg, tcg_env);
6785             register_name = "TCScheFBack";
6786             break;
6787         default:
6788             goto cp0_unimplemented;
6789         }
6790         break;
6791     case CP0_REGISTER_03:
6792         switch (sel) {
6793         case CP0_REG03__ENTRYLO1:
6794             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_EntryLo1));
6795             register_name = "EntryLo1";
6796             break;
6797         case CP0_REG03__GLOBALNUM:
6798             CP0_CHECK(ctx->vp);
6799             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_GlobalNumber));
6800             register_name = "GlobalNumber";
6801             break;
6802         default:
6803             goto cp0_unimplemented;
6804         }
6805         break;
6806     case CP0_REGISTER_04:
6807         switch (sel) {
6808         case CP0_REG04__CONTEXT:
6809             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_Context));
6810             register_name = "Context";
6811             break;
6812         case CP0_REG04__CONTEXTCONFIG:
6813             /* SmartMIPS ASE */
6814             /* gen_helper_dmfc0_contextconfig(arg); */
6815             register_name = "ContextConfig";
6816             goto cp0_unimplemented;
6817         case CP0_REG04__USERLOCAL:
6818             CP0_CHECK(ctx->ulri);
6819             tcg_gen_ld_tl(arg, tcg_env,
6820                           offsetof(CPUMIPSState, active_tc.CP0_UserLocal));
6821             register_name = "UserLocal";
6822             break;
6823         case CP0_REG04__MMID:
6824             CP0_CHECK(ctx->mi);
6825             gen_helper_mtc0_memorymapid(tcg_env, arg);
6826             register_name = "MMID";
6827             break;
6828         default:
6829             goto cp0_unimplemented;
6830         }
6831         break;
6832     case CP0_REGISTER_05:
6833         switch (sel) {
6834         case CP0_REG05__PAGEMASK:
6835             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PageMask));
6836             register_name = "PageMask";
6837             break;
6838         case CP0_REG05__PAGEGRAIN:
6839             check_insn(ctx, ISA_MIPS_R2);
6840             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PageGrain));
6841             register_name = "PageGrain";
6842             break;
6843         case CP0_REG05__SEGCTL0:
6844             CP0_CHECK(ctx->sc);
6845             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_SegCtl0));
6846             register_name = "SegCtl0";
6847             break;
6848         case CP0_REG05__SEGCTL1:
6849             CP0_CHECK(ctx->sc);
6850             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_SegCtl1));
6851             register_name = "SegCtl1";
6852             break;
6853         case CP0_REG05__SEGCTL2:
6854             CP0_CHECK(ctx->sc);
6855             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_SegCtl2));
6856             register_name = "SegCtl2";
6857             break;
6858         case CP0_REG05__PWBASE:
6859             check_pw(ctx);
6860             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_PWBase));
6861             register_name = "PWBase";
6862             break;
6863         case CP0_REG05__PWFIELD:
6864             check_pw(ctx);
6865             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_PWField));
6866             register_name = "PWField";
6867             break;
6868         case CP0_REG05__PWSIZE:
6869             check_pw(ctx);
6870             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_PWSize));
6871             register_name = "PWSize";
6872             break;
6873         default:
6874             goto cp0_unimplemented;
6875         }
6876         break;
6877     case CP0_REGISTER_06:
6878         switch (sel) {
6879         case CP0_REG06__WIRED:
6880             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Wired));
6881             register_name = "Wired";
6882             break;
6883         case CP0_REG06__SRSCONF0:
6884             check_insn(ctx, ISA_MIPS_R2);
6885             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf0));
6886             register_name = "SRSConf0";
6887             break;
6888         case CP0_REG06__SRSCONF1:
6889             check_insn(ctx, ISA_MIPS_R2);
6890             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf1));
6891             register_name = "SRSConf1";
6892             break;
6893         case CP0_REG06__SRSCONF2:
6894             check_insn(ctx, ISA_MIPS_R2);
6895             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf2));
6896             register_name = "SRSConf2";
6897             break;
6898         case CP0_REG06__SRSCONF3:
6899             check_insn(ctx, ISA_MIPS_R2);
6900             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf3));
6901             register_name = "SRSConf3";
6902             break;
6903         case CP0_REG06__SRSCONF4:
6904             check_insn(ctx, ISA_MIPS_R2);
6905             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSConf4));
6906             register_name = "SRSConf4";
6907             break;
6908         case CP0_REG06__PWCTL:
6909             check_pw(ctx);
6910             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PWCtl));
6911             register_name = "PWCtl";
6912             break;
6913         default:
6914             goto cp0_unimplemented;
6915         }
6916         break;
6917     case CP0_REGISTER_07:
6918         switch (sel) {
6919         case CP0_REG07__HWRENA:
6920             check_insn(ctx, ISA_MIPS_R2);
6921             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_HWREna));
6922             register_name = "HWREna";
6923             break;
6924         default:
6925             goto cp0_unimplemented;
6926         }
6927         break;
6928     case CP0_REGISTER_08:
6929         switch (sel) {
6930         case CP0_REG08__BADVADDR:
6931             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_BadVAddr));
6932             register_name = "BadVAddr";
6933             break;
6934         case CP0_REG08__BADINSTR:
6935             CP0_CHECK(ctx->bi);
6936             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_BadInstr));
6937             register_name = "BadInstr";
6938             break;
6939         case CP0_REG08__BADINSTRP:
6940             CP0_CHECK(ctx->bp);
6941             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_BadInstrP));
6942             register_name = "BadInstrP";
6943             break;
6944         case CP0_REG08__BADINSTRX:
6945             CP0_CHECK(ctx->bi);
6946             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_BadInstrX));
6947             tcg_gen_andi_tl(arg, arg, ~0xffff);
6948             register_name = "BadInstrX";
6949             break;
6950         default:
6951             goto cp0_unimplemented;
6952         }
6953         break;
6954     case CP0_REGISTER_09:
6955         switch (sel) {
6956         case CP0_REG09__COUNT:
6957             /* Mark as an IO operation because we read the time.  */
6958             translator_io_start(&ctx->base);
6959             gen_helper_mfc0_count(arg, tcg_env);
6960             /*
6961              * Break the TB to be able to take timer interrupts immediately
6962              * after reading count. DISAS_STOP isn't sufficient, we need to
6963              * ensure we break completely out of translated code.
6964              */
6965             gen_save_pc(ctx->base.pc_next + 4);
6966             ctx->base.is_jmp = DISAS_EXIT;
6967             register_name = "Count";
6968             break;
6969         default:
6970             goto cp0_unimplemented;
6971         }
6972         break;
6973     case CP0_REGISTER_10:
6974         switch (sel) {
6975         case CP0_REG10__ENTRYHI:
6976             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_EntryHi));
6977             register_name = "EntryHi";
6978             break;
6979         default:
6980             goto cp0_unimplemented;
6981         }
6982         break;
6983     case CP0_REGISTER_11:
6984         switch (sel) {
6985         case CP0_REG11__COMPARE:
6986             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Compare));
6987             register_name = "Compare";
6988             break;
6989         /* 6,7 are implementation dependent */
6990         default:
6991             goto cp0_unimplemented;
6992         }
6993         break;
6994     case CP0_REGISTER_12:
6995         switch (sel) {
6996         case CP0_REG12__STATUS:
6997             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Status));
6998             register_name = "Status";
6999             break;
7000         case CP0_REG12__INTCTL:
7001             check_insn(ctx, ISA_MIPS_R2);
7002             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_IntCtl));
7003             register_name = "IntCtl";
7004             break;
7005         case CP0_REG12__SRSCTL:
7006             check_insn(ctx, ISA_MIPS_R2);
7007             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSCtl));
7008             register_name = "SRSCtl";
7009             break;
7010         case CP0_REG12__SRSMAP:
7011             check_insn(ctx, ISA_MIPS_R2);
7012             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_SRSMap));
7013             register_name = "SRSMap";
7014             break;
7015         default:
7016             goto cp0_unimplemented;
7017         }
7018         break;
7019     case CP0_REGISTER_13:
7020         switch (sel) {
7021         case CP0_REG13__CAUSE:
7022             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Cause));
7023             register_name = "Cause";
7024             break;
7025         default:
7026             goto cp0_unimplemented;
7027         }
7028         break;
7029     case CP0_REGISTER_14:
7030         switch (sel) {
7031         case CP0_REG14__EPC:
7032             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_EPC));
7033             register_name = "EPC";
7034             break;
7035         default:
7036             goto cp0_unimplemented;
7037         }
7038         break;
7039     case CP0_REGISTER_15:
7040         switch (sel) {
7041         case CP0_REG15__PRID:
7042             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_PRid));
7043             register_name = "PRid";
7044             break;
7045         case CP0_REG15__EBASE:
7046             check_insn(ctx, ISA_MIPS_R2);
7047             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_EBase));
7048             register_name = "EBase";
7049             break;
7050         case CP0_REG15__CMGCRBASE:
7051             check_insn(ctx, ISA_MIPS_R2);
7052             CP0_CHECK(ctx->cmgcr);
7053             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_CMGCRBase));
7054             register_name = "CMGCRBase";
7055             break;
7056         default:
7057             goto cp0_unimplemented;
7058         }
7059         break;
7060     case CP0_REGISTER_16:
7061         switch (sel) {
7062         case CP0_REG16__CONFIG:
7063             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config0));
7064             register_name = "Config";
7065             break;
7066         case CP0_REG16__CONFIG1:
7067             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config1));
7068             register_name = "Config1";
7069             break;
7070         case CP0_REG16__CONFIG2:
7071             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config2));
7072             register_name = "Config2";
7073             break;
7074         case CP0_REG16__CONFIG3:
7075             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config3));
7076             register_name = "Config3";
7077             break;
7078         case CP0_REG16__CONFIG4:
7079             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config4));
7080             register_name = "Config4";
7081             break;
7082         case CP0_REG16__CONFIG5:
7083             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config5));
7084             register_name = "Config5";
7085             break;
7086         /* 6,7 are implementation dependent */
7087         case CP0_REG16__CONFIG6:
7088             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config6));
7089             register_name = "Config6";
7090             break;
7091         case CP0_REG16__CONFIG7:
7092             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Config7));
7093             register_name = "Config7";
7094             break;
7095         default:
7096             goto cp0_unimplemented;
7097         }
7098         break;
7099     case CP0_REGISTER_17:
7100         switch (sel) {
7101         case CP0_REG17__LLADDR:
7102             gen_helper_dmfc0_lladdr(arg, tcg_env);
7103             register_name = "LLAddr";
7104             break;
7105         case CP0_REG17__MAAR:
7106             CP0_CHECK(ctx->mrp);
7107             gen_helper_dmfc0_maar(arg, tcg_env);
7108             register_name = "MAAR";
7109             break;
7110         case CP0_REG17__MAARI:
7111             CP0_CHECK(ctx->mrp);
7112             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_MAARI));
7113             register_name = "MAARI";
7114             break;
7115         default:
7116             goto cp0_unimplemented;
7117         }
7118         break;
7119     case CP0_REGISTER_18:
7120         switch (sel) {
7121         case CP0_REG18__WATCHLO0:
7122         case CP0_REG18__WATCHLO1:
7123         case CP0_REG18__WATCHLO2:
7124         case CP0_REG18__WATCHLO3:
7125         case CP0_REG18__WATCHLO4:
7126         case CP0_REG18__WATCHLO5:
7127         case CP0_REG18__WATCHLO6:
7128         case CP0_REG18__WATCHLO7:
7129             CP0_CHECK(ctx->CP0_Config1 & (1 << CP0C1_WR));
7130             gen_helper_1e0i(dmfc0_watchlo, arg, sel);
7131             register_name = "WatchLo";
7132             break;
7133         default:
7134             goto cp0_unimplemented;
7135         }
7136         break;
7137     case CP0_REGISTER_19:
7138         switch (sel) {
7139         case CP0_REG19__WATCHHI0:
7140         case CP0_REG19__WATCHHI1:
7141         case CP0_REG19__WATCHHI2:
7142         case CP0_REG19__WATCHHI3:
7143         case CP0_REG19__WATCHHI4:
7144         case CP0_REG19__WATCHHI5:
7145         case CP0_REG19__WATCHHI6:
7146         case CP0_REG19__WATCHHI7:
7147             CP0_CHECK(ctx->CP0_Config1 & (1 << CP0C1_WR));
7148             gen_helper_1e0i(dmfc0_watchhi, arg, sel);
7149             register_name = "WatchHi";
7150             break;
7151         default:
7152             goto cp0_unimplemented;
7153         }
7154         break;
7155     case CP0_REGISTER_20:
7156         switch (sel) {
7157         case CP0_REG20__XCONTEXT:
7158             check_insn(ctx, ISA_MIPS3);
7159             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_XContext));
7160             register_name = "XContext";
7161             break;
7162         default:
7163             goto cp0_unimplemented;
7164         }
7165         break;
7166     case CP0_REGISTER_21:
7167         /* Officially reserved, but sel 0 is used for R1x000 framemask */
7168         CP0_CHECK(!(ctx->insn_flags & ISA_MIPS_R6));
7169         switch (sel) {
7170         case 0:
7171             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Framemask));
7172             register_name = "Framemask";
7173             break;
7174         default:
7175             goto cp0_unimplemented;
7176         }
7177         break;
7178     case CP0_REGISTER_22:
7179         tcg_gen_movi_tl(arg, 0); /* unimplemented */
7180         register_name = "'Diagnostic"; /* implementation dependent */
7181         break;
7182     case CP0_REGISTER_23:
7183         switch (sel) {
7184         case CP0_REG23__DEBUG:
7185             gen_helper_mfc0_debug(arg, tcg_env); /* EJTAG support */
7186             register_name = "Debug";
7187             break;
7188         case CP0_REG23__TRACECONTROL:
7189             /* PDtrace support */
7190             /* gen_helper_dmfc0_tracecontrol(arg, tcg_env);  */
7191             register_name = "TraceControl";
7192             goto cp0_unimplemented;
7193         case CP0_REG23__TRACECONTROL2:
7194             /* PDtrace support */
7195             /* gen_helper_dmfc0_tracecontrol2(arg, tcg_env); */
7196             register_name = "TraceControl2";
7197             goto cp0_unimplemented;
7198         case CP0_REG23__USERTRACEDATA1:
7199             /* PDtrace support */
7200             /* gen_helper_dmfc0_usertracedata1(arg, tcg_env);*/
7201             register_name = "UserTraceData1";
7202             goto cp0_unimplemented;
7203         case CP0_REG23__TRACEIBPC:
7204             /* PDtrace support */
7205             /* gen_helper_dmfc0_traceibpc(arg, tcg_env);     */
7206             register_name = "TraceIBPC";
7207             goto cp0_unimplemented;
7208         case CP0_REG23__TRACEDBPC:
7209             /* PDtrace support */
7210             /* gen_helper_dmfc0_tracedbpc(arg, tcg_env);     */
7211             register_name = "TraceDBPC";
7212             goto cp0_unimplemented;
7213         default:
7214             goto cp0_unimplemented;
7215         }
7216         break;
7217     case CP0_REGISTER_24:
7218         switch (sel) {
7219         case CP0_REG24__DEPC:
7220             /* EJTAG support */
7221             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_DEPC));
7222             register_name = "DEPC";
7223             break;
7224         default:
7225             goto cp0_unimplemented;
7226         }
7227         break;
7228     case CP0_REGISTER_25:
7229         switch (sel) {
7230         case CP0_REG25__PERFCTL0:
7231             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_Performance0));
7232             register_name = "Performance0";
7233             break;
7234         case CP0_REG25__PERFCNT0:
7235             /* gen_helper_dmfc0_performance1(arg); */
7236             register_name = "Performance1";
7237             goto cp0_unimplemented;
7238         case CP0_REG25__PERFCTL1:
7239             /* gen_helper_dmfc0_performance2(arg); */
7240             register_name = "Performance2";
7241             goto cp0_unimplemented;
7242         case CP0_REG25__PERFCNT1:
7243             /* gen_helper_dmfc0_performance3(arg); */
7244             register_name = "Performance3";
7245             goto cp0_unimplemented;
7246         case CP0_REG25__PERFCTL2:
7247             /* gen_helper_dmfc0_performance4(arg); */
7248             register_name = "Performance4";
7249             goto cp0_unimplemented;
7250         case CP0_REG25__PERFCNT2:
7251             /* gen_helper_dmfc0_performance5(arg); */
7252             register_name = "Performance5";
7253             goto cp0_unimplemented;
7254         case CP0_REG25__PERFCTL3:
7255             /* gen_helper_dmfc0_performance6(arg); */
7256             register_name = "Performance6";
7257             goto cp0_unimplemented;
7258         case CP0_REG25__PERFCNT3:
7259             /* gen_helper_dmfc0_performance7(arg); */
7260             register_name = "Performance7";
7261             goto cp0_unimplemented;
7262         default:
7263             goto cp0_unimplemented;
7264         }
7265         break;
7266     case CP0_REGISTER_26:
7267         switch (sel) {
7268         case CP0_REG26__ERRCTL:
7269             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_ErrCtl));
7270             register_name = "ErrCtl";
7271             break;
7272         default:
7273             goto cp0_unimplemented;
7274         }
7275         break;
7276     case CP0_REGISTER_27:
7277         switch (sel) {
7278         /* ignored */
7279         case CP0_REG27__CACHERR:
7280             tcg_gen_movi_tl(arg, 0); /* unimplemented */
7281             register_name = "CacheErr";
7282             break;
7283         default:
7284             goto cp0_unimplemented;
7285         }
7286         break;
7287     case CP0_REGISTER_28:
7288         switch (sel) {
7289         case CP0_REG28__TAGLO:
7290         case CP0_REG28__TAGLO1:
7291         case CP0_REG28__TAGLO2:
7292         case CP0_REG28__TAGLO3:
7293             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_TagLo));
7294             register_name = "TagLo";
7295             break;
7296         case CP0_REG28__DATALO:
7297         case CP0_REG28__DATALO1:
7298         case CP0_REG28__DATALO2:
7299         case CP0_REG28__DATALO3:
7300             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DataLo));
7301             register_name = "DataLo";
7302             break;
7303         default:
7304             goto cp0_unimplemented;
7305         }
7306         break;
7307     case CP0_REGISTER_29:
7308         switch (sel) {
7309         case CP0_REG29__TAGHI:
7310         case CP0_REG29__TAGHI1:
7311         case CP0_REG29__TAGHI2:
7312         case CP0_REG29__TAGHI3:
7313             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_TagHi));
7314             register_name = "TagHi";
7315             break;
7316         case CP0_REG29__DATAHI:
7317         case CP0_REG29__DATAHI1:
7318         case CP0_REG29__DATAHI2:
7319         case CP0_REG29__DATAHI3:
7320             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DataHi));
7321             register_name = "DataHi";
7322             break;
7323         default:
7324             goto cp0_unimplemented;
7325         }
7326         break;
7327     case CP0_REGISTER_30:
7328         switch (sel) {
7329         case CP0_REG30__ERROREPC:
7330             tcg_gen_ld_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_ErrorEPC));
7331             register_name = "ErrorEPC";
7332             break;
7333         default:
7334             goto cp0_unimplemented;
7335         }
7336         break;
7337     case CP0_REGISTER_31:
7338         switch (sel) {
7339         case CP0_REG31__DESAVE:
7340             /* EJTAG support */
7341             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_DESAVE));
7342             register_name = "DESAVE";
7343             break;
7344         case CP0_REG31__KSCRATCH1:
7345         case CP0_REG31__KSCRATCH2:
7346         case CP0_REG31__KSCRATCH3:
7347         case CP0_REG31__KSCRATCH4:
7348         case CP0_REG31__KSCRATCH5:
7349         case CP0_REG31__KSCRATCH6:
7350             CP0_CHECK(ctx->kscrexist & (1 << sel));
7351             tcg_gen_ld_tl(arg, tcg_env,
7352                           offsetof(CPUMIPSState, CP0_KScratch[sel - 2]));
7353             register_name = "KScratch";
7354             break;
7355         default:
7356             goto cp0_unimplemented;
7357         }
7358         break;
7359     default:
7360         goto cp0_unimplemented;
7361     }
7362     trace_mips_translate_c0("dmfc0", register_name, reg, sel);
7363     return;
7364 
7365 cp0_unimplemented:
7366     qemu_log_mask(LOG_UNIMP, "dmfc0 %s (reg %d sel %d)\n",
7367                   register_name, reg, sel);
7368     gen_mfc0_unimplemented(ctx, arg);
7369 }
7370 
7371 static void gen_dmtc0(DisasContext *ctx, TCGv arg, int reg, int sel)
7372 {
7373     const char *register_name = "invalid";
7374     bool icount;
7375 
7376     if (sel != 0) {
7377         check_insn(ctx, ISA_MIPS_R1);
7378     }
7379 
7380     icount = translator_io_start(&ctx->base);
7381 
7382     switch (reg) {
7383     case CP0_REGISTER_00:
7384         switch (sel) {
7385         case CP0_REG00__INDEX:
7386             gen_helper_mtc0_index(tcg_env, arg);
7387             register_name = "Index";
7388             break;
7389         case CP0_REG00__MVPCONTROL:
7390             CP0_CHECK(ctx->insn_flags & ASE_MT);
7391             gen_helper_mtc0_mvpcontrol(tcg_env, arg);
7392             register_name = "MVPControl";
7393             break;
7394         case CP0_REG00__MVPCONF0:
7395             CP0_CHECK(ctx->insn_flags & ASE_MT);
7396             /* ignored */
7397             register_name = "MVPConf0";
7398             break;
7399         case CP0_REG00__MVPCONF1:
7400             CP0_CHECK(ctx->insn_flags & ASE_MT);
7401             /* ignored */
7402             register_name = "MVPConf1";
7403             break;
7404         case CP0_REG00__VPCONTROL:
7405             CP0_CHECK(ctx->vp);
7406             /* ignored */
7407             register_name = "VPControl";
7408             break;
7409         default:
7410             goto cp0_unimplemented;
7411         }
7412         break;
7413     case CP0_REGISTER_01:
7414         switch (sel) {
7415         case CP0_REG01__RANDOM:
7416             /* ignored */
7417             register_name = "Random";
7418             break;
7419         case CP0_REG01__VPECONTROL:
7420             CP0_CHECK(ctx->insn_flags & ASE_MT);
7421             gen_helper_mtc0_vpecontrol(tcg_env, arg);
7422             register_name = "VPEControl";
7423             break;
7424         case CP0_REG01__VPECONF0:
7425             CP0_CHECK(ctx->insn_flags & ASE_MT);
7426             gen_helper_mtc0_vpeconf0(tcg_env, arg);
7427             register_name = "VPEConf0";
7428             break;
7429         case CP0_REG01__VPECONF1:
7430             CP0_CHECK(ctx->insn_flags & ASE_MT);
7431             gen_helper_mtc0_vpeconf1(tcg_env, arg);
7432             register_name = "VPEConf1";
7433             break;
7434         case CP0_REG01__YQMASK:
7435             CP0_CHECK(ctx->insn_flags & ASE_MT);
7436             gen_helper_mtc0_yqmask(tcg_env, arg);
7437             register_name = "YQMask";
7438             break;
7439         case CP0_REG01__VPESCHEDULE:
7440             CP0_CHECK(ctx->insn_flags & ASE_MT);
7441             tcg_gen_st_tl(arg, tcg_env,
7442                           offsetof(CPUMIPSState, CP0_VPESchedule));
7443             register_name = "VPESchedule";
7444             break;
7445         case CP0_REG01__VPESCHEFBACK:
7446             CP0_CHECK(ctx->insn_flags & ASE_MT);
7447             tcg_gen_st_tl(arg, tcg_env,
7448                           offsetof(CPUMIPSState, CP0_VPEScheFBack));
7449             register_name = "VPEScheFBack";
7450             break;
7451         case CP0_REG01__VPEOPT:
7452             CP0_CHECK(ctx->insn_flags & ASE_MT);
7453             gen_helper_mtc0_vpeopt(tcg_env, arg);
7454             register_name = "VPEOpt";
7455             break;
7456         default:
7457             goto cp0_unimplemented;
7458         }
7459         break;
7460     case CP0_REGISTER_02:
7461         switch (sel) {
7462         case CP0_REG02__ENTRYLO0:
7463             gen_helper_dmtc0_entrylo0(tcg_env, arg);
7464             register_name = "EntryLo0";
7465             break;
7466         case CP0_REG02__TCSTATUS:
7467             CP0_CHECK(ctx->insn_flags & ASE_MT);
7468             gen_helper_mtc0_tcstatus(tcg_env, arg);
7469             register_name = "TCStatus";
7470             break;
7471         case CP0_REG02__TCBIND:
7472             CP0_CHECK(ctx->insn_flags & ASE_MT);
7473             gen_helper_mtc0_tcbind(tcg_env, arg);
7474             register_name = "TCBind";
7475             break;
7476         case CP0_REG02__TCRESTART:
7477             CP0_CHECK(ctx->insn_flags & ASE_MT);
7478             gen_helper_mtc0_tcrestart(tcg_env, arg);
7479             register_name = "TCRestart";
7480             break;
7481         case CP0_REG02__TCHALT:
7482             CP0_CHECK(ctx->insn_flags & ASE_MT);
7483             gen_helper_mtc0_tchalt(tcg_env, arg);
7484             register_name = "TCHalt";
7485             break;
7486         case CP0_REG02__TCCONTEXT:
7487             CP0_CHECK(ctx->insn_flags & ASE_MT);
7488             gen_helper_mtc0_tccontext(tcg_env, arg);
7489             register_name = "TCContext";
7490             break;
7491         case CP0_REG02__TCSCHEDULE:
7492             CP0_CHECK(ctx->insn_flags & ASE_MT);
7493             gen_helper_mtc0_tcschedule(tcg_env, arg);
7494             register_name = "TCSchedule";
7495             break;
7496         case CP0_REG02__TCSCHEFBACK:
7497             CP0_CHECK(ctx->insn_flags & ASE_MT);
7498             gen_helper_mtc0_tcschefback(tcg_env, arg);
7499             register_name = "TCScheFBack";
7500             break;
7501         default:
7502             goto cp0_unimplemented;
7503         }
7504         break;
7505     case CP0_REGISTER_03:
7506         switch (sel) {
7507         case CP0_REG03__ENTRYLO1:
7508             gen_helper_dmtc0_entrylo1(tcg_env, arg);
7509             register_name = "EntryLo1";
7510             break;
7511         case CP0_REG03__GLOBALNUM:
7512             CP0_CHECK(ctx->vp);
7513             /* ignored */
7514             register_name = "GlobalNumber";
7515             break;
7516         default:
7517             goto cp0_unimplemented;
7518         }
7519         break;
7520     case CP0_REGISTER_04:
7521         switch (sel) {
7522         case CP0_REG04__CONTEXT:
7523             gen_helper_mtc0_context(tcg_env, arg);
7524             register_name = "Context";
7525             break;
7526         case CP0_REG04__CONTEXTCONFIG:
7527             /* SmartMIPS ASE */
7528             /* gen_helper_dmtc0_contextconfig(arg); */
7529             register_name = "ContextConfig";
7530             goto cp0_unimplemented;
7531         case CP0_REG04__USERLOCAL:
7532             CP0_CHECK(ctx->ulri);
7533             tcg_gen_st_tl(arg, tcg_env,
7534                           offsetof(CPUMIPSState, active_tc.CP0_UserLocal));
7535             register_name = "UserLocal";
7536             break;
7537         case CP0_REG04__MMID:
7538             CP0_CHECK(ctx->mi);
7539             gen_mfc0_load32(arg, offsetof(CPUMIPSState, CP0_MemoryMapID));
7540             register_name = "MMID";
7541             break;
7542         default:
7543             goto cp0_unimplemented;
7544         }
7545         break;
7546     case CP0_REGISTER_05:
7547         switch (sel) {
7548         case CP0_REG05__PAGEMASK:
7549             gen_helper_mtc0_pagemask(tcg_env, arg);
7550             register_name = "PageMask";
7551             break;
7552         case CP0_REG05__PAGEGRAIN:
7553             check_insn(ctx, ISA_MIPS_R2);
7554             gen_helper_mtc0_pagegrain(tcg_env, arg);
7555             register_name = "PageGrain";
7556             break;
7557         case CP0_REG05__SEGCTL0:
7558             CP0_CHECK(ctx->sc);
7559             gen_helper_mtc0_segctl0(tcg_env, arg);
7560             register_name = "SegCtl0";
7561             break;
7562         case CP0_REG05__SEGCTL1:
7563             CP0_CHECK(ctx->sc);
7564             gen_helper_mtc0_segctl1(tcg_env, arg);
7565             register_name = "SegCtl1";
7566             break;
7567         case CP0_REG05__SEGCTL2:
7568             CP0_CHECK(ctx->sc);
7569             gen_helper_mtc0_segctl2(tcg_env, arg);
7570             register_name = "SegCtl2";
7571             break;
7572         case CP0_REG05__PWBASE:
7573             check_pw(ctx);
7574             tcg_gen_st_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_PWBase));
7575             register_name = "PWBase";
7576             break;
7577         case CP0_REG05__PWFIELD:
7578             check_pw(ctx);
7579             gen_helper_mtc0_pwfield(tcg_env, arg);
7580             register_name = "PWField";
7581             break;
7582         case CP0_REG05__PWSIZE:
7583             check_pw(ctx);
7584             gen_helper_mtc0_pwsize(tcg_env, arg);
7585             register_name = "PWSize";
7586             break;
7587         default:
7588             goto cp0_unimplemented;
7589         }
7590         break;
7591     case CP0_REGISTER_06:
7592         switch (sel) {
7593         case CP0_REG06__WIRED:
7594             gen_helper_mtc0_wired(tcg_env, arg);
7595             register_name = "Wired";
7596             break;
7597         case CP0_REG06__SRSCONF0:
7598             check_insn(ctx, ISA_MIPS_R2);
7599             gen_helper_mtc0_srsconf0(tcg_env, arg);
7600             register_name = "SRSConf0";
7601             break;
7602         case CP0_REG06__SRSCONF1:
7603             check_insn(ctx, ISA_MIPS_R2);
7604             gen_helper_mtc0_srsconf1(tcg_env, arg);
7605             register_name = "SRSConf1";
7606             break;
7607         case CP0_REG06__SRSCONF2:
7608             check_insn(ctx, ISA_MIPS_R2);
7609             gen_helper_mtc0_srsconf2(tcg_env, arg);
7610             register_name = "SRSConf2";
7611             break;
7612         case CP0_REG06__SRSCONF3:
7613             check_insn(ctx, ISA_MIPS_R2);
7614             gen_helper_mtc0_srsconf3(tcg_env, arg);
7615             register_name = "SRSConf3";
7616             break;
7617         case CP0_REG06__SRSCONF4:
7618             check_insn(ctx, ISA_MIPS_R2);
7619             gen_helper_mtc0_srsconf4(tcg_env, arg);
7620             register_name = "SRSConf4";
7621             break;
7622         case CP0_REG06__PWCTL:
7623             check_pw(ctx);
7624             gen_helper_mtc0_pwctl(tcg_env, arg);
7625             register_name = "PWCtl";
7626             break;
7627         default:
7628             goto cp0_unimplemented;
7629         }
7630         break;
7631     case CP0_REGISTER_07:
7632         switch (sel) {
7633         case CP0_REG07__HWRENA:
7634             check_insn(ctx, ISA_MIPS_R2);
7635             gen_helper_mtc0_hwrena(tcg_env, arg);
7636             ctx->base.is_jmp = DISAS_STOP;
7637             register_name = "HWREna";
7638             break;
7639         default:
7640             goto cp0_unimplemented;
7641         }
7642         break;
7643     case CP0_REGISTER_08:
7644         switch (sel) {
7645         case CP0_REG08__BADVADDR:
7646             /* ignored */
7647             register_name = "BadVAddr";
7648             break;
7649         case CP0_REG08__BADINSTR:
7650             /* ignored */
7651             register_name = "BadInstr";
7652             break;
7653         case CP0_REG08__BADINSTRP:
7654             /* ignored */
7655             register_name = "BadInstrP";
7656             break;
7657         case CP0_REG08__BADINSTRX:
7658             /* ignored */
7659             register_name = "BadInstrX";
7660             break;
7661         default:
7662             goto cp0_unimplemented;
7663         }
7664         break;
7665     case CP0_REGISTER_09:
7666         switch (sel) {
7667         case CP0_REG09__COUNT:
7668             gen_helper_mtc0_count(tcg_env, arg);
7669             register_name = "Count";
7670             break;
7671         default:
7672             goto cp0_unimplemented;
7673         }
7674         /* Stop translation as we may have switched the execution mode */
7675         ctx->base.is_jmp = DISAS_STOP;
7676         break;
7677     case CP0_REGISTER_10:
7678         switch (sel) {
7679         case CP0_REG10__ENTRYHI:
7680             gen_helper_mtc0_entryhi(tcg_env, arg);
7681             register_name = "EntryHi";
7682             break;
7683         default:
7684             goto cp0_unimplemented;
7685         }
7686         break;
7687     case CP0_REGISTER_11:
7688         switch (sel) {
7689         case CP0_REG11__COMPARE:
7690             gen_helper_mtc0_compare(tcg_env, arg);
7691             register_name = "Compare";
7692             break;
7693         /* 6,7 are implementation dependent */
7694         default:
7695             goto cp0_unimplemented;
7696         }
7697         /* Stop translation as we may have switched the execution mode */
7698         ctx->base.is_jmp = DISAS_STOP;
7699         break;
7700     case CP0_REGISTER_12:
7701         switch (sel) {
7702         case CP0_REG12__STATUS:
7703             save_cpu_state(ctx, 1);
7704             gen_helper_mtc0_status(tcg_env, arg);
7705             /* DISAS_STOP isn't good enough here, hflags may have changed. */
7706             gen_save_pc(ctx->base.pc_next + 4);
7707             ctx->base.is_jmp = DISAS_EXIT;
7708             register_name = "Status";
7709             break;
7710         case CP0_REG12__INTCTL:
7711             check_insn(ctx, ISA_MIPS_R2);
7712             gen_helper_mtc0_intctl(tcg_env, arg);
7713             /* Stop translation as we may have switched the execution mode */
7714             ctx->base.is_jmp = DISAS_STOP;
7715             register_name = "IntCtl";
7716             break;
7717         case CP0_REG12__SRSCTL:
7718             check_insn(ctx, ISA_MIPS_R2);
7719             gen_helper_mtc0_srsctl(tcg_env, arg);
7720             /* Stop translation as we may have switched the execution mode */
7721             ctx->base.is_jmp = DISAS_STOP;
7722             register_name = "SRSCtl";
7723             break;
7724         case CP0_REG12__SRSMAP:
7725             check_insn(ctx, ISA_MIPS_R2);
7726             gen_mtc0_store32(arg, offsetof(CPUMIPSState, CP0_SRSMap));
7727             /* Stop translation as we may have switched the execution mode */
7728             ctx->base.is_jmp = DISAS_STOP;
7729             register_name = "SRSMap";
7730             break;
7731         default:
7732             goto cp0_unimplemented;
7733         }
7734         break;
7735     case CP0_REGISTER_13:
7736         switch (sel) {
7737         case CP0_REG13__CAUSE:
7738             save_cpu_state(ctx, 1);
7739             gen_helper_mtc0_cause(tcg_env, arg);
7740             /*
7741              * Stop translation as we may have triggered an interrupt.
7742              * DISAS_STOP isn't sufficient, we need to ensure we break out of
7743              * translated code to check for pending interrupts.
7744              */
7745             gen_save_pc(ctx->base.pc_next + 4);
7746             ctx->base.is_jmp = DISAS_EXIT;
7747             register_name = "Cause";
7748             break;
7749         default:
7750             goto cp0_unimplemented;
7751         }
7752         break;
7753     case CP0_REGISTER_14:
7754         switch (sel) {
7755         case CP0_REG14__EPC:
7756             tcg_gen_st_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_EPC));
7757             register_name = "EPC";
7758             break;
7759         default:
7760             goto cp0_unimplemented;
7761         }
7762         break;
7763     case CP0_REGISTER_15:
7764         switch (sel) {
7765         case CP0_REG15__PRID:
7766             /* ignored */
7767             register_name = "PRid";
7768             break;
7769         case CP0_REG15__EBASE:
7770             check_insn(ctx, ISA_MIPS_R2);
7771             gen_helper_mtc0_ebase(tcg_env, arg);
7772             register_name = "EBase";
7773             break;
7774         default:
7775             goto cp0_unimplemented;
7776         }
7777         break;
7778     case CP0_REGISTER_16:
7779         switch (sel) {
7780         case CP0_REG16__CONFIG:
7781             gen_helper_mtc0_config0(tcg_env, arg);
7782             register_name = "Config";
7783             /* Stop translation as we may have switched the execution mode */
7784             ctx->base.is_jmp = DISAS_STOP;
7785             break;
7786         case CP0_REG16__CONFIG1:
7787             /* ignored, read only */
7788             register_name = "Config1";
7789             break;
7790         case CP0_REG16__CONFIG2:
7791             gen_helper_mtc0_config2(tcg_env, arg);
7792             register_name = "Config2";
7793             /* Stop translation as we may have switched the execution mode */
7794             ctx->base.is_jmp = DISAS_STOP;
7795             break;
7796         case CP0_REG16__CONFIG3:
7797             gen_helper_mtc0_config3(tcg_env, arg);
7798             register_name = "Config3";
7799             /* Stop translation as we may have switched the execution mode */
7800             ctx->base.is_jmp = DISAS_STOP;
7801             break;
7802         case CP0_REG16__CONFIG4:
7803             /* currently ignored */
7804             register_name = "Config4";
7805             break;
7806         case CP0_REG16__CONFIG5:
7807             gen_helper_mtc0_config5(tcg_env, arg);
7808             register_name = "Config5";
7809             /* Stop translation as we may have switched the execution mode */
7810             ctx->base.is_jmp = DISAS_STOP;
7811             break;
7812         /* 6,7 are implementation dependent */
7813         default:
7814             register_name = "Invalid config selector";
7815             goto cp0_unimplemented;
7816         }
7817         break;
7818     case CP0_REGISTER_17:
7819         switch (sel) {
7820         case CP0_REG17__LLADDR:
7821             gen_helper_mtc0_lladdr(tcg_env, arg);
7822             register_name = "LLAddr";
7823             break;
7824         case CP0_REG17__MAAR:
7825             CP0_CHECK(ctx->mrp);
7826             gen_helper_mtc0_maar(tcg_env, arg);
7827             register_name = "MAAR";
7828             break;
7829         case CP0_REG17__MAARI:
7830             CP0_CHECK(ctx->mrp);
7831             gen_helper_mtc0_maari(tcg_env, arg);
7832             register_name = "MAARI";
7833             break;
7834         default:
7835             goto cp0_unimplemented;
7836         }
7837         break;
7838     case CP0_REGISTER_18:
7839         switch (sel) {
7840         case CP0_REG18__WATCHLO0:
7841         case CP0_REG18__WATCHLO1:
7842         case CP0_REG18__WATCHLO2:
7843         case CP0_REG18__WATCHLO3:
7844         case CP0_REG18__WATCHLO4:
7845         case CP0_REG18__WATCHLO5:
7846         case CP0_REG18__WATCHLO6:
7847         case CP0_REG18__WATCHLO7:
7848             CP0_CHECK(ctx->CP0_Config1 & (1 << CP0C1_WR));
7849             gen_helper_0e1i(mtc0_watchlo, arg, sel);
7850             register_name = "WatchLo";
7851             break;
7852         default:
7853             goto cp0_unimplemented;
7854         }
7855         break;
7856     case CP0_REGISTER_19:
7857         switch (sel) {
7858         case CP0_REG19__WATCHHI0:
7859         case CP0_REG19__WATCHHI1:
7860         case CP0_REG19__WATCHHI2:
7861         case CP0_REG19__WATCHHI3:
7862         case CP0_REG19__WATCHHI4:
7863         case CP0_REG19__WATCHHI5:
7864         case CP0_REG19__WATCHHI6:
7865         case CP0_REG19__WATCHHI7:
7866             CP0_CHECK(ctx->CP0_Config1 & (1 << CP0C1_WR));
7867             gen_helper_0e1i(mtc0_watchhi, arg, sel);
7868             register_name = "WatchHi";
7869             break;
7870         default:
7871             goto cp0_unimplemented;
7872         }
7873         break;
7874     case CP0_REGISTER_20:
7875         switch (sel) {
7876         case CP0_REG20__XCONTEXT:
7877             check_insn(ctx, ISA_MIPS3);
7878             gen_helper_mtc0_xcontext(tcg_env, arg);
7879             register_name = "XContext";
7880             break;
7881         default:
7882             goto cp0_unimplemented;
7883         }
7884         break;
7885     case CP0_REGISTER_21:
7886        /* Officially reserved, but sel 0 is used for R1x000 framemask */
7887         CP0_CHECK(!(ctx->insn_flags & ISA_MIPS_R6));
7888         switch (sel) {
7889         case 0:
7890             gen_helper_mtc0_framemask(tcg_env, arg);
7891             register_name = "Framemask";
7892             break;
7893         default:
7894             goto cp0_unimplemented;
7895         }
7896         break;
7897     case CP0_REGISTER_22:
7898         /* ignored */
7899         register_name = "Diagnostic"; /* implementation dependent */
7900         break;
7901     case CP0_REGISTER_23:
7902         switch (sel) {
7903         case CP0_REG23__DEBUG:
7904             gen_helper_mtc0_debug(tcg_env, arg); /* EJTAG support */
7905             /* DISAS_STOP isn't good enough here, hflags may have changed. */
7906             gen_save_pc(ctx->base.pc_next + 4);
7907             ctx->base.is_jmp = DISAS_EXIT;
7908             register_name = "Debug";
7909             break;
7910         case CP0_REG23__TRACECONTROL:
7911             /* PDtrace support */
7912             /* gen_helper_mtc0_tracecontrol(tcg_env, arg);  */
7913             /* Stop translation as we may have switched the execution mode */
7914             ctx->base.is_jmp = DISAS_STOP;
7915             register_name = "TraceControl";
7916             goto cp0_unimplemented;
7917         case CP0_REG23__TRACECONTROL2:
7918             /* PDtrace support */
7919             /* gen_helper_mtc0_tracecontrol2(tcg_env, arg); */
7920             /* Stop translation as we may have switched the execution mode */
7921             ctx->base.is_jmp = DISAS_STOP;
7922             register_name = "TraceControl2";
7923             goto cp0_unimplemented;
7924         case CP0_REG23__USERTRACEDATA1:
7925             /* PDtrace support */
7926             /* gen_helper_mtc0_usertracedata1(tcg_env, arg);*/
7927             /* Stop translation as we may have switched the execution mode */
7928             ctx->base.is_jmp = DISAS_STOP;
7929             register_name = "UserTraceData1";
7930             goto cp0_unimplemented;
7931         case CP0_REG23__TRACEIBPC:
7932             /* PDtrace support */
7933             /* gen_helper_mtc0_traceibpc(tcg_env, arg);     */
7934             /* Stop translation as we may have switched the execution mode */
7935             ctx->base.is_jmp = DISAS_STOP;
7936             register_name = "TraceIBPC";
7937             goto cp0_unimplemented;
7938         case CP0_REG23__TRACEDBPC:
7939             /* PDtrace support */
7940             /* gen_helper_mtc0_tracedbpc(tcg_env, arg);     */
7941             /* Stop translation as we may have switched the execution mode */
7942             ctx->base.is_jmp = DISAS_STOP;
7943             register_name = "TraceDBPC";
7944             goto cp0_unimplemented;
7945         default:
7946             goto cp0_unimplemented;
7947         }
7948         break;
7949     case CP0_REGISTER_24:
7950         switch (sel) {
7951         case CP0_REG24__DEPC:
7952             /* EJTAG support */
7953             tcg_gen_st_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_DEPC));
7954             register_name = "DEPC";
7955             break;
7956         default:
7957             goto cp0_unimplemented;
7958         }
7959         break;
7960     case CP0_REGISTER_25:
7961         switch (sel) {
7962         case CP0_REG25__PERFCTL0:
7963             gen_helper_mtc0_performance0(tcg_env, arg);
7964             register_name = "Performance0";
7965             break;
7966         case CP0_REG25__PERFCNT0:
7967             /* gen_helper_mtc0_performance1(tcg_env, arg); */
7968             register_name = "Performance1";
7969             goto cp0_unimplemented;
7970         case CP0_REG25__PERFCTL1:
7971             /* gen_helper_mtc0_performance2(tcg_env, arg); */
7972             register_name = "Performance2";
7973             goto cp0_unimplemented;
7974         case CP0_REG25__PERFCNT1:
7975             /* gen_helper_mtc0_performance3(tcg_env, arg); */
7976             register_name = "Performance3";
7977             goto cp0_unimplemented;
7978         case CP0_REG25__PERFCTL2:
7979             /* gen_helper_mtc0_performance4(tcg_env, arg); */
7980             register_name = "Performance4";
7981             goto cp0_unimplemented;
7982         case CP0_REG25__PERFCNT2:
7983             /* gen_helper_mtc0_performance5(tcg_env, arg); */
7984             register_name = "Performance5";
7985             goto cp0_unimplemented;
7986         case CP0_REG25__PERFCTL3:
7987             /* gen_helper_mtc0_performance6(tcg_env, arg); */
7988             register_name = "Performance6";
7989             goto cp0_unimplemented;
7990         case CP0_REG25__PERFCNT3:
7991             /* gen_helper_mtc0_performance7(tcg_env, arg); */
7992             register_name = "Performance7";
7993             goto cp0_unimplemented;
7994         default:
7995             goto cp0_unimplemented;
7996         }
7997         break;
7998     case CP0_REGISTER_26:
7999         switch (sel) {
8000         case CP0_REG26__ERRCTL:
8001             gen_helper_mtc0_errctl(tcg_env, arg);
8002             ctx->base.is_jmp = DISAS_STOP;
8003             register_name = "ErrCtl";
8004             break;
8005         default:
8006             goto cp0_unimplemented;
8007         }
8008         break;
8009     case CP0_REGISTER_27:
8010         switch (sel) {
8011         case CP0_REG27__CACHERR:
8012             /* ignored */
8013             register_name = "CacheErr";
8014             break;
8015         default:
8016             goto cp0_unimplemented;
8017         }
8018         break;
8019     case CP0_REGISTER_28:
8020         switch (sel) {
8021         case CP0_REG28__TAGLO:
8022         case CP0_REG28__TAGLO1:
8023         case CP0_REG28__TAGLO2:
8024         case CP0_REG28__TAGLO3:
8025             gen_helper_mtc0_taglo(tcg_env, arg);
8026             register_name = "TagLo";
8027             break;
8028         case CP0_REG28__DATALO:
8029         case CP0_REG28__DATALO1:
8030         case CP0_REG28__DATALO2:
8031         case CP0_REG28__DATALO3:
8032             gen_helper_mtc0_datalo(tcg_env, arg);
8033             register_name = "DataLo";
8034             break;
8035         default:
8036             goto cp0_unimplemented;
8037         }
8038         break;
8039     case CP0_REGISTER_29:
8040         switch (sel) {
8041         case CP0_REG29__TAGHI:
8042         case CP0_REG29__TAGHI1:
8043         case CP0_REG29__TAGHI2:
8044         case CP0_REG29__TAGHI3:
8045             gen_helper_mtc0_taghi(tcg_env, arg);
8046             register_name = "TagHi";
8047             break;
8048         case CP0_REG29__DATAHI:
8049         case CP0_REG29__DATAHI1:
8050         case CP0_REG29__DATAHI2:
8051         case CP0_REG29__DATAHI3:
8052             gen_helper_mtc0_datahi(tcg_env, arg);
8053             register_name = "DataHi";
8054             break;
8055         default:
8056             register_name = "invalid sel";
8057             goto cp0_unimplemented;
8058         }
8059         break;
8060     case CP0_REGISTER_30:
8061         switch (sel) {
8062         case CP0_REG30__ERROREPC:
8063             tcg_gen_st_tl(arg, tcg_env, offsetof(CPUMIPSState, CP0_ErrorEPC));
8064             register_name = "ErrorEPC";
8065             break;
8066         default:
8067             goto cp0_unimplemented;
8068         }
8069         break;
8070     case CP0_REGISTER_31:
8071         switch (sel) {
8072         case CP0_REG31__DESAVE:
8073             /* EJTAG support */
8074             gen_mtc0_store32(arg, offsetof(CPUMIPSState, CP0_DESAVE));
8075             register_name = "DESAVE";
8076             break;
8077         case CP0_REG31__KSCRATCH1:
8078         case CP0_REG31__KSCRATCH2:
8079         case CP0_REG31__KSCRATCH3:
8080         case CP0_REG31__KSCRATCH4:
8081         case CP0_REG31__KSCRATCH5:
8082         case CP0_REG31__KSCRATCH6:
8083             CP0_CHECK(ctx->kscrexist & (1 << sel));
8084             tcg_gen_st_tl(arg, tcg_env,
8085                           offsetof(CPUMIPSState, CP0_KScratch[sel - 2]));
8086             register_name = "KScratch";
8087             break;
8088         default:
8089             goto cp0_unimplemented;
8090         }
8091         break;
8092     default:
8093         goto cp0_unimplemented;
8094     }
8095     trace_mips_translate_c0("dmtc0", register_name, reg, sel);
8096 
8097     /* For simplicity assume that all writes can cause interrupts.  */
8098     if (icount) {
8099         /*
8100          * DISAS_STOP isn't sufficient, we need to ensure we break out of
8101          * translated code to check for pending interrupts.
8102          */
8103         gen_save_pc(ctx->base.pc_next + 4);
8104         ctx->base.is_jmp = DISAS_EXIT;
8105     }
8106     return;
8107 
8108 cp0_unimplemented:
8109     qemu_log_mask(LOG_UNIMP, "dmtc0 %s (reg %d sel %d)\n",
8110                   register_name, reg, sel);
8111 }
8112 #endif /* TARGET_MIPS64 */
8113 
8114 static void gen_mftr(CPUMIPSState *env, DisasContext *ctx, int rt, int rd,
8115                      int u, int sel, int h)
8116 {
8117     int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
8118     TCGv t0 = tcg_temp_new();
8119 
8120     if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
8121         ((env->tcs[other_tc].CP0_TCBind & (0xf << CP0TCBd_CurVPE)) !=
8122          (env->active_tc.CP0_TCBind & (0xf << CP0TCBd_CurVPE)))) {
8123         tcg_gen_movi_tl(t0, -1);
8124     } else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
8125                (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC))) {
8126         tcg_gen_movi_tl(t0, -1);
8127     } else if (u == 0) {
8128         switch (rt) {
8129         case 1:
8130             switch (sel) {
8131             case 1:
8132                 gen_helper_mftc0_vpecontrol(t0, tcg_env);
8133                 break;
8134             case 2:
8135                 gen_helper_mftc0_vpeconf0(t0, tcg_env);
8136                 break;
8137             default:
8138                 goto die;
8139                 break;
8140             }
8141             break;
8142         case 2:
8143             switch (sel) {
8144             case 1:
8145                 gen_helper_mftc0_tcstatus(t0, tcg_env);
8146                 break;
8147             case 2:
8148                 gen_helper_mftc0_tcbind(t0, tcg_env);
8149                 break;
8150             case 3:
8151                 gen_helper_mftc0_tcrestart(t0, tcg_env);
8152                 break;
8153             case 4:
8154                 gen_helper_mftc0_tchalt(t0, tcg_env);
8155                 break;
8156             case 5:
8157                 gen_helper_mftc0_tccontext(t0, tcg_env);
8158                 break;
8159             case 6:
8160                 gen_helper_mftc0_tcschedule(t0, tcg_env);
8161                 break;
8162             case 7:
8163                 gen_helper_mftc0_tcschefback(t0, tcg_env);
8164                 break;
8165             default:
8166                 gen_mfc0(ctx, t0, rt, sel);
8167                 break;
8168             }
8169             break;
8170         case 10:
8171             switch (sel) {
8172             case 0:
8173                 gen_helper_mftc0_entryhi(t0, tcg_env);
8174                 break;
8175             default:
8176                 gen_mfc0(ctx, t0, rt, sel);
8177                 break;
8178             }
8179             break;
8180         case 12:
8181             switch (sel) {
8182             case 0:
8183                 gen_helper_mftc0_status(t0, tcg_env);
8184                 break;
8185             default:
8186                 gen_mfc0(ctx, t0, rt, sel);
8187                 break;
8188             }
8189             break;
8190         case 13:
8191             switch (sel) {
8192             case 0:
8193                 gen_helper_mftc0_cause(t0, tcg_env);
8194                 break;
8195             default:
8196                 goto die;
8197                 break;
8198             }
8199             break;
8200         case 14:
8201             switch (sel) {
8202             case 0:
8203                 gen_helper_mftc0_epc(t0, tcg_env);
8204                 break;
8205             default:
8206                 goto die;
8207                 break;
8208             }
8209             break;
8210         case 15:
8211             switch (sel) {
8212             case 1:
8213                 gen_helper_mftc0_ebase(t0, tcg_env);
8214                 break;
8215             default:
8216                 goto die;
8217                 break;
8218             }
8219             break;
8220         case 16:
8221             switch (sel) {
8222             case 0:
8223             case 1:
8224             case 2:
8225             case 3:
8226             case 4:
8227             case 5:
8228             case 6:
8229             case 7:
8230                 gen_helper_mftc0_configx(t0, tcg_env, tcg_constant_tl(sel));
8231                 break;
8232             default:
8233                 goto die;
8234                 break;
8235             }
8236             break;
8237         case 23:
8238             switch (sel) {
8239             case 0:
8240                 gen_helper_mftc0_debug(t0, tcg_env);
8241                 break;
8242             default:
8243                 gen_mfc0(ctx, t0, rt, sel);
8244                 break;
8245             }
8246             break;
8247         default:
8248             gen_mfc0(ctx, t0, rt, sel);
8249         }
8250     } else {
8251         switch (sel) {
8252         /* GPR registers. */
8253         case 0:
8254             gen_helper_1e0i(mftgpr, t0, rt);
8255             break;
8256         /* Auxiliary CPU registers */
8257         case 1:
8258             switch (rt) {
8259             case 0:
8260                 gen_helper_1e0i(mftlo, t0, 0);
8261                 break;
8262             case 1:
8263                 gen_helper_1e0i(mfthi, t0, 0);
8264                 break;
8265             case 2:
8266                 gen_helper_1e0i(mftacx, t0, 0);
8267                 break;
8268             case 4:
8269                 gen_helper_1e0i(mftlo, t0, 1);
8270                 break;
8271             case 5:
8272                 gen_helper_1e0i(mfthi, t0, 1);
8273                 break;
8274             case 6:
8275                 gen_helper_1e0i(mftacx, t0, 1);
8276                 break;
8277             case 8:
8278                 gen_helper_1e0i(mftlo, t0, 2);
8279                 break;
8280             case 9:
8281                 gen_helper_1e0i(mfthi, t0, 2);
8282                 break;
8283             case 10:
8284                 gen_helper_1e0i(mftacx, t0, 2);
8285                 break;
8286             case 12:
8287                 gen_helper_1e0i(mftlo, t0, 3);
8288                 break;
8289             case 13:
8290                 gen_helper_1e0i(mfthi, t0, 3);
8291                 break;
8292             case 14:
8293                 gen_helper_1e0i(mftacx, t0, 3);
8294                 break;
8295             case 16:
8296                 gen_helper_mftdsp(t0, tcg_env);
8297                 break;
8298             default:
8299                 goto die;
8300             }
8301             break;
8302         /* Floating point (COP1). */
8303         case 2:
8304             /* XXX: For now we support only a single FPU context. */
8305             if (h == 0) {
8306                 TCGv_i32 fp0 = tcg_temp_new_i32();
8307 
8308                 gen_load_fpr32(ctx, fp0, rt);
8309                 tcg_gen_ext_i32_tl(t0, fp0);
8310             } else {
8311                 TCGv_i32 fp0 = tcg_temp_new_i32();
8312 
8313                 gen_load_fpr32h(ctx, fp0, rt);
8314                 tcg_gen_ext_i32_tl(t0, fp0);
8315             }
8316             break;
8317         case 3:
8318             /* XXX: For now we support only a single FPU context. */
8319             gen_helper_1e0i(cfc1, t0, rt);
8320             break;
8321         /* COP2: Not implemented. */
8322         case 4:
8323         case 5:
8324             /* fall through */
8325         default:
8326             goto die;
8327         }
8328     }
8329     trace_mips_translate_tr("mftr", rt, u, sel, h);
8330     gen_store_gpr(t0, rd);
8331     return;
8332 
8333 die:
8334     LOG_DISAS("mftr (reg %d u %d sel %d h %d)\n", rt, u, sel, h);
8335     gen_reserved_instruction(ctx);
8336 }
8337 
8338 static void gen_mttr(CPUMIPSState *env, DisasContext *ctx, int rd, int rt,
8339                      int u, int sel, int h)
8340 {
8341     int other_tc = env->CP0_VPEControl & (0xff << CP0VPECo_TargTC);
8342     TCGv t0 = tcg_temp_new();
8343 
8344     gen_load_gpr(t0, rt);
8345     if ((env->CP0_VPEConf0 & (1 << CP0VPEC0_MVP)) == 0 &&
8346         ((env->tcs[other_tc].CP0_TCBind & (0xf << CP0TCBd_CurVPE)) !=
8347          (env->active_tc.CP0_TCBind & (0xf << CP0TCBd_CurVPE)))) {
8348         /* NOP */
8349         ;
8350     } else if ((env->CP0_VPEControl & (0xff << CP0VPECo_TargTC)) >
8351              (env->mvp->CP0_MVPConf0 & (0xff << CP0MVPC0_PTC))) {
8352         /* NOP */
8353         ;
8354     } else if (u == 0) {
8355         switch (rd) {
8356         case 1:
8357             switch (sel) {
8358             case 1:
8359                 gen_helper_mttc0_vpecontrol(tcg_env, t0);
8360                 break;
8361             case 2:
8362                 gen_helper_mttc0_vpeconf0(tcg_env, t0);
8363                 break;
8364             default:
8365                 goto die;
8366                 break;
8367             }
8368             break;
8369         case 2:
8370             switch (sel) {
8371             case 1:
8372                 gen_helper_mttc0_tcstatus(tcg_env, t0);
8373                 break;
8374             case 2:
8375                 gen_helper_mttc0_tcbind(tcg_env, t0);
8376                 break;
8377             case 3:
8378                 gen_helper_mttc0_tcrestart(tcg_env, t0);
8379                 break;
8380             case 4:
8381                 gen_helper_mttc0_tchalt(tcg_env, t0);
8382                 break;
8383             case 5:
8384                 gen_helper_mttc0_tccontext(tcg_env, t0);
8385                 break;
8386             case 6:
8387                 gen_helper_mttc0_tcschedule(tcg_env, t0);
8388                 break;
8389             case 7:
8390                 gen_helper_mttc0_tcschefback(tcg_env, t0);
8391                 break;
8392             default:
8393                 gen_mtc0(ctx, t0, rd, sel);
8394                 break;
8395             }
8396             break;
8397         case 10:
8398             switch (sel) {
8399             case 0:
8400                 gen_helper_mttc0_entryhi(tcg_env, t0);
8401                 break;
8402             default:
8403                 gen_mtc0(ctx, t0, rd, sel);
8404                 break;
8405             }
8406             break;
8407         case 12:
8408             switch (sel) {
8409             case 0:
8410                 gen_helper_mttc0_status(tcg_env, t0);
8411                 break;
8412             default:
8413                 gen_mtc0(ctx, t0, rd, sel);
8414                 break;
8415             }
8416             break;
8417         case 13:
8418             switch (sel) {
8419             case 0:
8420                 gen_helper_mttc0_cause(tcg_env, t0);
8421                 break;
8422             default:
8423                 goto die;
8424                 break;
8425             }
8426             break;
8427         case 15:
8428             switch (sel) {
8429             case 1:
8430                 gen_helper_mttc0_ebase(tcg_env, t0);
8431                 break;
8432             default:
8433                 goto die;
8434                 break;
8435             }
8436             break;
8437         case 23:
8438             switch (sel) {
8439             case 0:
8440                 gen_helper_mttc0_debug(tcg_env, t0);
8441                 break;
8442             default:
8443                 gen_mtc0(ctx, t0, rd, sel);
8444                 break;
8445             }
8446             break;
8447         default:
8448             gen_mtc0(ctx, t0, rd, sel);
8449         }
8450     } else {
8451         switch (sel) {
8452         /* GPR registers. */
8453         case 0:
8454             gen_helper_0e1i(mttgpr, t0, rd);
8455             break;
8456         /* Auxiliary CPU registers */
8457         case 1:
8458             switch (rd) {
8459             case 0:
8460                 gen_helper_0e1i(mttlo, t0, 0);
8461                 break;
8462             case 1:
8463                 gen_helper_0e1i(mtthi, t0, 0);
8464                 break;
8465             case 2:
8466                 gen_helper_0e1i(mttacx, t0, 0);
8467                 break;
8468             case 4:
8469                 gen_helper_0e1i(mttlo, t0, 1);
8470                 break;
8471             case 5:
8472                 gen_helper_0e1i(mtthi, t0, 1);
8473                 break;
8474             case 6:
8475                 gen_helper_0e1i(mttacx, t0, 1);
8476                 break;
8477             case 8:
8478                 gen_helper_0e1i(mttlo, t0, 2);
8479                 break;
8480             case 9:
8481                 gen_helper_0e1i(mtthi, t0, 2);
8482                 break;
8483             case 10:
8484                 gen_helper_0e1i(mttacx, t0, 2);
8485                 break;
8486             case 12:
8487                 gen_helper_0e1i(mttlo, t0, 3);
8488                 break;
8489             case 13:
8490                 gen_helper_0e1i(mtthi, t0, 3);
8491                 break;
8492             case 14:
8493                 gen_helper_0e1i(mttacx, t0, 3);
8494                 break;
8495             case 16:
8496                 gen_helper_mttdsp(tcg_env, t0);
8497                 break;
8498             default:
8499                 goto die;
8500             }
8501             break;
8502         /* Floating point (COP1). */
8503         case 2:
8504             /* XXX: For now we support only a single FPU context. */
8505             if (h == 0) {
8506                 TCGv_i32 fp0 = tcg_temp_new_i32();
8507 
8508                 tcg_gen_trunc_tl_i32(fp0, t0);
8509                 gen_store_fpr32(ctx, fp0, rd);
8510             } else {
8511                 TCGv_i32 fp0 = tcg_temp_new_i32();
8512 
8513                 tcg_gen_trunc_tl_i32(fp0, t0);
8514                 gen_store_fpr32h(ctx, fp0, rd);
8515             }
8516             break;
8517         case 3:
8518             /* XXX: For now we support only a single FPU context. */
8519             gen_helper_0e2i(ctc1, t0, tcg_constant_i32(rd), rt);
8520             /* Stop translation as we may have changed hflags */
8521             ctx->base.is_jmp = DISAS_STOP;
8522             break;
8523         /* COP2: Not implemented. */
8524         case 4:
8525         case 5:
8526             /* fall through */
8527         default:
8528             goto die;
8529         }
8530     }
8531     trace_mips_translate_tr("mttr", rd, u, sel, h);
8532     return;
8533 
8534 die:
8535     LOG_DISAS("mttr (reg %d u %d sel %d h %d)\n", rd, u, sel, h);
8536     gen_reserved_instruction(ctx);
8537 }
8538 
8539 static void gen_cp0(CPUMIPSState *env, DisasContext *ctx, uint32_t opc,
8540                     int rt, int rd)
8541 {
8542     const char *opn = "ldst";
8543 
8544     check_cp0_enabled(ctx);
8545     switch (opc) {
8546     case OPC_MFC0:
8547         if (rt == 0) {
8548             /* Treat as NOP. */
8549             return;
8550         }
8551         gen_mfc0(ctx, cpu_gpr[rt], rd, ctx->opcode & 0x7);
8552         opn = "mfc0";
8553         break;
8554     case OPC_MTC0:
8555         {
8556             TCGv t0 = tcg_temp_new();
8557 
8558             gen_load_gpr(t0, rt);
8559             gen_mtc0(ctx, t0, rd, ctx->opcode & 0x7);
8560         }
8561         opn = "mtc0";
8562         break;
8563 #if defined(TARGET_MIPS64)
8564     case OPC_DMFC0:
8565         check_insn(ctx, ISA_MIPS3);
8566         if (rt == 0) {
8567             /* Treat as NOP. */
8568             return;
8569         }
8570         gen_dmfc0(ctx, cpu_gpr[rt], rd, ctx->opcode & 0x7);
8571         opn = "dmfc0";
8572         break;
8573     case OPC_DMTC0:
8574         check_insn(ctx, ISA_MIPS3);
8575         {
8576             TCGv t0 = tcg_temp_new();
8577 
8578             gen_load_gpr(t0, rt);
8579             gen_dmtc0(ctx, t0, rd, ctx->opcode & 0x7);
8580         }
8581         opn = "dmtc0";
8582         break;
8583 #endif
8584     case OPC_MFHC0:
8585         check_mvh(ctx);
8586         if (rt == 0) {
8587             /* Treat as NOP. */
8588             return;
8589         }
8590         gen_mfhc0(ctx, cpu_gpr[rt], rd, ctx->opcode & 0x7);
8591         opn = "mfhc0";
8592         break;
8593     case OPC_MTHC0:
8594         check_mvh(ctx);
8595         {
8596             TCGv t0 = tcg_temp_new();
8597             gen_load_gpr(t0, rt);
8598             gen_mthc0(ctx, t0, rd, ctx->opcode & 0x7);
8599         }
8600         opn = "mthc0";
8601         break;
8602     case OPC_MFTR:
8603         check_cp0_enabled(ctx);
8604         if (rd == 0) {
8605             /* Treat as NOP. */
8606             return;
8607         }
8608         gen_mftr(env, ctx, rt, rd, (ctx->opcode >> 5) & 1,
8609                  ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
8610         opn = "mftr";
8611         break;
8612     case OPC_MTTR:
8613         check_cp0_enabled(ctx);
8614         gen_mttr(env, ctx, rd, rt, (ctx->opcode >> 5) & 1,
8615                  ctx->opcode & 0x7, (ctx->opcode >> 4) & 1);
8616         opn = "mttr";
8617         break;
8618     case OPC_TLBWI:
8619         opn = "tlbwi";
8620         if (!env->tlb->helper_tlbwi) {
8621             goto die;
8622         }
8623         gen_helper_tlbwi(tcg_env);
8624         break;
8625     case OPC_TLBINV:
8626         opn = "tlbinv";
8627         if (ctx->ie >= 2) {
8628             if (!env->tlb->helper_tlbinv) {
8629                 goto die;
8630             }
8631             gen_helper_tlbinv(tcg_env);
8632         } /* treat as nop if TLBINV not supported */
8633         break;
8634     case OPC_TLBINVF:
8635         opn = "tlbinvf";
8636         if (ctx->ie >= 2) {
8637             if (!env->tlb->helper_tlbinvf) {
8638                 goto die;
8639             }
8640             gen_helper_tlbinvf(tcg_env);
8641         } /* treat as nop if TLBINV not supported */
8642         break;
8643     case OPC_TLBWR:
8644         opn = "tlbwr";
8645         if (!env->tlb->helper_tlbwr) {
8646             goto die;
8647         }
8648         gen_helper_tlbwr(tcg_env);
8649         break;
8650     case OPC_TLBP:
8651         opn = "tlbp";
8652         if (!env->tlb->helper_tlbp) {
8653             goto die;
8654         }
8655         gen_helper_tlbp(tcg_env);
8656         break;
8657     case OPC_TLBR:
8658         opn = "tlbr";
8659         if (!env->tlb->helper_tlbr) {
8660             goto die;
8661         }
8662         gen_helper_tlbr(tcg_env);
8663         break;
8664     case OPC_ERET: /* OPC_ERETNC */
8665         if ((ctx->insn_flags & ISA_MIPS_R6) &&
8666             (ctx->hflags & MIPS_HFLAG_BMASK)) {
8667             goto die;
8668         } else {
8669             int bit_shift = (ctx->hflags & MIPS_HFLAG_M16) ? 16 : 6;
8670             if (ctx->opcode & (1 << bit_shift)) {
8671                 /* OPC_ERETNC */
8672                 opn = "eretnc";
8673                 check_insn(ctx, ISA_MIPS_R5);
8674                 gen_helper_eretnc(tcg_env);
8675             } else {
8676                 /* OPC_ERET */
8677                 opn = "eret";
8678                 check_insn(ctx, ISA_MIPS2);
8679                 gen_helper_eret(tcg_env);
8680             }
8681             ctx->base.is_jmp = DISAS_EXIT;
8682         }
8683         break;
8684     case OPC_DERET:
8685         opn = "deret";
8686         check_insn(ctx, ISA_MIPS_R1);
8687         if ((ctx->insn_flags & ISA_MIPS_R6) &&
8688             (ctx->hflags & MIPS_HFLAG_BMASK)) {
8689             goto die;
8690         }
8691         if (!(ctx->hflags & MIPS_HFLAG_DM)) {
8692             MIPS_INVAL(opn);
8693             gen_reserved_instruction(ctx);
8694         } else {
8695             gen_helper_deret(tcg_env);
8696             ctx->base.is_jmp = DISAS_EXIT;
8697         }
8698         break;
8699     case OPC_WAIT:
8700         opn = "wait";
8701         check_insn(ctx, ISA_MIPS3 | ISA_MIPS_R1);
8702         if ((ctx->insn_flags & ISA_MIPS_R6) &&
8703             (ctx->hflags & MIPS_HFLAG_BMASK)) {
8704             goto die;
8705         }
8706         /* If we get an exception, we want to restart at next instruction */
8707         ctx->base.pc_next += 4;
8708         save_cpu_state(ctx, 1);
8709         ctx->base.pc_next -= 4;
8710         gen_helper_wait(tcg_env);
8711         ctx->base.is_jmp = DISAS_NORETURN;
8712         break;
8713     default:
8714  die:
8715         MIPS_INVAL(opn);
8716         gen_reserved_instruction(ctx);
8717         return;
8718     }
8719     (void)opn; /* avoid a compiler warning */
8720 }
8721 #endif /* !CONFIG_USER_ONLY */
8722 
8723 /* CP1 Branches (before delay slot) */
8724 static void gen_compute_branch1(DisasContext *ctx, uint32_t op,
8725                                 int32_t cc, int32_t offset)
8726 {
8727     target_ulong btarget;
8728     TCGv_i32 t0 = tcg_temp_new_i32();
8729 
8730     if ((ctx->insn_flags & ISA_MIPS_R6) && (ctx->hflags & MIPS_HFLAG_BMASK)) {
8731         gen_reserved_instruction(ctx);
8732         return;
8733     }
8734 
8735     if (cc != 0) {
8736         check_insn(ctx, ISA_MIPS4 | ISA_MIPS_R1);
8737     }
8738 
8739     btarget = ctx->base.pc_next + 4 + offset;
8740 
8741     switch (op) {
8742     case OPC_BC1F:
8743         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
8744         tcg_gen_not_i32(t0, t0);
8745         tcg_gen_andi_i32(t0, t0, 1);
8746         tcg_gen_extu_i32_tl(bcond, t0);
8747         goto not_likely;
8748     case OPC_BC1FL:
8749         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
8750         tcg_gen_not_i32(t0, t0);
8751         tcg_gen_andi_i32(t0, t0, 1);
8752         tcg_gen_extu_i32_tl(bcond, t0);
8753         goto likely;
8754     case OPC_BC1T:
8755         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
8756         tcg_gen_andi_i32(t0, t0, 1);
8757         tcg_gen_extu_i32_tl(bcond, t0);
8758         goto not_likely;
8759     case OPC_BC1TL:
8760         tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
8761         tcg_gen_andi_i32(t0, t0, 1);
8762         tcg_gen_extu_i32_tl(bcond, t0);
8763     likely:
8764         ctx->hflags |= MIPS_HFLAG_BL;
8765         break;
8766     case OPC_BC1FANY2:
8767         {
8768             TCGv_i32 t1 = tcg_temp_new_i32();
8769             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
8770             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc + 1));
8771             tcg_gen_nand_i32(t0, t0, t1);
8772             tcg_gen_andi_i32(t0, t0, 1);
8773             tcg_gen_extu_i32_tl(bcond, t0);
8774         }
8775         goto not_likely;
8776     case OPC_BC1TANY2:
8777         {
8778             TCGv_i32 t1 = tcg_temp_new_i32();
8779             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
8780             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc + 1));
8781             tcg_gen_or_i32(t0, t0, t1);
8782             tcg_gen_andi_i32(t0, t0, 1);
8783             tcg_gen_extu_i32_tl(bcond, t0);
8784         }
8785         goto not_likely;
8786     case OPC_BC1FANY4:
8787         {
8788             TCGv_i32 t1 = tcg_temp_new_i32();
8789             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
8790             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc + 1));
8791             tcg_gen_and_i32(t0, t0, t1);
8792             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc + 2));
8793             tcg_gen_and_i32(t0, t0, t1);
8794             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc + 3));
8795             tcg_gen_nand_i32(t0, t0, t1);
8796             tcg_gen_andi_i32(t0, t0, 1);
8797             tcg_gen_extu_i32_tl(bcond, t0);
8798         }
8799         goto not_likely;
8800     case OPC_BC1TANY4:
8801         {
8802             TCGv_i32 t1 = tcg_temp_new_i32();
8803             tcg_gen_shri_i32(t0, fpu_fcr31, get_fp_bit(cc));
8804             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc + 1));
8805             tcg_gen_or_i32(t0, t0, t1);
8806             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc + 2));
8807             tcg_gen_or_i32(t0, t0, t1);
8808             tcg_gen_shri_i32(t1, fpu_fcr31, get_fp_bit(cc + 3));
8809             tcg_gen_or_i32(t0, t0, t1);
8810             tcg_gen_andi_i32(t0, t0, 1);
8811             tcg_gen_extu_i32_tl(bcond, t0);
8812         }
8813     not_likely:
8814         ctx->hflags |= MIPS_HFLAG_BC;
8815         break;
8816     default:
8817         MIPS_INVAL("cp1 cond branch");
8818         gen_reserved_instruction(ctx);
8819         return;
8820     }
8821     ctx->btarget = btarget;
8822     ctx->hflags |= MIPS_HFLAG_BDS32;
8823 }
8824 
8825 /* R6 CP1 Branches */
8826 static void gen_compute_branch1_r6(DisasContext *ctx, uint32_t op,
8827                                    int32_t ft, int32_t offset,
8828                                    int delayslot_size)
8829 {
8830     target_ulong btarget;
8831     TCGv_i64 t0 = tcg_temp_new_i64();
8832 
8833     if (ctx->hflags & MIPS_HFLAG_BMASK) {
8834 #ifdef MIPS_DEBUG_DISAS
8835         LOG_DISAS("Branch in delay / forbidden slot at PC 0x%016"
8836                   VADDR_PRIx "\n", ctx->base.pc_next);
8837 #endif
8838         gen_reserved_instruction(ctx);
8839         return;
8840     }
8841 
8842     gen_load_fpr64(ctx, t0, ft);
8843     tcg_gen_andi_i64(t0, t0, 1);
8844 
8845     btarget = addr_add(ctx, ctx->base.pc_next + 4, offset);
8846 
8847     switch (op) {
8848     case OPC_BC1EQZ:
8849         tcg_gen_xori_i64(t0, t0, 1);
8850         ctx->hflags |= MIPS_HFLAG_BC;
8851         break;
8852     case OPC_BC1NEZ:
8853         /* t0 already set */
8854         ctx->hflags |= MIPS_HFLAG_BC;
8855         break;
8856     default:
8857         MIPS_INVAL("cp1 cond branch");
8858         gen_reserved_instruction(ctx);
8859         return;
8860     }
8861 
8862     tcg_gen_trunc_i64_tl(bcond, t0);
8863 
8864     ctx->btarget = btarget;
8865 
8866     switch (delayslot_size) {
8867     case 2:
8868         ctx->hflags |= MIPS_HFLAG_BDS16;
8869         break;
8870     case 4:
8871         ctx->hflags |= MIPS_HFLAG_BDS32;
8872         break;
8873     }
8874 }
8875 
8876 /* Coprocessor 1 (FPU) */
8877 
8878 #define FOP(func, fmt) (((fmt) << 21) | (func))
8879 
8880 enum fopcode {
8881     OPC_ADD_S = FOP(0, FMT_S),
8882     OPC_SUB_S = FOP(1, FMT_S),
8883     OPC_MUL_S = FOP(2, FMT_S),
8884     OPC_DIV_S = FOP(3, FMT_S),
8885     OPC_SQRT_S = FOP(4, FMT_S),
8886     OPC_ABS_S = FOP(5, FMT_S),
8887     OPC_MOV_S = FOP(6, FMT_S),
8888     OPC_NEG_S = FOP(7, FMT_S),
8889     OPC_ROUND_L_S = FOP(8, FMT_S),
8890     OPC_TRUNC_L_S = FOP(9, FMT_S),
8891     OPC_CEIL_L_S = FOP(10, FMT_S),
8892     OPC_FLOOR_L_S = FOP(11, FMT_S),
8893     OPC_ROUND_W_S = FOP(12, FMT_S),
8894     OPC_TRUNC_W_S = FOP(13, FMT_S),
8895     OPC_CEIL_W_S = FOP(14, FMT_S),
8896     OPC_FLOOR_W_S = FOP(15, FMT_S),
8897     OPC_SEL_S = FOP(16, FMT_S),
8898     OPC_MOVCF_S = FOP(17, FMT_S),
8899     OPC_MOVZ_S = FOP(18, FMT_S),
8900     OPC_MOVN_S = FOP(19, FMT_S),
8901     OPC_SELEQZ_S = FOP(20, FMT_S),
8902     OPC_RECIP_S = FOP(21, FMT_S),
8903     OPC_RSQRT_S = FOP(22, FMT_S),
8904     OPC_SELNEZ_S = FOP(23, FMT_S),
8905     OPC_MADDF_S = FOP(24, FMT_S),
8906     OPC_MSUBF_S = FOP(25, FMT_S),
8907     OPC_RINT_S = FOP(26, FMT_S),
8908     OPC_CLASS_S = FOP(27, FMT_S),
8909     OPC_MIN_S = FOP(28, FMT_S),
8910     OPC_RECIP2_S = FOP(28, FMT_S),
8911     OPC_MINA_S = FOP(29, FMT_S),
8912     OPC_RECIP1_S = FOP(29, FMT_S),
8913     OPC_MAX_S = FOP(30, FMT_S),
8914     OPC_RSQRT1_S = FOP(30, FMT_S),
8915     OPC_MAXA_S = FOP(31, FMT_S),
8916     OPC_RSQRT2_S = FOP(31, FMT_S),
8917     OPC_CVT_D_S = FOP(33, FMT_S),
8918     OPC_CVT_W_S = FOP(36, FMT_S),
8919     OPC_CVT_L_S = FOP(37, FMT_S),
8920     OPC_CVT_PS_S = FOP(38, FMT_S),
8921     OPC_CMP_F_S = FOP(48, FMT_S),
8922     OPC_CMP_UN_S = FOP(49, FMT_S),
8923     OPC_CMP_EQ_S = FOP(50, FMT_S),
8924     OPC_CMP_UEQ_S = FOP(51, FMT_S),
8925     OPC_CMP_OLT_S = FOP(52, FMT_S),
8926     OPC_CMP_ULT_S = FOP(53, FMT_S),
8927     OPC_CMP_OLE_S = FOP(54, FMT_S),
8928     OPC_CMP_ULE_S = FOP(55, FMT_S),
8929     OPC_CMP_SF_S = FOP(56, FMT_S),
8930     OPC_CMP_NGLE_S = FOP(57, FMT_S),
8931     OPC_CMP_SEQ_S = FOP(58, FMT_S),
8932     OPC_CMP_NGL_S = FOP(59, FMT_S),
8933     OPC_CMP_LT_S = FOP(60, FMT_S),
8934     OPC_CMP_NGE_S = FOP(61, FMT_S),
8935     OPC_CMP_LE_S = FOP(62, FMT_S),
8936     OPC_CMP_NGT_S = FOP(63, FMT_S),
8937 
8938     OPC_ADD_D = FOP(0, FMT_D),
8939     OPC_SUB_D = FOP(1, FMT_D),
8940     OPC_MUL_D = FOP(2, FMT_D),
8941     OPC_DIV_D = FOP(3, FMT_D),
8942     OPC_SQRT_D = FOP(4, FMT_D),
8943     OPC_ABS_D = FOP(5, FMT_D),
8944     OPC_MOV_D = FOP(6, FMT_D),
8945     OPC_NEG_D = FOP(7, FMT_D),
8946     OPC_ROUND_L_D = FOP(8, FMT_D),
8947     OPC_TRUNC_L_D = FOP(9, FMT_D),
8948     OPC_CEIL_L_D = FOP(10, FMT_D),
8949     OPC_FLOOR_L_D = FOP(11, FMT_D),
8950     OPC_ROUND_W_D = FOP(12, FMT_D),
8951     OPC_TRUNC_W_D = FOP(13, FMT_D),
8952     OPC_CEIL_W_D = FOP(14, FMT_D),
8953     OPC_FLOOR_W_D = FOP(15, FMT_D),
8954     OPC_SEL_D = FOP(16, FMT_D),
8955     OPC_MOVCF_D = FOP(17, FMT_D),
8956     OPC_MOVZ_D = FOP(18, FMT_D),
8957     OPC_MOVN_D = FOP(19, FMT_D),
8958     OPC_SELEQZ_D = FOP(20, FMT_D),
8959     OPC_RECIP_D = FOP(21, FMT_D),
8960     OPC_RSQRT_D = FOP(22, FMT_D),
8961     OPC_SELNEZ_D = FOP(23, FMT_D),
8962     OPC_MADDF_D = FOP(24, FMT_D),
8963     OPC_MSUBF_D = FOP(25, FMT_D),
8964     OPC_RINT_D = FOP(26, FMT_D),
8965     OPC_CLASS_D = FOP(27, FMT_D),
8966     OPC_MIN_D = FOP(28, FMT_D),
8967     OPC_RECIP2_D = FOP(28, FMT_D),
8968     OPC_MINA_D = FOP(29, FMT_D),
8969     OPC_RECIP1_D = FOP(29, FMT_D),
8970     OPC_MAX_D = FOP(30, FMT_D),
8971     OPC_RSQRT1_D = FOP(30, FMT_D),
8972     OPC_MAXA_D = FOP(31, FMT_D),
8973     OPC_RSQRT2_D = FOP(31, FMT_D),
8974     OPC_CVT_S_D = FOP(32, FMT_D),
8975     OPC_CVT_W_D = FOP(36, FMT_D),
8976     OPC_CVT_L_D = FOP(37, FMT_D),
8977     OPC_CMP_F_D = FOP(48, FMT_D),
8978     OPC_CMP_UN_D = FOP(49, FMT_D),
8979     OPC_CMP_EQ_D = FOP(50, FMT_D),
8980     OPC_CMP_UEQ_D = FOP(51, FMT_D),
8981     OPC_CMP_OLT_D = FOP(52, FMT_D),
8982     OPC_CMP_ULT_D = FOP(53, FMT_D),
8983     OPC_CMP_OLE_D = FOP(54, FMT_D),
8984     OPC_CMP_ULE_D = FOP(55, FMT_D),
8985     OPC_CMP_SF_D = FOP(56, FMT_D),
8986     OPC_CMP_NGLE_D = FOP(57, FMT_D),
8987     OPC_CMP_SEQ_D = FOP(58, FMT_D),
8988     OPC_CMP_NGL_D = FOP(59, FMT_D),
8989     OPC_CMP_LT_D = FOP(60, FMT_D),
8990     OPC_CMP_NGE_D = FOP(61, FMT_D),
8991     OPC_CMP_LE_D = FOP(62, FMT_D),
8992     OPC_CMP_NGT_D = FOP(63, FMT_D),
8993 
8994     OPC_CVT_S_W = FOP(32, FMT_W),
8995     OPC_CVT_D_W = FOP(33, FMT_W),
8996     OPC_CVT_S_L = FOP(32, FMT_L),
8997     OPC_CVT_D_L = FOP(33, FMT_L),
8998     OPC_CVT_PS_PW = FOP(38, FMT_W),
8999 
9000     OPC_ADD_PS = FOP(0, FMT_PS),
9001     OPC_SUB_PS = FOP(1, FMT_PS),
9002     OPC_MUL_PS = FOP(2, FMT_PS),
9003     OPC_DIV_PS = FOP(3, FMT_PS),
9004     OPC_ABS_PS = FOP(5, FMT_PS),
9005     OPC_MOV_PS = FOP(6, FMT_PS),
9006     OPC_NEG_PS = FOP(7, FMT_PS),
9007     OPC_MOVCF_PS = FOP(17, FMT_PS),
9008     OPC_MOVZ_PS = FOP(18, FMT_PS),
9009     OPC_MOVN_PS = FOP(19, FMT_PS),
9010     OPC_ADDR_PS = FOP(24, FMT_PS),
9011     OPC_MULR_PS = FOP(26, FMT_PS),
9012     OPC_RECIP2_PS = FOP(28, FMT_PS),
9013     OPC_RECIP1_PS = FOP(29, FMT_PS),
9014     OPC_RSQRT1_PS = FOP(30, FMT_PS),
9015     OPC_RSQRT2_PS = FOP(31, FMT_PS),
9016 
9017     OPC_CVT_S_PU = FOP(32, FMT_PS),
9018     OPC_CVT_PW_PS = FOP(36, FMT_PS),
9019     OPC_CVT_S_PL = FOP(40, FMT_PS),
9020     OPC_PLL_PS = FOP(44, FMT_PS),
9021     OPC_PLU_PS = FOP(45, FMT_PS),
9022     OPC_PUL_PS = FOP(46, FMT_PS),
9023     OPC_PUU_PS = FOP(47, FMT_PS),
9024     OPC_CMP_F_PS = FOP(48, FMT_PS),
9025     OPC_CMP_UN_PS = FOP(49, FMT_PS),
9026     OPC_CMP_EQ_PS = FOP(50, FMT_PS),
9027     OPC_CMP_UEQ_PS = FOP(51, FMT_PS),
9028     OPC_CMP_OLT_PS = FOP(52, FMT_PS),
9029     OPC_CMP_ULT_PS = FOP(53, FMT_PS),
9030     OPC_CMP_OLE_PS = FOP(54, FMT_PS),
9031     OPC_CMP_ULE_PS = FOP(55, FMT_PS),
9032     OPC_CMP_SF_PS = FOP(56, FMT_PS),
9033     OPC_CMP_NGLE_PS = FOP(57, FMT_PS),
9034     OPC_CMP_SEQ_PS = FOP(58, FMT_PS),
9035     OPC_CMP_NGL_PS = FOP(59, FMT_PS),
9036     OPC_CMP_LT_PS = FOP(60, FMT_PS),
9037     OPC_CMP_NGE_PS = FOP(61, FMT_PS),
9038     OPC_CMP_LE_PS = FOP(62, FMT_PS),
9039     OPC_CMP_NGT_PS = FOP(63, FMT_PS),
9040 };
9041 
9042 enum r6_f_cmp_op {
9043     R6_OPC_CMP_AF_S   = FOP(0, FMT_W),
9044     R6_OPC_CMP_UN_S   = FOP(1, FMT_W),
9045     R6_OPC_CMP_EQ_S   = FOP(2, FMT_W),
9046     R6_OPC_CMP_UEQ_S  = FOP(3, FMT_W),
9047     R6_OPC_CMP_LT_S   = FOP(4, FMT_W),
9048     R6_OPC_CMP_ULT_S  = FOP(5, FMT_W),
9049     R6_OPC_CMP_LE_S   = FOP(6, FMT_W),
9050     R6_OPC_CMP_ULE_S  = FOP(7, FMT_W),
9051     R6_OPC_CMP_SAF_S  = FOP(8, FMT_W),
9052     R6_OPC_CMP_SUN_S  = FOP(9, FMT_W),
9053     R6_OPC_CMP_SEQ_S  = FOP(10, FMT_W),
9054     R6_OPC_CMP_SEUQ_S = FOP(11, FMT_W),
9055     R6_OPC_CMP_SLT_S  = FOP(12, FMT_W),
9056     R6_OPC_CMP_SULT_S = FOP(13, FMT_W),
9057     R6_OPC_CMP_SLE_S  = FOP(14, FMT_W),
9058     R6_OPC_CMP_SULE_S = FOP(15, FMT_W),
9059     R6_OPC_CMP_OR_S   = FOP(17, FMT_W),
9060     R6_OPC_CMP_UNE_S  = FOP(18, FMT_W),
9061     R6_OPC_CMP_NE_S   = FOP(19, FMT_W),
9062     R6_OPC_CMP_SOR_S  = FOP(25, FMT_W),
9063     R6_OPC_CMP_SUNE_S = FOP(26, FMT_W),
9064     R6_OPC_CMP_SNE_S  = FOP(27, FMT_W),
9065 
9066     R6_OPC_CMP_AF_D   = FOP(0, FMT_L),
9067     R6_OPC_CMP_UN_D   = FOP(1, FMT_L),
9068     R6_OPC_CMP_EQ_D   = FOP(2, FMT_L),
9069     R6_OPC_CMP_UEQ_D  = FOP(3, FMT_L),
9070     R6_OPC_CMP_LT_D   = FOP(4, FMT_L),
9071     R6_OPC_CMP_ULT_D  = FOP(5, FMT_L),
9072     R6_OPC_CMP_LE_D   = FOP(6, FMT_L),
9073     R6_OPC_CMP_ULE_D  = FOP(7, FMT_L),
9074     R6_OPC_CMP_SAF_D  = FOP(8, FMT_L),
9075     R6_OPC_CMP_SUN_D  = FOP(9, FMT_L),
9076     R6_OPC_CMP_SEQ_D  = FOP(10, FMT_L),
9077     R6_OPC_CMP_SEUQ_D = FOP(11, FMT_L),
9078     R6_OPC_CMP_SLT_D  = FOP(12, FMT_L),
9079     R6_OPC_CMP_SULT_D = FOP(13, FMT_L),
9080     R6_OPC_CMP_SLE_D  = FOP(14, FMT_L),
9081     R6_OPC_CMP_SULE_D = FOP(15, FMT_L),
9082     R6_OPC_CMP_OR_D   = FOP(17, FMT_L),
9083     R6_OPC_CMP_UNE_D  = FOP(18, FMT_L),
9084     R6_OPC_CMP_NE_D   = FOP(19, FMT_L),
9085     R6_OPC_CMP_SOR_D  = FOP(25, FMT_L),
9086     R6_OPC_CMP_SUNE_D = FOP(26, FMT_L),
9087     R6_OPC_CMP_SNE_D  = FOP(27, FMT_L),
9088 };
9089 
9090 static void gen_cp1(DisasContext *ctx, uint32_t opc, int rt, int fs)
9091 {
9092     TCGv t0 = tcg_temp_new();
9093 
9094     switch (opc) {
9095     case OPC_MFC1:
9096         {
9097             TCGv_i32 fp0 = tcg_temp_new_i32();
9098 
9099             gen_load_fpr32(ctx, fp0, fs);
9100             tcg_gen_ext_i32_tl(t0, fp0);
9101         }
9102         gen_store_gpr(t0, rt);
9103         break;
9104     case OPC_MTC1:
9105         gen_load_gpr(t0, rt);
9106         {
9107             TCGv_i32 fp0 = tcg_temp_new_i32();
9108 
9109             tcg_gen_trunc_tl_i32(fp0, t0);
9110             gen_store_fpr32(ctx, fp0, fs);
9111         }
9112         break;
9113     case OPC_CFC1:
9114         gen_helper_1e0i(cfc1, t0, fs);
9115         gen_store_gpr(t0, rt);
9116         break;
9117     case OPC_CTC1:
9118         gen_load_gpr(t0, rt);
9119         save_cpu_state(ctx, 0);
9120         gen_helper_0e2i(ctc1, t0, tcg_constant_i32(fs), rt);
9121         /* Stop translation as we may have changed hflags */
9122         ctx->base.is_jmp = DISAS_STOP;
9123         break;
9124 #if defined(TARGET_MIPS64)
9125     case OPC_DMFC1:
9126         gen_load_fpr64(ctx, t0, fs);
9127         gen_store_gpr(t0, rt);
9128         break;
9129     case OPC_DMTC1:
9130         gen_load_gpr(t0, rt);
9131         gen_store_fpr64(ctx, t0, fs);
9132         break;
9133 #endif
9134     case OPC_MFHC1:
9135         {
9136             TCGv_i32 fp0 = tcg_temp_new_i32();
9137 
9138             gen_load_fpr32h(ctx, fp0, fs);
9139             tcg_gen_ext_i32_tl(t0, fp0);
9140         }
9141         gen_store_gpr(t0, rt);
9142         break;
9143     case OPC_MTHC1:
9144         gen_load_gpr(t0, rt);
9145         {
9146             TCGv_i32 fp0 = tcg_temp_new_i32();
9147 
9148             tcg_gen_trunc_tl_i32(fp0, t0);
9149             gen_store_fpr32h(ctx, fp0, fs);
9150         }
9151         break;
9152     default:
9153         MIPS_INVAL("cp1 move");
9154         gen_reserved_instruction(ctx);
9155         return;
9156     }
9157 }
9158 
9159 static void gen_movci(DisasContext *ctx, int rd, int rs, int cc, int tf)
9160 {
9161     TCGLabel *l1;
9162     TCGCond cond;
9163     TCGv_i32 t0;
9164 
9165     if (rd == 0) {
9166         /* Treat as NOP. */
9167         return;
9168     }
9169 
9170     if (tf) {
9171         cond = TCG_COND_EQ;
9172     } else {
9173         cond = TCG_COND_NE;
9174     }
9175 
9176     l1 = gen_new_label();
9177     t0 = tcg_temp_new_i32();
9178     tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
9179     tcg_gen_brcondi_i32(cond, t0, 0, l1);
9180     gen_load_gpr(cpu_gpr[rd], rs);
9181     gen_set_label(l1);
9182 }
9183 
9184 static inline void gen_movcf_s(DisasContext *ctx, int fs, int fd, int cc,
9185                                int tf)
9186 {
9187     int cond;
9188     TCGv_i32 t0 = tcg_temp_new_i32();
9189     TCGLabel *l1 = gen_new_label();
9190 
9191     if (tf) {
9192         cond = TCG_COND_EQ;
9193     } else {
9194         cond = TCG_COND_NE;
9195     }
9196 
9197     tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
9198     tcg_gen_brcondi_i32(cond, t0, 0, l1);
9199     gen_load_fpr32(ctx, t0, fs);
9200     gen_store_fpr32(ctx, t0, fd);
9201     gen_set_label(l1);
9202 }
9203 
9204 static inline void gen_movcf_d(DisasContext *ctx, int fs, int fd, int cc,
9205                                int tf)
9206 {
9207     int cond;
9208     TCGv_i32 t0 = tcg_temp_new_i32();
9209     TCGv_i64 fp0;
9210     TCGLabel *l1 = gen_new_label();
9211 
9212     if (tf) {
9213         cond = TCG_COND_EQ;
9214     } else {
9215         cond = TCG_COND_NE;
9216     }
9217 
9218     tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
9219     tcg_gen_brcondi_i32(cond, t0, 0, l1);
9220     fp0 = tcg_temp_new_i64();
9221     gen_load_fpr64(ctx, fp0, fs);
9222     gen_store_fpr64(ctx, fp0, fd);
9223     gen_set_label(l1);
9224 }
9225 
9226 static inline void gen_movcf_ps(DisasContext *ctx, int fs, int fd,
9227                                 int cc, int tf)
9228 {
9229     int cond;
9230     TCGv_i32 t0 = tcg_temp_new_i32();
9231     TCGLabel *l1 = gen_new_label();
9232     TCGLabel *l2 = gen_new_label();
9233 
9234     if (tf) {
9235         cond = TCG_COND_EQ;
9236     } else {
9237         cond = TCG_COND_NE;
9238     }
9239 
9240     tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc));
9241     tcg_gen_brcondi_i32(cond, t0, 0, l1);
9242     gen_load_fpr32(ctx, t0, fs);
9243     gen_store_fpr32(ctx, t0, fd);
9244     gen_set_label(l1);
9245 
9246     tcg_gen_andi_i32(t0, fpu_fcr31, 1 << get_fp_bit(cc + 1));
9247     tcg_gen_brcondi_i32(cond, t0, 0, l2);
9248     gen_load_fpr32h(ctx, t0, fs);
9249     gen_store_fpr32h(ctx, t0, fd);
9250     gen_set_label(l2);
9251 }
9252 
9253 static void gen_sel_s(DisasContext *ctx, enum fopcode op1, int fd, int ft,
9254                       int fs)
9255 {
9256     TCGv_i32 t1 = tcg_constant_i32(0);
9257     TCGv_i32 fp0 = tcg_temp_new_i32();
9258     TCGv_i32 fp1 = tcg_temp_new_i32();
9259     TCGv_i32 fp2 = tcg_temp_new_i32();
9260     gen_load_fpr32(ctx, fp0, fd);
9261     gen_load_fpr32(ctx, fp1, ft);
9262     gen_load_fpr32(ctx, fp2, fs);
9263 
9264     switch (op1) {
9265     case OPC_SEL_S:
9266         tcg_gen_andi_i32(fp0, fp0, 1);
9267         tcg_gen_movcond_i32(TCG_COND_NE, fp0, fp0, t1, fp1, fp2);
9268         break;
9269     case OPC_SELEQZ_S:
9270         tcg_gen_andi_i32(fp1, fp1, 1);
9271         tcg_gen_movcond_i32(TCG_COND_EQ, fp0, fp1, t1, fp2, t1);
9272         break;
9273     case OPC_SELNEZ_S:
9274         tcg_gen_andi_i32(fp1, fp1, 1);
9275         tcg_gen_movcond_i32(TCG_COND_NE, fp0, fp1, t1, fp2, t1);
9276         break;
9277     default:
9278         MIPS_INVAL("gen_sel_s");
9279         gen_reserved_instruction(ctx);
9280         break;
9281     }
9282 
9283     gen_store_fpr32(ctx, fp0, fd);
9284 }
9285 
9286 static void gen_sel_d(DisasContext *ctx, enum fopcode op1, int fd, int ft,
9287                       int fs)
9288 {
9289     TCGv_i64 t1 = tcg_constant_i64(0);
9290     TCGv_i64 fp0 = tcg_temp_new_i64();
9291     TCGv_i64 fp1 = tcg_temp_new_i64();
9292     TCGv_i64 fp2 = tcg_temp_new_i64();
9293     gen_load_fpr64(ctx, fp0, fd);
9294     gen_load_fpr64(ctx, fp1, ft);
9295     gen_load_fpr64(ctx, fp2, fs);
9296 
9297     switch (op1) {
9298     case OPC_SEL_D:
9299         tcg_gen_andi_i64(fp0, fp0, 1);
9300         tcg_gen_movcond_i64(TCG_COND_NE, fp0, fp0, t1, fp1, fp2);
9301         break;
9302     case OPC_SELEQZ_D:
9303         tcg_gen_andi_i64(fp1, fp1, 1);
9304         tcg_gen_movcond_i64(TCG_COND_EQ, fp0, fp1, t1, fp2, t1);
9305         break;
9306     case OPC_SELNEZ_D:
9307         tcg_gen_andi_i64(fp1, fp1, 1);
9308         tcg_gen_movcond_i64(TCG_COND_NE, fp0, fp1, t1, fp2, t1);
9309         break;
9310     default:
9311         MIPS_INVAL("gen_sel_d");
9312         gen_reserved_instruction(ctx);
9313         break;
9314     }
9315 
9316     gen_store_fpr64(ctx, fp0, fd);
9317 }
9318 
9319 static void gen_farith(DisasContext *ctx, enum fopcode op1,
9320                        int ft, int fs, int fd, int cc)
9321 {
9322     uint32_t func = ctx->opcode & 0x3f;
9323     switch (op1) {
9324     case OPC_ADD_S:
9325         {
9326             TCGv_i32 fp0 = tcg_temp_new_i32();
9327             TCGv_i32 fp1 = tcg_temp_new_i32();
9328 
9329             gen_load_fpr32(ctx, fp0, fs);
9330             gen_load_fpr32(ctx, fp1, ft);
9331             gen_helper_float_add_s(fp0, tcg_env, fp0, fp1);
9332             gen_store_fpr32(ctx, fp0, fd);
9333         }
9334         break;
9335     case OPC_SUB_S:
9336         {
9337             TCGv_i32 fp0 = tcg_temp_new_i32();
9338             TCGv_i32 fp1 = tcg_temp_new_i32();
9339 
9340             gen_load_fpr32(ctx, fp0, fs);
9341             gen_load_fpr32(ctx, fp1, ft);
9342             gen_helper_float_sub_s(fp0, tcg_env, fp0, fp1);
9343             gen_store_fpr32(ctx, fp0, fd);
9344         }
9345         break;
9346     case OPC_MUL_S:
9347         {
9348             TCGv_i32 fp0 = tcg_temp_new_i32();
9349             TCGv_i32 fp1 = tcg_temp_new_i32();
9350 
9351             gen_load_fpr32(ctx, fp0, fs);
9352             gen_load_fpr32(ctx, fp1, ft);
9353             gen_helper_float_mul_s(fp0, tcg_env, fp0, fp1);
9354             gen_store_fpr32(ctx, fp0, fd);
9355         }
9356         break;
9357     case OPC_DIV_S:
9358         {
9359             TCGv_i32 fp0 = tcg_temp_new_i32();
9360             TCGv_i32 fp1 = tcg_temp_new_i32();
9361 
9362             gen_load_fpr32(ctx, fp0, fs);
9363             gen_load_fpr32(ctx, fp1, ft);
9364             gen_helper_float_div_s(fp0, tcg_env, fp0, fp1);
9365             gen_store_fpr32(ctx, fp0, fd);
9366         }
9367         break;
9368     case OPC_SQRT_S:
9369         {
9370             TCGv_i32 fp0 = tcg_temp_new_i32();
9371 
9372             gen_load_fpr32(ctx, fp0, fs);
9373             gen_helper_float_sqrt_s(fp0, tcg_env, fp0);
9374             gen_store_fpr32(ctx, fp0, fd);
9375         }
9376         break;
9377     case OPC_ABS_S:
9378         {
9379             TCGv_i32 fp0 = tcg_temp_new_i32();
9380 
9381             gen_load_fpr32(ctx, fp0, fs);
9382             if (ctx->abs2008) {
9383                 tcg_gen_andi_i32(fp0, fp0, 0x7fffffffUL);
9384             } else {
9385                 gen_helper_float_abs_s(fp0, fp0);
9386             }
9387             gen_store_fpr32(ctx, fp0, fd);
9388         }
9389         break;
9390     case OPC_MOV_S:
9391         {
9392             TCGv_i32 fp0 = tcg_temp_new_i32();
9393 
9394             gen_load_fpr32(ctx, fp0, fs);
9395             gen_store_fpr32(ctx, fp0, fd);
9396         }
9397         break;
9398     case OPC_NEG_S:
9399         {
9400             TCGv_i32 fp0 = tcg_temp_new_i32();
9401 
9402             gen_load_fpr32(ctx, fp0, fs);
9403             if (ctx->abs2008) {
9404                 tcg_gen_xori_i32(fp0, fp0, 1UL << 31);
9405             } else {
9406                 gen_helper_float_chs_s(fp0, fp0);
9407             }
9408             gen_store_fpr32(ctx, fp0, fd);
9409         }
9410         break;
9411     case OPC_ROUND_L_S:
9412         check_cp1_64bitmode(ctx);
9413         {
9414             TCGv_i32 fp32 = tcg_temp_new_i32();
9415             TCGv_i64 fp64 = tcg_temp_new_i64();
9416 
9417             gen_load_fpr32(ctx, fp32, fs);
9418             if (ctx->nan2008) {
9419                 gen_helper_float_round_2008_l_s(fp64, tcg_env, fp32);
9420             } else {
9421                 gen_helper_float_round_l_s(fp64, tcg_env, fp32);
9422             }
9423             gen_store_fpr64(ctx, fp64, fd);
9424         }
9425         break;
9426     case OPC_TRUNC_L_S:
9427         check_cp1_64bitmode(ctx);
9428         {
9429             TCGv_i32 fp32 = tcg_temp_new_i32();
9430             TCGv_i64 fp64 = tcg_temp_new_i64();
9431 
9432             gen_load_fpr32(ctx, fp32, fs);
9433             if (ctx->nan2008) {
9434                 gen_helper_float_trunc_2008_l_s(fp64, tcg_env, fp32);
9435             } else {
9436                 gen_helper_float_trunc_l_s(fp64, tcg_env, fp32);
9437             }
9438             gen_store_fpr64(ctx, fp64, fd);
9439         }
9440         break;
9441     case OPC_CEIL_L_S:
9442         check_cp1_64bitmode(ctx);
9443         {
9444             TCGv_i32 fp32 = tcg_temp_new_i32();
9445             TCGv_i64 fp64 = tcg_temp_new_i64();
9446 
9447             gen_load_fpr32(ctx, fp32, fs);
9448             if (ctx->nan2008) {
9449                 gen_helper_float_ceil_2008_l_s(fp64, tcg_env, fp32);
9450             } else {
9451                 gen_helper_float_ceil_l_s(fp64, tcg_env, fp32);
9452             }
9453             gen_store_fpr64(ctx, fp64, fd);
9454         }
9455         break;
9456     case OPC_FLOOR_L_S:
9457         check_cp1_64bitmode(ctx);
9458         {
9459             TCGv_i32 fp32 = tcg_temp_new_i32();
9460             TCGv_i64 fp64 = tcg_temp_new_i64();
9461 
9462             gen_load_fpr32(ctx, fp32, fs);
9463             if (ctx->nan2008) {
9464                 gen_helper_float_floor_2008_l_s(fp64, tcg_env, fp32);
9465             } else {
9466                 gen_helper_float_floor_l_s(fp64, tcg_env, fp32);
9467             }
9468             gen_store_fpr64(ctx, fp64, fd);
9469         }
9470         break;
9471     case OPC_ROUND_W_S:
9472         {
9473             TCGv_i32 fp0 = tcg_temp_new_i32();
9474 
9475             gen_load_fpr32(ctx, fp0, fs);
9476             if (ctx->nan2008) {
9477                 gen_helper_float_round_2008_w_s(fp0, tcg_env, fp0);
9478             } else {
9479                 gen_helper_float_round_w_s(fp0, tcg_env, fp0);
9480             }
9481             gen_store_fpr32(ctx, fp0, fd);
9482         }
9483         break;
9484     case OPC_TRUNC_W_S:
9485         {
9486             TCGv_i32 fp0 = tcg_temp_new_i32();
9487 
9488             gen_load_fpr32(ctx, fp0, fs);
9489             if (ctx->nan2008) {
9490                 gen_helper_float_trunc_2008_w_s(fp0, tcg_env, fp0);
9491             } else {
9492                 gen_helper_float_trunc_w_s(fp0, tcg_env, fp0);
9493             }
9494             gen_store_fpr32(ctx, fp0, fd);
9495         }
9496         break;
9497     case OPC_CEIL_W_S:
9498         {
9499             TCGv_i32 fp0 = tcg_temp_new_i32();
9500 
9501             gen_load_fpr32(ctx, fp0, fs);
9502             if (ctx->nan2008) {
9503                 gen_helper_float_ceil_2008_w_s(fp0, tcg_env, fp0);
9504             } else {
9505                 gen_helper_float_ceil_w_s(fp0, tcg_env, fp0);
9506             }
9507             gen_store_fpr32(ctx, fp0, fd);
9508         }
9509         break;
9510     case OPC_FLOOR_W_S:
9511         {
9512             TCGv_i32 fp0 = tcg_temp_new_i32();
9513 
9514             gen_load_fpr32(ctx, fp0, fs);
9515             if (ctx->nan2008) {
9516                 gen_helper_float_floor_2008_w_s(fp0, tcg_env, fp0);
9517             } else {
9518                 gen_helper_float_floor_w_s(fp0, tcg_env, fp0);
9519             }
9520             gen_store_fpr32(ctx, fp0, fd);
9521         }
9522         break;
9523     case OPC_SEL_S:
9524         check_insn(ctx, ISA_MIPS_R6);
9525         gen_sel_s(ctx, op1, fd, ft, fs);
9526         break;
9527     case OPC_SELEQZ_S:
9528         check_insn(ctx, ISA_MIPS_R6);
9529         gen_sel_s(ctx, op1, fd, ft, fs);
9530         break;
9531     case OPC_SELNEZ_S:
9532         check_insn(ctx, ISA_MIPS_R6);
9533         gen_sel_s(ctx, op1, fd, ft, fs);
9534         break;
9535     case OPC_MOVCF_S:
9536         check_insn_opc_removed(ctx, ISA_MIPS_R6);
9537         gen_movcf_s(ctx, fs, fd, (ft >> 2) & 0x7, ft & 0x1);
9538         break;
9539     case OPC_MOVZ_S:
9540         check_insn_opc_removed(ctx, ISA_MIPS_R6);
9541         {
9542             TCGLabel *l1 = gen_new_label();
9543             TCGv_i32 fp0;
9544 
9545             if (ft != 0) {
9546                 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
9547             }
9548             fp0 = tcg_temp_new_i32();
9549             gen_load_fpr32(ctx, fp0, fs);
9550             gen_store_fpr32(ctx, fp0, fd);
9551             gen_set_label(l1);
9552         }
9553         break;
9554     case OPC_MOVN_S:
9555         check_insn_opc_removed(ctx, ISA_MIPS_R6);
9556         {
9557             TCGLabel *l1 = gen_new_label();
9558             TCGv_i32 fp0;
9559 
9560             if (ft != 0) {
9561                 tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
9562                 fp0 = tcg_temp_new_i32();
9563                 gen_load_fpr32(ctx, fp0, fs);
9564                 gen_store_fpr32(ctx, fp0, fd);
9565                 gen_set_label(l1);
9566             }
9567         }
9568         break;
9569     case OPC_RECIP_S:
9570         {
9571             TCGv_i32 fp0 = tcg_temp_new_i32();
9572 
9573             gen_load_fpr32(ctx, fp0, fs);
9574             gen_helper_float_recip_s(fp0, tcg_env, fp0);
9575             gen_store_fpr32(ctx, fp0, fd);
9576         }
9577         break;
9578     case OPC_RSQRT_S:
9579         {
9580             TCGv_i32 fp0 = tcg_temp_new_i32();
9581 
9582             gen_load_fpr32(ctx, fp0, fs);
9583             gen_helper_float_rsqrt_s(fp0, tcg_env, fp0);
9584             gen_store_fpr32(ctx, fp0, fd);
9585         }
9586         break;
9587     case OPC_MADDF_S:
9588         check_insn(ctx, ISA_MIPS_R6);
9589         {
9590             TCGv_i32 fp0 = tcg_temp_new_i32();
9591             TCGv_i32 fp1 = tcg_temp_new_i32();
9592             TCGv_i32 fp2 = tcg_temp_new_i32();
9593             gen_load_fpr32(ctx, fp0, fs);
9594             gen_load_fpr32(ctx, fp1, ft);
9595             gen_load_fpr32(ctx, fp2, fd);
9596             gen_helper_float_maddf_s(fp2, tcg_env, fp0, fp1, fp2);
9597             gen_store_fpr32(ctx, fp2, fd);
9598         }
9599         break;
9600     case OPC_MSUBF_S:
9601         check_insn(ctx, ISA_MIPS_R6);
9602         {
9603             TCGv_i32 fp0 = tcg_temp_new_i32();
9604             TCGv_i32 fp1 = tcg_temp_new_i32();
9605             TCGv_i32 fp2 = tcg_temp_new_i32();
9606             gen_load_fpr32(ctx, fp0, fs);
9607             gen_load_fpr32(ctx, fp1, ft);
9608             gen_load_fpr32(ctx, fp2, fd);
9609             gen_helper_float_msubf_s(fp2, tcg_env, fp0, fp1, fp2);
9610             gen_store_fpr32(ctx, fp2, fd);
9611         }
9612         break;
9613     case OPC_RINT_S:
9614         check_insn(ctx, ISA_MIPS_R6);
9615         {
9616             TCGv_i32 fp0 = tcg_temp_new_i32();
9617             gen_load_fpr32(ctx, fp0, fs);
9618             gen_helper_float_rint_s(fp0, tcg_env, fp0);
9619             gen_store_fpr32(ctx, fp0, fd);
9620         }
9621         break;
9622     case OPC_CLASS_S:
9623         check_insn(ctx, ISA_MIPS_R6);
9624         {
9625             TCGv_i32 fp0 = tcg_temp_new_i32();
9626             gen_load_fpr32(ctx, fp0, fs);
9627             gen_helper_float_class_s(fp0, tcg_env, fp0);
9628             gen_store_fpr32(ctx, fp0, fd);
9629         }
9630         break;
9631     case OPC_MIN_S: /* OPC_RECIP2_S */
9632         if (ctx->insn_flags & ISA_MIPS_R6) {
9633             /* OPC_MIN_S */
9634             TCGv_i32 fp0 = tcg_temp_new_i32();
9635             TCGv_i32 fp1 = tcg_temp_new_i32();
9636             TCGv_i32 fp2 = tcg_temp_new_i32();
9637             gen_load_fpr32(ctx, fp0, fs);
9638             gen_load_fpr32(ctx, fp1, ft);
9639             gen_helper_float_min_s(fp2, tcg_env, fp0, fp1);
9640             gen_store_fpr32(ctx, fp2, fd);
9641         } else {
9642             /* OPC_RECIP2_S */
9643             check_cp1_64bitmode(ctx);
9644             {
9645                 TCGv_i32 fp0 = tcg_temp_new_i32();
9646                 TCGv_i32 fp1 = tcg_temp_new_i32();
9647 
9648                 gen_load_fpr32(ctx, fp0, fs);
9649                 gen_load_fpr32(ctx, fp1, ft);
9650                 gen_helper_float_recip2_s(fp0, tcg_env, fp0, fp1);
9651                 gen_store_fpr32(ctx, fp0, fd);
9652             }
9653         }
9654         break;
9655     case OPC_MINA_S: /* OPC_RECIP1_S */
9656         if (ctx->insn_flags & ISA_MIPS_R6) {
9657             /* OPC_MINA_S */
9658             TCGv_i32 fp0 = tcg_temp_new_i32();
9659             TCGv_i32 fp1 = tcg_temp_new_i32();
9660             TCGv_i32 fp2 = tcg_temp_new_i32();
9661             gen_load_fpr32(ctx, fp0, fs);
9662             gen_load_fpr32(ctx, fp1, ft);
9663             gen_helper_float_mina_s(fp2, tcg_env, fp0, fp1);
9664             gen_store_fpr32(ctx, fp2, fd);
9665         } else {
9666             /* OPC_RECIP1_S */
9667             check_cp1_64bitmode(ctx);
9668             {
9669                 TCGv_i32 fp0 = tcg_temp_new_i32();
9670 
9671                 gen_load_fpr32(ctx, fp0, fs);
9672                 gen_helper_float_recip1_s(fp0, tcg_env, fp0);
9673                 gen_store_fpr32(ctx, fp0, fd);
9674             }
9675         }
9676         break;
9677     case OPC_MAX_S: /* OPC_RSQRT1_S */
9678         if (ctx->insn_flags & ISA_MIPS_R6) {
9679             /* OPC_MAX_S */
9680             TCGv_i32 fp0 = tcg_temp_new_i32();
9681             TCGv_i32 fp1 = tcg_temp_new_i32();
9682             gen_load_fpr32(ctx, fp0, fs);
9683             gen_load_fpr32(ctx, fp1, ft);
9684             gen_helper_float_max_s(fp1, tcg_env, fp0, fp1);
9685             gen_store_fpr32(ctx, fp1, fd);
9686         } else {
9687             /* OPC_RSQRT1_S */
9688             check_cp1_64bitmode(ctx);
9689             {
9690                 TCGv_i32 fp0 = tcg_temp_new_i32();
9691 
9692                 gen_load_fpr32(ctx, fp0, fs);
9693                 gen_helper_float_rsqrt1_s(fp0, tcg_env, fp0);
9694                 gen_store_fpr32(ctx, fp0, fd);
9695             }
9696         }
9697         break;
9698     case OPC_MAXA_S: /* OPC_RSQRT2_S */
9699         if (ctx->insn_flags & ISA_MIPS_R6) {
9700             /* OPC_MAXA_S */
9701             TCGv_i32 fp0 = tcg_temp_new_i32();
9702             TCGv_i32 fp1 = tcg_temp_new_i32();
9703             gen_load_fpr32(ctx, fp0, fs);
9704             gen_load_fpr32(ctx, fp1, ft);
9705             gen_helper_float_maxa_s(fp1, tcg_env, fp0, fp1);
9706             gen_store_fpr32(ctx, fp1, fd);
9707         } else {
9708             /* OPC_RSQRT2_S */
9709             check_cp1_64bitmode(ctx);
9710             {
9711                 TCGv_i32 fp0 = tcg_temp_new_i32();
9712                 TCGv_i32 fp1 = tcg_temp_new_i32();
9713 
9714                 gen_load_fpr32(ctx, fp0, fs);
9715                 gen_load_fpr32(ctx, fp1, ft);
9716                 gen_helper_float_rsqrt2_s(fp0, tcg_env, fp0, fp1);
9717                 gen_store_fpr32(ctx, fp0, fd);
9718             }
9719         }
9720         break;
9721     case OPC_CVT_D_S:
9722         check_cp1_registers(ctx, fd);
9723         {
9724             TCGv_i32 fp32 = tcg_temp_new_i32();
9725             TCGv_i64 fp64 = tcg_temp_new_i64();
9726 
9727             gen_load_fpr32(ctx, fp32, fs);
9728             gen_helper_float_cvtd_s(fp64, tcg_env, fp32);
9729             gen_store_fpr64(ctx, fp64, fd);
9730         }
9731         break;
9732     case OPC_CVT_W_S:
9733         {
9734             TCGv_i32 fp0 = tcg_temp_new_i32();
9735 
9736             gen_load_fpr32(ctx, fp0, fs);
9737             if (ctx->nan2008) {
9738                 gen_helper_float_cvt_2008_w_s(fp0, tcg_env, fp0);
9739             } else {
9740                 gen_helper_float_cvt_w_s(fp0, tcg_env, fp0);
9741             }
9742             gen_store_fpr32(ctx, fp0, fd);
9743         }
9744         break;
9745     case OPC_CVT_L_S:
9746         check_cp1_64bitmode(ctx);
9747         {
9748             TCGv_i32 fp32 = tcg_temp_new_i32();
9749             TCGv_i64 fp64 = tcg_temp_new_i64();
9750 
9751             gen_load_fpr32(ctx, fp32, fs);
9752             if (ctx->nan2008) {
9753                 gen_helper_float_cvt_2008_l_s(fp64, tcg_env, fp32);
9754             } else {
9755                 gen_helper_float_cvt_l_s(fp64, tcg_env, fp32);
9756             }
9757             gen_store_fpr64(ctx, fp64, fd);
9758         }
9759         break;
9760     case OPC_CVT_PS_S:
9761         check_ps(ctx);
9762         {
9763             TCGv_i64 fp64 = tcg_temp_new_i64();
9764             TCGv_i32 fp32_0 = tcg_temp_new_i32();
9765             TCGv_i32 fp32_1 = tcg_temp_new_i32();
9766 
9767             gen_load_fpr32(ctx, fp32_0, fs);
9768             gen_load_fpr32(ctx, fp32_1, ft);
9769             tcg_gen_concat_i32_i64(fp64, fp32_1, fp32_0);
9770             gen_store_fpr64(ctx, fp64, fd);
9771         }
9772         break;
9773     case OPC_CMP_F_S:
9774     case OPC_CMP_UN_S:
9775     case OPC_CMP_EQ_S:
9776     case OPC_CMP_UEQ_S:
9777     case OPC_CMP_OLT_S:
9778     case OPC_CMP_ULT_S:
9779     case OPC_CMP_OLE_S:
9780     case OPC_CMP_ULE_S:
9781     case OPC_CMP_SF_S:
9782     case OPC_CMP_NGLE_S:
9783     case OPC_CMP_SEQ_S:
9784     case OPC_CMP_NGL_S:
9785     case OPC_CMP_LT_S:
9786     case OPC_CMP_NGE_S:
9787     case OPC_CMP_LE_S:
9788     case OPC_CMP_NGT_S:
9789         check_insn_opc_removed(ctx, ISA_MIPS_R6);
9790         if (ctx->opcode & (1 << 6)) {
9791             gen_cmpabs_s(ctx, func - 48, ft, fs, cc);
9792         } else {
9793             gen_cmp_s(ctx, func - 48, ft, fs, cc);
9794         }
9795         break;
9796     case OPC_ADD_D:
9797         check_cp1_registers(ctx, fs | ft | fd);
9798         {
9799             TCGv_i64 fp0 = tcg_temp_new_i64();
9800             TCGv_i64 fp1 = tcg_temp_new_i64();
9801 
9802             gen_load_fpr64(ctx, fp0, fs);
9803             gen_load_fpr64(ctx, fp1, ft);
9804             gen_helper_float_add_d(fp0, tcg_env, fp0, fp1);
9805             gen_store_fpr64(ctx, fp0, fd);
9806         }
9807         break;
9808     case OPC_SUB_D:
9809         check_cp1_registers(ctx, fs | ft | fd);
9810         {
9811             TCGv_i64 fp0 = tcg_temp_new_i64();
9812             TCGv_i64 fp1 = tcg_temp_new_i64();
9813 
9814             gen_load_fpr64(ctx, fp0, fs);
9815             gen_load_fpr64(ctx, fp1, ft);
9816             gen_helper_float_sub_d(fp0, tcg_env, fp0, fp1);
9817             gen_store_fpr64(ctx, fp0, fd);
9818         }
9819         break;
9820     case OPC_MUL_D:
9821         check_cp1_registers(ctx, fs | ft | fd);
9822         {
9823             TCGv_i64 fp0 = tcg_temp_new_i64();
9824             TCGv_i64 fp1 = tcg_temp_new_i64();
9825 
9826             gen_load_fpr64(ctx, fp0, fs);
9827             gen_load_fpr64(ctx, fp1, ft);
9828             gen_helper_float_mul_d(fp0, tcg_env, fp0, fp1);
9829             gen_store_fpr64(ctx, fp0, fd);
9830         }
9831         break;
9832     case OPC_DIV_D:
9833         check_cp1_registers(ctx, fs | ft | fd);
9834         {
9835             TCGv_i64 fp0 = tcg_temp_new_i64();
9836             TCGv_i64 fp1 = tcg_temp_new_i64();
9837 
9838             gen_load_fpr64(ctx, fp0, fs);
9839             gen_load_fpr64(ctx, fp1, ft);
9840             gen_helper_float_div_d(fp0, tcg_env, fp0, fp1);
9841             gen_store_fpr64(ctx, fp0, fd);
9842         }
9843         break;
9844     case OPC_SQRT_D:
9845         check_cp1_registers(ctx, fs | fd);
9846         {
9847             TCGv_i64 fp0 = tcg_temp_new_i64();
9848 
9849             gen_load_fpr64(ctx, fp0, fs);
9850             gen_helper_float_sqrt_d(fp0, tcg_env, fp0);
9851             gen_store_fpr64(ctx, fp0, fd);
9852         }
9853         break;
9854     case OPC_ABS_D:
9855         check_cp1_registers(ctx, fs | fd);
9856         {
9857             TCGv_i64 fp0 = tcg_temp_new_i64();
9858 
9859             gen_load_fpr64(ctx, fp0, fs);
9860             if (ctx->abs2008) {
9861                 tcg_gen_andi_i64(fp0, fp0, 0x7fffffffffffffffULL);
9862             } else {
9863                 gen_helper_float_abs_d(fp0, fp0);
9864             }
9865             gen_store_fpr64(ctx, fp0, fd);
9866         }
9867         break;
9868     case OPC_MOV_D:
9869         check_cp1_registers(ctx, fs | fd);
9870         {
9871             TCGv_i64 fp0 = tcg_temp_new_i64();
9872 
9873             gen_load_fpr64(ctx, fp0, fs);
9874             gen_store_fpr64(ctx, fp0, fd);
9875         }
9876         break;
9877     case OPC_NEG_D:
9878         check_cp1_registers(ctx, fs | fd);
9879         {
9880             TCGv_i64 fp0 = tcg_temp_new_i64();
9881 
9882             gen_load_fpr64(ctx, fp0, fs);
9883             if (ctx->abs2008) {
9884                 tcg_gen_xori_i64(fp0, fp0, 1ULL << 63);
9885             } else {
9886                 gen_helper_float_chs_d(fp0, fp0);
9887             }
9888             gen_store_fpr64(ctx, fp0, fd);
9889         }
9890         break;
9891     case OPC_ROUND_L_D:
9892         check_cp1_64bitmode(ctx);
9893         {
9894             TCGv_i64 fp0 = tcg_temp_new_i64();
9895 
9896             gen_load_fpr64(ctx, fp0, fs);
9897             if (ctx->nan2008) {
9898                 gen_helper_float_round_2008_l_d(fp0, tcg_env, fp0);
9899             } else {
9900                 gen_helper_float_round_l_d(fp0, tcg_env, fp0);
9901             }
9902             gen_store_fpr64(ctx, fp0, fd);
9903         }
9904         break;
9905     case OPC_TRUNC_L_D:
9906         check_cp1_64bitmode(ctx);
9907         {
9908             TCGv_i64 fp0 = tcg_temp_new_i64();
9909 
9910             gen_load_fpr64(ctx, fp0, fs);
9911             if (ctx->nan2008) {
9912                 gen_helper_float_trunc_2008_l_d(fp0, tcg_env, fp0);
9913             } else {
9914                 gen_helper_float_trunc_l_d(fp0, tcg_env, fp0);
9915             }
9916             gen_store_fpr64(ctx, fp0, fd);
9917         }
9918         break;
9919     case OPC_CEIL_L_D:
9920         check_cp1_64bitmode(ctx);
9921         {
9922             TCGv_i64 fp0 = tcg_temp_new_i64();
9923 
9924             gen_load_fpr64(ctx, fp0, fs);
9925             if (ctx->nan2008) {
9926                 gen_helper_float_ceil_2008_l_d(fp0, tcg_env, fp0);
9927             } else {
9928                 gen_helper_float_ceil_l_d(fp0, tcg_env, fp0);
9929             }
9930             gen_store_fpr64(ctx, fp0, fd);
9931         }
9932         break;
9933     case OPC_FLOOR_L_D:
9934         check_cp1_64bitmode(ctx);
9935         {
9936             TCGv_i64 fp0 = tcg_temp_new_i64();
9937 
9938             gen_load_fpr64(ctx, fp0, fs);
9939             if (ctx->nan2008) {
9940                 gen_helper_float_floor_2008_l_d(fp0, tcg_env, fp0);
9941             } else {
9942                 gen_helper_float_floor_l_d(fp0, tcg_env, fp0);
9943             }
9944             gen_store_fpr64(ctx, fp0, fd);
9945         }
9946         break;
9947     case OPC_ROUND_W_D:
9948         check_cp1_registers(ctx, fs);
9949         {
9950             TCGv_i32 fp32 = tcg_temp_new_i32();
9951             TCGv_i64 fp64 = tcg_temp_new_i64();
9952 
9953             gen_load_fpr64(ctx, fp64, fs);
9954             if (ctx->nan2008) {
9955                 gen_helper_float_round_2008_w_d(fp32, tcg_env, fp64);
9956             } else {
9957                 gen_helper_float_round_w_d(fp32, tcg_env, fp64);
9958             }
9959             gen_store_fpr32(ctx, fp32, fd);
9960         }
9961         break;
9962     case OPC_TRUNC_W_D:
9963         check_cp1_registers(ctx, fs);
9964         {
9965             TCGv_i32 fp32 = tcg_temp_new_i32();
9966             TCGv_i64 fp64 = tcg_temp_new_i64();
9967 
9968             gen_load_fpr64(ctx, fp64, fs);
9969             if (ctx->nan2008) {
9970                 gen_helper_float_trunc_2008_w_d(fp32, tcg_env, fp64);
9971             } else {
9972                 gen_helper_float_trunc_w_d(fp32, tcg_env, fp64);
9973             }
9974             gen_store_fpr32(ctx, fp32, fd);
9975         }
9976         break;
9977     case OPC_CEIL_W_D:
9978         check_cp1_registers(ctx, fs);
9979         {
9980             TCGv_i32 fp32 = tcg_temp_new_i32();
9981             TCGv_i64 fp64 = tcg_temp_new_i64();
9982 
9983             gen_load_fpr64(ctx, fp64, fs);
9984             if (ctx->nan2008) {
9985                 gen_helper_float_ceil_2008_w_d(fp32, tcg_env, fp64);
9986             } else {
9987                 gen_helper_float_ceil_w_d(fp32, tcg_env, fp64);
9988             }
9989             gen_store_fpr32(ctx, fp32, fd);
9990         }
9991         break;
9992     case OPC_FLOOR_W_D:
9993         check_cp1_registers(ctx, fs);
9994         {
9995             TCGv_i32 fp32 = tcg_temp_new_i32();
9996             TCGv_i64 fp64 = tcg_temp_new_i64();
9997 
9998             gen_load_fpr64(ctx, fp64, fs);
9999             if (ctx->nan2008) {
10000                 gen_helper_float_floor_2008_w_d(fp32, tcg_env, fp64);
10001             } else {
10002                 gen_helper_float_floor_w_d(fp32, tcg_env, fp64);
10003             }
10004             gen_store_fpr32(ctx, fp32, fd);
10005         }
10006         break;
10007     case OPC_SEL_D:
10008         check_insn(ctx, ISA_MIPS_R6);
10009         gen_sel_d(ctx, op1, fd, ft, fs);
10010         break;
10011     case OPC_SELEQZ_D:
10012         check_insn(ctx, ISA_MIPS_R6);
10013         gen_sel_d(ctx, op1, fd, ft, fs);
10014         break;
10015     case OPC_SELNEZ_D:
10016         check_insn(ctx, ISA_MIPS_R6);
10017         gen_sel_d(ctx, op1, fd, ft, fs);
10018         break;
10019     case OPC_MOVCF_D:
10020         check_insn_opc_removed(ctx, ISA_MIPS_R6);
10021         gen_movcf_d(ctx, fs, fd, (ft >> 2) & 0x7, ft & 0x1);
10022         break;
10023     case OPC_MOVZ_D:
10024         check_insn_opc_removed(ctx, ISA_MIPS_R6);
10025         {
10026             TCGLabel *l1 = gen_new_label();
10027             TCGv_i64 fp0;
10028 
10029             if (ft != 0) {
10030                 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
10031             }
10032             fp0 = tcg_temp_new_i64();
10033             gen_load_fpr64(ctx, fp0, fs);
10034             gen_store_fpr64(ctx, fp0, fd);
10035             gen_set_label(l1);
10036         }
10037         break;
10038     case OPC_MOVN_D:
10039         check_insn_opc_removed(ctx, ISA_MIPS_R6);
10040         {
10041             TCGLabel *l1 = gen_new_label();
10042             TCGv_i64 fp0;
10043 
10044             if (ft != 0) {
10045                 tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
10046                 fp0 = tcg_temp_new_i64();
10047                 gen_load_fpr64(ctx, fp0, fs);
10048                 gen_store_fpr64(ctx, fp0, fd);
10049                 gen_set_label(l1);
10050             }
10051         }
10052         break;
10053     case OPC_RECIP_D:
10054         check_cp1_registers(ctx, fs | fd);
10055         {
10056             TCGv_i64 fp0 = tcg_temp_new_i64();
10057 
10058             gen_load_fpr64(ctx, fp0, fs);
10059             gen_helper_float_recip_d(fp0, tcg_env, fp0);
10060             gen_store_fpr64(ctx, fp0, fd);
10061         }
10062         break;
10063     case OPC_RSQRT_D:
10064         check_cp1_registers(ctx, fs | fd);
10065         {
10066             TCGv_i64 fp0 = tcg_temp_new_i64();
10067 
10068             gen_load_fpr64(ctx, fp0, fs);
10069             gen_helper_float_rsqrt_d(fp0, tcg_env, fp0);
10070             gen_store_fpr64(ctx, fp0, fd);
10071         }
10072         break;
10073     case OPC_MADDF_D:
10074         check_insn(ctx, ISA_MIPS_R6);
10075         {
10076             TCGv_i64 fp0 = tcg_temp_new_i64();
10077             TCGv_i64 fp1 = tcg_temp_new_i64();
10078             TCGv_i64 fp2 = tcg_temp_new_i64();
10079             gen_load_fpr64(ctx, fp0, fs);
10080             gen_load_fpr64(ctx, fp1, ft);
10081             gen_load_fpr64(ctx, fp2, fd);
10082             gen_helper_float_maddf_d(fp2, tcg_env, fp0, fp1, fp2);
10083             gen_store_fpr64(ctx, fp2, fd);
10084         }
10085         break;
10086     case OPC_MSUBF_D:
10087         check_insn(ctx, ISA_MIPS_R6);
10088         {
10089             TCGv_i64 fp0 = tcg_temp_new_i64();
10090             TCGv_i64 fp1 = tcg_temp_new_i64();
10091             TCGv_i64 fp2 = tcg_temp_new_i64();
10092             gen_load_fpr64(ctx, fp0, fs);
10093             gen_load_fpr64(ctx, fp1, ft);
10094             gen_load_fpr64(ctx, fp2, fd);
10095             gen_helper_float_msubf_d(fp2, tcg_env, fp0, fp1, fp2);
10096             gen_store_fpr64(ctx, fp2, fd);
10097         }
10098         break;
10099     case OPC_RINT_D:
10100         check_insn(ctx, ISA_MIPS_R6);
10101         {
10102             TCGv_i64 fp0 = tcg_temp_new_i64();
10103             gen_load_fpr64(ctx, fp0, fs);
10104             gen_helper_float_rint_d(fp0, tcg_env, fp0);
10105             gen_store_fpr64(ctx, fp0, fd);
10106         }
10107         break;
10108     case OPC_CLASS_D:
10109         check_insn(ctx, ISA_MIPS_R6);
10110         {
10111             TCGv_i64 fp0 = tcg_temp_new_i64();
10112             gen_load_fpr64(ctx, fp0, fs);
10113             gen_helper_float_class_d(fp0, tcg_env, fp0);
10114             gen_store_fpr64(ctx, fp0, fd);
10115         }
10116         break;
10117     case OPC_MIN_D: /* OPC_RECIP2_D */
10118         if (ctx->insn_flags & ISA_MIPS_R6) {
10119             /* OPC_MIN_D */
10120             TCGv_i64 fp0 = tcg_temp_new_i64();
10121             TCGv_i64 fp1 = tcg_temp_new_i64();
10122             gen_load_fpr64(ctx, fp0, fs);
10123             gen_load_fpr64(ctx, fp1, ft);
10124             gen_helper_float_min_d(fp1, tcg_env, fp0, fp1);
10125             gen_store_fpr64(ctx, fp1, fd);
10126         } else {
10127             /* OPC_RECIP2_D */
10128             check_cp1_64bitmode(ctx);
10129             {
10130                 TCGv_i64 fp0 = tcg_temp_new_i64();
10131                 TCGv_i64 fp1 = tcg_temp_new_i64();
10132 
10133                 gen_load_fpr64(ctx, fp0, fs);
10134                 gen_load_fpr64(ctx, fp1, ft);
10135                 gen_helper_float_recip2_d(fp0, tcg_env, fp0, fp1);
10136                 gen_store_fpr64(ctx, fp0, fd);
10137             }
10138         }
10139         break;
10140     case OPC_MINA_D: /* OPC_RECIP1_D */
10141         if (ctx->insn_flags & ISA_MIPS_R6) {
10142             /* OPC_MINA_D */
10143             TCGv_i64 fp0 = tcg_temp_new_i64();
10144             TCGv_i64 fp1 = tcg_temp_new_i64();
10145             gen_load_fpr64(ctx, fp0, fs);
10146             gen_load_fpr64(ctx, fp1, ft);
10147             gen_helper_float_mina_d(fp1, tcg_env, fp0, fp1);
10148             gen_store_fpr64(ctx, fp1, fd);
10149         } else {
10150             /* OPC_RECIP1_D */
10151             check_cp1_64bitmode(ctx);
10152             {
10153                 TCGv_i64 fp0 = tcg_temp_new_i64();
10154 
10155                 gen_load_fpr64(ctx, fp0, fs);
10156                 gen_helper_float_recip1_d(fp0, tcg_env, fp0);
10157                 gen_store_fpr64(ctx, fp0, fd);
10158             }
10159         }
10160         break;
10161     case OPC_MAX_D: /*  OPC_RSQRT1_D */
10162         if (ctx->insn_flags & ISA_MIPS_R6) {
10163             /* OPC_MAX_D */
10164             TCGv_i64 fp0 = tcg_temp_new_i64();
10165             TCGv_i64 fp1 = tcg_temp_new_i64();
10166             gen_load_fpr64(ctx, fp0, fs);
10167             gen_load_fpr64(ctx, fp1, ft);
10168             gen_helper_float_max_d(fp1, tcg_env, fp0, fp1);
10169             gen_store_fpr64(ctx, fp1, fd);
10170         } else {
10171             /* OPC_RSQRT1_D */
10172             check_cp1_64bitmode(ctx);
10173             {
10174                 TCGv_i64 fp0 = tcg_temp_new_i64();
10175 
10176                 gen_load_fpr64(ctx, fp0, fs);
10177                 gen_helper_float_rsqrt1_d(fp0, tcg_env, fp0);
10178                 gen_store_fpr64(ctx, fp0, fd);
10179             }
10180         }
10181         break;
10182     case OPC_MAXA_D: /* OPC_RSQRT2_D */
10183         if (ctx->insn_flags & ISA_MIPS_R6) {
10184             /* OPC_MAXA_D */
10185             TCGv_i64 fp0 = tcg_temp_new_i64();
10186             TCGv_i64 fp1 = tcg_temp_new_i64();
10187             gen_load_fpr64(ctx, fp0, fs);
10188             gen_load_fpr64(ctx, fp1, ft);
10189             gen_helper_float_maxa_d(fp1, tcg_env, fp0, fp1);
10190             gen_store_fpr64(ctx, fp1, fd);
10191         } else {
10192             /* OPC_RSQRT2_D */
10193             check_cp1_64bitmode(ctx);
10194             {
10195                 TCGv_i64 fp0 = tcg_temp_new_i64();
10196                 TCGv_i64 fp1 = tcg_temp_new_i64();
10197 
10198                 gen_load_fpr64(ctx, fp0, fs);
10199                 gen_load_fpr64(ctx, fp1, ft);
10200                 gen_helper_float_rsqrt2_d(fp0, tcg_env, fp0, fp1);
10201                 gen_store_fpr64(ctx, fp0, fd);
10202             }
10203         }
10204         break;
10205     case OPC_CMP_F_D:
10206     case OPC_CMP_UN_D:
10207     case OPC_CMP_EQ_D:
10208     case OPC_CMP_UEQ_D:
10209     case OPC_CMP_OLT_D:
10210     case OPC_CMP_ULT_D:
10211     case OPC_CMP_OLE_D:
10212     case OPC_CMP_ULE_D:
10213     case OPC_CMP_SF_D:
10214     case OPC_CMP_NGLE_D:
10215     case OPC_CMP_SEQ_D:
10216     case OPC_CMP_NGL_D:
10217     case OPC_CMP_LT_D:
10218     case OPC_CMP_NGE_D:
10219     case OPC_CMP_LE_D:
10220     case OPC_CMP_NGT_D:
10221         check_insn_opc_removed(ctx, ISA_MIPS_R6);
10222         if (ctx->opcode & (1 << 6)) {
10223             gen_cmpabs_d(ctx, func - 48, ft, fs, cc);
10224         } else {
10225             gen_cmp_d(ctx, func - 48, ft, fs, cc);
10226         }
10227         break;
10228     case OPC_CVT_S_D:
10229         check_cp1_registers(ctx, fs);
10230         {
10231             TCGv_i32 fp32 = tcg_temp_new_i32();
10232             TCGv_i64 fp64 = tcg_temp_new_i64();
10233 
10234             gen_load_fpr64(ctx, fp64, fs);
10235             gen_helper_float_cvts_d(fp32, tcg_env, fp64);
10236             gen_store_fpr32(ctx, fp32, fd);
10237         }
10238         break;
10239     case OPC_CVT_W_D:
10240         check_cp1_registers(ctx, fs);
10241         {
10242             TCGv_i32 fp32 = tcg_temp_new_i32();
10243             TCGv_i64 fp64 = tcg_temp_new_i64();
10244 
10245             gen_load_fpr64(ctx, fp64, fs);
10246             if (ctx->nan2008) {
10247                 gen_helper_float_cvt_2008_w_d(fp32, tcg_env, fp64);
10248             } else {
10249                 gen_helper_float_cvt_w_d(fp32, tcg_env, fp64);
10250             }
10251             gen_store_fpr32(ctx, fp32, fd);
10252         }
10253         break;
10254     case OPC_CVT_L_D:
10255         check_cp1_64bitmode(ctx);
10256         {
10257             TCGv_i64 fp0 = tcg_temp_new_i64();
10258 
10259             gen_load_fpr64(ctx, fp0, fs);
10260             if (ctx->nan2008) {
10261                 gen_helper_float_cvt_2008_l_d(fp0, tcg_env, fp0);
10262             } else {
10263                 gen_helper_float_cvt_l_d(fp0, tcg_env, fp0);
10264             }
10265             gen_store_fpr64(ctx, fp0, fd);
10266         }
10267         break;
10268     case OPC_CVT_S_W:
10269         {
10270             TCGv_i32 fp0 = tcg_temp_new_i32();
10271 
10272             gen_load_fpr32(ctx, fp0, fs);
10273             gen_helper_float_cvts_w(fp0, tcg_env, fp0);
10274             gen_store_fpr32(ctx, fp0, fd);
10275         }
10276         break;
10277     case OPC_CVT_D_W:
10278         check_cp1_registers(ctx, fd);
10279         {
10280             TCGv_i32 fp32 = tcg_temp_new_i32();
10281             TCGv_i64 fp64 = tcg_temp_new_i64();
10282 
10283             gen_load_fpr32(ctx, fp32, fs);
10284             gen_helper_float_cvtd_w(fp64, tcg_env, fp32);
10285             gen_store_fpr64(ctx, fp64, fd);
10286         }
10287         break;
10288     case OPC_CVT_S_L:
10289         check_cp1_64bitmode(ctx);
10290         {
10291             TCGv_i32 fp32 = tcg_temp_new_i32();
10292             TCGv_i64 fp64 = tcg_temp_new_i64();
10293 
10294             gen_load_fpr64(ctx, fp64, fs);
10295             gen_helper_float_cvts_l(fp32, tcg_env, fp64);
10296             gen_store_fpr32(ctx, fp32, fd);
10297         }
10298         break;
10299     case OPC_CVT_D_L:
10300         check_cp1_64bitmode(ctx);
10301         {
10302             TCGv_i64 fp0 = tcg_temp_new_i64();
10303 
10304             gen_load_fpr64(ctx, fp0, fs);
10305             gen_helper_float_cvtd_l(fp0, tcg_env, fp0);
10306             gen_store_fpr64(ctx, fp0, fd);
10307         }
10308         break;
10309     case OPC_CVT_PS_PW:
10310         check_ps(ctx);
10311         {
10312             TCGv_i64 fp0 = tcg_temp_new_i64();
10313 
10314             gen_load_fpr64(ctx, fp0, fs);
10315             gen_helper_float_cvtps_pw(fp0, tcg_env, fp0);
10316             gen_store_fpr64(ctx, fp0, fd);
10317         }
10318         break;
10319     case OPC_ADD_PS:
10320         check_ps(ctx);
10321         {
10322             TCGv_i64 fp0 = tcg_temp_new_i64();
10323             TCGv_i64 fp1 = tcg_temp_new_i64();
10324 
10325             gen_load_fpr64(ctx, fp0, fs);
10326             gen_load_fpr64(ctx, fp1, ft);
10327             gen_helper_float_add_ps(fp0, tcg_env, fp0, fp1);
10328             gen_store_fpr64(ctx, fp0, fd);
10329         }
10330         break;
10331     case OPC_SUB_PS:
10332         check_ps(ctx);
10333         {
10334             TCGv_i64 fp0 = tcg_temp_new_i64();
10335             TCGv_i64 fp1 = tcg_temp_new_i64();
10336 
10337             gen_load_fpr64(ctx, fp0, fs);
10338             gen_load_fpr64(ctx, fp1, ft);
10339             gen_helper_float_sub_ps(fp0, tcg_env, fp0, fp1);
10340             gen_store_fpr64(ctx, fp0, fd);
10341         }
10342         break;
10343     case OPC_MUL_PS:
10344         check_ps(ctx);
10345         {
10346             TCGv_i64 fp0 = tcg_temp_new_i64();
10347             TCGv_i64 fp1 = tcg_temp_new_i64();
10348 
10349             gen_load_fpr64(ctx, fp0, fs);
10350             gen_load_fpr64(ctx, fp1, ft);
10351             gen_helper_float_mul_ps(fp0, tcg_env, fp0, fp1);
10352             gen_store_fpr64(ctx, fp0, fd);
10353         }
10354         break;
10355     case OPC_ABS_PS:
10356         check_ps(ctx);
10357         {
10358             TCGv_i64 fp0 = tcg_temp_new_i64();
10359 
10360             gen_load_fpr64(ctx, fp0, fs);
10361             gen_helper_float_abs_ps(fp0, fp0);
10362             gen_store_fpr64(ctx, fp0, fd);
10363         }
10364         break;
10365     case OPC_MOV_PS:
10366         check_ps(ctx);
10367         {
10368             TCGv_i64 fp0 = tcg_temp_new_i64();
10369 
10370             gen_load_fpr64(ctx, fp0, fs);
10371             gen_store_fpr64(ctx, fp0, fd);
10372         }
10373         break;
10374     case OPC_NEG_PS:
10375         check_ps(ctx);
10376         {
10377             TCGv_i64 fp0 = tcg_temp_new_i64();
10378 
10379             gen_load_fpr64(ctx, fp0, fs);
10380             gen_helper_float_chs_ps(fp0, fp0);
10381             gen_store_fpr64(ctx, fp0, fd);
10382         }
10383         break;
10384     case OPC_MOVCF_PS:
10385         check_ps(ctx);
10386         gen_movcf_ps(ctx, fs, fd, (ft >> 2) & 0x7, ft & 0x1);
10387         break;
10388     case OPC_MOVZ_PS:
10389         check_ps(ctx);
10390         {
10391             TCGLabel *l1 = gen_new_label();
10392             TCGv_i64 fp0;
10393 
10394             if (ft != 0) {
10395                 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[ft], 0, l1);
10396             }
10397             fp0 = tcg_temp_new_i64();
10398             gen_load_fpr64(ctx, fp0, fs);
10399             gen_store_fpr64(ctx, fp0, fd);
10400             gen_set_label(l1);
10401         }
10402         break;
10403     case OPC_MOVN_PS:
10404         check_ps(ctx);
10405         {
10406             TCGLabel *l1 = gen_new_label();
10407             TCGv_i64 fp0;
10408 
10409             if (ft != 0) {
10410                 tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[ft], 0, l1);
10411                 fp0 = tcg_temp_new_i64();
10412                 gen_load_fpr64(ctx, fp0, fs);
10413                 gen_store_fpr64(ctx, fp0, fd);
10414                 gen_set_label(l1);
10415             }
10416         }
10417         break;
10418     case OPC_ADDR_PS:
10419         check_ps(ctx);
10420         {
10421             TCGv_i64 fp0 = tcg_temp_new_i64();
10422             TCGv_i64 fp1 = tcg_temp_new_i64();
10423 
10424             gen_load_fpr64(ctx, fp0, ft);
10425             gen_load_fpr64(ctx, fp1, fs);
10426             gen_helper_float_addr_ps(fp0, tcg_env, fp0, fp1);
10427             gen_store_fpr64(ctx, fp0, fd);
10428         }
10429         break;
10430     case OPC_MULR_PS:
10431         check_ps(ctx);
10432         {
10433             TCGv_i64 fp0 = tcg_temp_new_i64();
10434             TCGv_i64 fp1 = tcg_temp_new_i64();
10435 
10436             gen_load_fpr64(ctx, fp0, ft);
10437             gen_load_fpr64(ctx, fp1, fs);
10438             gen_helper_float_mulr_ps(fp0, tcg_env, fp0, fp1);
10439             gen_store_fpr64(ctx, fp0, fd);
10440         }
10441         break;
10442     case OPC_RECIP2_PS:
10443         check_ps(ctx);
10444         {
10445             TCGv_i64 fp0 = tcg_temp_new_i64();
10446             TCGv_i64 fp1 = tcg_temp_new_i64();
10447 
10448             gen_load_fpr64(ctx, fp0, fs);
10449             gen_load_fpr64(ctx, fp1, ft);
10450             gen_helper_float_recip2_ps(fp0, tcg_env, fp0, fp1);
10451             gen_store_fpr64(ctx, fp0, fd);
10452         }
10453         break;
10454     case OPC_RECIP1_PS:
10455         check_ps(ctx);
10456         {
10457             TCGv_i64 fp0 = tcg_temp_new_i64();
10458 
10459             gen_load_fpr64(ctx, fp0, fs);
10460             gen_helper_float_recip1_ps(fp0, tcg_env, fp0);
10461             gen_store_fpr64(ctx, fp0, fd);
10462         }
10463         break;
10464     case OPC_RSQRT1_PS:
10465         check_ps(ctx);
10466         {
10467             TCGv_i64 fp0 = tcg_temp_new_i64();
10468 
10469             gen_load_fpr64(ctx, fp0, fs);
10470             gen_helper_float_rsqrt1_ps(fp0, tcg_env, fp0);
10471             gen_store_fpr64(ctx, fp0, fd);
10472         }
10473         break;
10474     case OPC_RSQRT2_PS:
10475         check_ps(ctx);
10476         {
10477             TCGv_i64 fp0 = tcg_temp_new_i64();
10478             TCGv_i64 fp1 = tcg_temp_new_i64();
10479 
10480             gen_load_fpr64(ctx, fp0, fs);
10481             gen_load_fpr64(ctx, fp1, ft);
10482             gen_helper_float_rsqrt2_ps(fp0, tcg_env, fp0, fp1);
10483             gen_store_fpr64(ctx, fp0, fd);
10484         }
10485         break;
10486     case OPC_CVT_S_PU:
10487         check_cp1_64bitmode(ctx);
10488         {
10489             TCGv_i32 fp0 = tcg_temp_new_i32();
10490 
10491             gen_load_fpr32h(ctx, fp0, fs);
10492             gen_helper_float_cvts_pu(fp0, tcg_env, fp0);
10493             gen_store_fpr32(ctx, fp0, fd);
10494         }
10495         break;
10496     case OPC_CVT_PW_PS:
10497         check_ps(ctx);
10498         {
10499             TCGv_i64 fp0 = tcg_temp_new_i64();
10500 
10501             gen_load_fpr64(ctx, fp0, fs);
10502             gen_helper_float_cvtpw_ps(fp0, tcg_env, fp0);
10503             gen_store_fpr64(ctx, fp0, fd);
10504         }
10505         break;
10506     case OPC_CVT_S_PL:
10507         check_cp1_64bitmode(ctx);
10508         {
10509             TCGv_i32 fp0 = tcg_temp_new_i32();
10510 
10511             gen_load_fpr32(ctx, fp0, fs);
10512             gen_helper_float_cvts_pl(fp0, tcg_env, fp0);
10513             gen_store_fpr32(ctx, fp0, fd);
10514         }
10515         break;
10516     case OPC_PLL_PS:
10517         check_ps(ctx);
10518         {
10519             TCGv_i32 fp0 = tcg_temp_new_i32();
10520             TCGv_i32 fp1 = tcg_temp_new_i32();
10521 
10522             gen_load_fpr32(ctx, fp0, fs);
10523             gen_load_fpr32(ctx, fp1, ft);
10524             gen_store_fpr32h(ctx, fp0, fd);
10525             gen_store_fpr32(ctx, fp1, fd);
10526         }
10527         break;
10528     case OPC_PLU_PS:
10529         check_ps(ctx);
10530         {
10531             TCGv_i32 fp0 = tcg_temp_new_i32();
10532             TCGv_i32 fp1 = tcg_temp_new_i32();
10533 
10534             gen_load_fpr32(ctx, fp0, fs);
10535             gen_load_fpr32h(ctx, fp1, ft);
10536             gen_store_fpr32(ctx, fp1, fd);
10537             gen_store_fpr32h(ctx, fp0, fd);
10538         }
10539         break;
10540     case OPC_PUL_PS:
10541         check_ps(ctx);
10542         {
10543             TCGv_i32 fp0 = tcg_temp_new_i32();
10544             TCGv_i32 fp1 = tcg_temp_new_i32();
10545 
10546             gen_load_fpr32h(ctx, fp0, fs);
10547             gen_load_fpr32(ctx, fp1, ft);
10548             gen_store_fpr32(ctx, fp1, fd);
10549             gen_store_fpr32h(ctx, fp0, fd);
10550         }
10551         break;
10552     case OPC_PUU_PS:
10553         check_ps(ctx);
10554         {
10555             TCGv_i32 fp0 = tcg_temp_new_i32();
10556             TCGv_i32 fp1 = tcg_temp_new_i32();
10557 
10558             gen_load_fpr32h(ctx, fp0, fs);
10559             gen_load_fpr32h(ctx, fp1, ft);
10560             gen_store_fpr32(ctx, fp1, fd);
10561             gen_store_fpr32h(ctx, fp0, fd);
10562         }
10563         break;
10564     case OPC_CMP_F_PS:
10565     case OPC_CMP_UN_PS:
10566     case OPC_CMP_EQ_PS:
10567     case OPC_CMP_UEQ_PS:
10568     case OPC_CMP_OLT_PS:
10569     case OPC_CMP_ULT_PS:
10570     case OPC_CMP_OLE_PS:
10571     case OPC_CMP_ULE_PS:
10572     case OPC_CMP_SF_PS:
10573     case OPC_CMP_NGLE_PS:
10574     case OPC_CMP_SEQ_PS:
10575     case OPC_CMP_NGL_PS:
10576     case OPC_CMP_LT_PS:
10577     case OPC_CMP_NGE_PS:
10578     case OPC_CMP_LE_PS:
10579     case OPC_CMP_NGT_PS:
10580         if (ctx->opcode & (1 << 6)) {
10581             gen_cmpabs_ps(ctx, func - 48, ft, fs, cc);
10582         } else {
10583             gen_cmp_ps(ctx, func - 48, ft, fs, cc);
10584         }
10585         break;
10586     default:
10587         MIPS_INVAL("farith");
10588         gen_reserved_instruction(ctx);
10589         return;
10590     }
10591 }
10592 
10593 /* Coprocessor 3 (FPU) */
10594 static void gen_flt3_ldst(DisasContext *ctx, uint32_t opc,
10595                           int fd, int fs, int base, int index)
10596 {
10597     TCGv t0 = tcg_temp_new();
10598 
10599     if (base == 0) {
10600         gen_load_gpr(t0, index);
10601     } else if (index == 0) {
10602         gen_load_gpr(t0, base);
10603     } else {
10604         gen_op_addr_add(ctx, t0, cpu_gpr[base], cpu_gpr[index]);
10605     }
10606     /*
10607      * Don't do NOP if destination is zero: we must perform the actual
10608      * memory access.
10609      */
10610     switch (opc) {
10611     case OPC_LWXC1:
10612         check_cop1x(ctx);
10613         {
10614             TCGv_i32 fp0 = tcg_temp_new_i32();
10615 
10616             tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, mo_endian(ctx) | MO_SL);
10617             tcg_gen_trunc_tl_i32(fp0, t0);
10618             gen_store_fpr32(ctx, fp0, fd);
10619         }
10620         break;
10621     case OPC_LDXC1:
10622         check_cop1x(ctx);
10623         check_cp1_registers(ctx, fd);
10624         {
10625             TCGv_i64 fp0 = tcg_temp_new_i64();
10626             tcg_gen_qemu_ld_i64(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ);
10627             gen_store_fpr64(ctx, fp0, fd);
10628         }
10629         break;
10630     case OPC_LUXC1:
10631         check_cp1_64bitmode(ctx);
10632         tcg_gen_andi_tl(t0, t0, ~0x7);
10633         {
10634             TCGv_i64 fp0 = tcg_temp_new_i64();
10635 
10636             tcg_gen_qemu_ld_i64(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ);
10637             gen_store_fpr64(ctx, fp0, fd);
10638         }
10639         break;
10640     case OPC_SWXC1:
10641         check_cop1x(ctx);
10642         {
10643             TCGv_i32 fp0 = tcg_temp_new_i32();
10644             gen_load_fpr32(ctx, fp0, fs);
10645             tcg_gen_qemu_st_i32(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UL);
10646         }
10647         break;
10648     case OPC_SDXC1:
10649         check_cop1x(ctx);
10650         check_cp1_registers(ctx, fs);
10651         {
10652             TCGv_i64 fp0 = tcg_temp_new_i64();
10653             gen_load_fpr64(ctx, fp0, fs);
10654             tcg_gen_qemu_st_i64(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ);
10655         }
10656         break;
10657     case OPC_SUXC1:
10658         check_cp1_64bitmode(ctx);
10659         tcg_gen_andi_tl(t0, t0, ~0x7);
10660         {
10661             TCGv_i64 fp0 = tcg_temp_new_i64();
10662             gen_load_fpr64(ctx, fp0, fs);
10663             tcg_gen_qemu_st_i64(fp0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ);
10664         }
10665         break;
10666     }
10667 }
10668 
10669 static void gen_flt3_arith(DisasContext *ctx, uint32_t opc,
10670                            int fd, int fr, int fs, int ft)
10671 {
10672     switch (opc) {
10673     case OPC_ALNV_PS:
10674         check_ps(ctx);
10675         {
10676             TCGv t0 = tcg_temp_new();
10677             TCGv_i32 fp = tcg_temp_new_i32();
10678             TCGv_i32 fph = tcg_temp_new_i32();
10679             TCGLabel *l1 = gen_new_label();
10680             TCGLabel *l2 = gen_new_label();
10681 
10682             gen_load_gpr(t0, fr);
10683             tcg_gen_andi_tl(t0, t0, 0x7);
10684 
10685             tcg_gen_brcondi_tl(TCG_COND_NE, t0, 0, l1);
10686             gen_load_fpr32(ctx, fp, fs);
10687             gen_load_fpr32h(ctx, fph, fs);
10688             gen_store_fpr32(ctx, fp, fd);
10689             gen_store_fpr32h(ctx, fph, fd);
10690             tcg_gen_br(l2);
10691             gen_set_label(l1);
10692             tcg_gen_brcondi_tl(TCG_COND_NE, t0, 4, l2);
10693             if (disas_is_bigendian(ctx)) {
10694                 gen_load_fpr32(ctx, fp, fs);
10695                 gen_load_fpr32h(ctx, fph, ft);
10696                 gen_store_fpr32h(ctx, fp, fd);
10697                 gen_store_fpr32(ctx, fph, fd);
10698             } else {
10699                 gen_load_fpr32h(ctx, fph, fs);
10700                 gen_load_fpr32(ctx, fp, ft);
10701                 gen_store_fpr32(ctx, fph, fd);
10702                 gen_store_fpr32h(ctx, fp, fd);
10703             }
10704             gen_set_label(l2);
10705         }
10706         break;
10707     case OPC_MADD_S:
10708         check_cop1x(ctx);
10709         {
10710             TCGv_i32 fp0 = tcg_temp_new_i32();
10711             TCGv_i32 fp1 = tcg_temp_new_i32();
10712             TCGv_i32 fp2 = tcg_temp_new_i32();
10713 
10714             gen_load_fpr32(ctx, fp0, fs);
10715             gen_load_fpr32(ctx, fp1, ft);
10716             gen_load_fpr32(ctx, fp2, fr);
10717             gen_helper_float_madd_s(fp2, tcg_env, fp0, fp1, fp2);
10718             gen_store_fpr32(ctx, fp2, fd);
10719         }
10720         break;
10721     case OPC_MADD_D:
10722         check_cop1x(ctx);
10723         check_cp1_registers(ctx, fd | fs | ft | fr);
10724         {
10725             TCGv_i64 fp0 = tcg_temp_new_i64();
10726             TCGv_i64 fp1 = tcg_temp_new_i64();
10727             TCGv_i64 fp2 = tcg_temp_new_i64();
10728 
10729             gen_load_fpr64(ctx, fp0, fs);
10730             gen_load_fpr64(ctx, fp1, ft);
10731             gen_load_fpr64(ctx, fp2, fr);
10732             gen_helper_float_madd_d(fp2, tcg_env, fp0, fp1, fp2);
10733             gen_store_fpr64(ctx, fp2, fd);
10734         }
10735         break;
10736     case OPC_MADD_PS:
10737         check_ps(ctx);
10738         {
10739             TCGv_i64 fp0 = tcg_temp_new_i64();
10740             TCGv_i64 fp1 = tcg_temp_new_i64();
10741             TCGv_i64 fp2 = tcg_temp_new_i64();
10742 
10743             gen_load_fpr64(ctx, fp0, fs);
10744             gen_load_fpr64(ctx, fp1, ft);
10745             gen_load_fpr64(ctx, fp2, fr);
10746             gen_helper_float_madd_ps(fp2, tcg_env, fp0, fp1, fp2);
10747             gen_store_fpr64(ctx, fp2, fd);
10748         }
10749         break;
10750     case OPC_MSUB_S:
10751         check_cop1x(ctx);
10752         {
10753             TCGv_i32 fp0 = tcg_temp_new_i32();
10754             TCGv_i32 fp1 = tcg_temp_new_i32();
10755             TCGv_i32 fp2 = tcg_temp_new_i32();
10756 
10757             gen_load_fpr32(ctx, fp0, fs);
10758             gen_load_fpr32(ctx, fp1, ft);
10759             gen_load_fpr32(ctx, fp2, fr);
10760             gen_helper_float_msub_s(fp2, tcg_env, fp0, fp1, fp2);
10761             gen_store_fpr32(ctx, fp2, fd);
10762         }
10763         break;
10764     case OPC_MSUB_D:
10765         check_cop1x(ctx);
10766         check_cp1_registers(ctx, fd | fs | ft | fr);
10767         {
10768             TCGv_i64 fp0 = tcg_temp_new_i64();
10769             TCGv_i64 fp1 = tcg_temp_new_i64();
10770             TCGv_i64 fp2 = tcg_temp_new_i64();
10771 
10772             gen_load_fpr64(ctx, fp0, fs);
10773             gen_load_fpr64(ctx, fp1, ft);
10774             gen_load_fpr64(ctx, fp2, fr);
10775             gen_helper_float_msub_d(fp2, tcg_env, fp0, fp1, fp2);
10776             gen_store_fpr64(ctx, fp2, fd);
10777         }
10778         break;
10779     case OPC_MSUB_PS:
10780         check_ps(ctx);
10781         {
10782             TCGv_i64 fp0 = tcg_temp_new_i64();
10783             TCGv_i64 fp1 = tcg_temp_new_i64();
10784             TCGv_i64 fp2 = tcg_temp_new_i64();
10785 
10786             gen_load_fpr64(ctx, fp0, fs);
10787             gen_load_fpr64(ctx, fp1, ft);
10788             gen_load_fpr64(ctx, fp2, fr);
10789             gen_helper_float_msub_ps(fp2, tcg_env, fp0, fp1, fp2);
10790             gen_store_fpr64(ctx, fp2, fd);
10791         }
10792         break;
10793     case OPC_NMADD_S:
10794         check_cop1x(ctx);
10795         {
10796             TCGv_i32 fp0 = tcg_temp_new_i32();
10797             TCGv_i32 fp1 = tcg_temp_new_i32();
10798             TCGv_i32 fp2 = tcg_temp_new_i32();
10799 
10800             gen_load_fpr32(ctx, fp0, fs);
10801             gen_load_fpr32(ctx, fp1, ft);
10802             gen_load_fpr32(ctx, fp2, fr);
10803             gen_helper_float_nmadd_s(fp2, tcg_env, fp0, fp1, fp2);
10804             gen_store_fpr32(ctx, fp2, fd);
10805         }
10806         break;
10807     case OPC_NMADD_D:
10808         check_cop1x(ctx);
10809         check_cp1_registers(ctx, fd | fs | ft | fr);
10810         {
10811             TCGv_i64 fp0 = tcg_temp_new_i64();
10812             TCGv_i64 fp1 = tcg_temp_new_i64();
10813             TCGv_i64 fp2 = tcg_temp_new_i64();
10814 
10815             gen_load_fpr64(ctx, fp0, fs);
10816             gen_load_fpr64(ctx, fp1, ft);
10817             gen_load_fpr64(ctx, fp2, fr);
10818             gen_helper_float_nmadd_d(fp2, tcg_env, fp0, fp1, fp2);
10819             gen_store_fpr64(ctx, fp2, fd);
10820         }
10821         break;
10822     case OPC_NMADD_PS:
10823         check_ps(ctx);
10824         {
10825             TCGv_i64 fp0 = tcg_temp_new_i64();
10826             TCGv_i64 fp1 = tcg_temp_new_i64();
10827             TCGv_i64 fp2 = tcg_temp_new_i64();
10828 
10829             gen_load_fpr64(ctx, fp0, fs);
10830             gen_load_fpr64(ctx, fp1, ft);
10831             gen_load_fpr64(ctx, fp2, fr);
10832             gen_helper_float_nmadd_ps(fp2, tcg_env, fp0, fp1, fp2);
10833             gen_store_fpr64(ctx, fp2, fd);
10834         }
10835         break;
10836     case OPC_NMSUB_S:
10837         check_cop1x(ctx);
10838         {
10839             TCGv_i32 fp0 = tcg_temp_new_i32();
10840             TCGv_i32 fp1 = tcg_temp_new_i32();
10841             TCGv_i32 fp2 = tcg_temp_new_i32();
10842 
10843             gen_load_fpr32(ctx, fp0, fs);
10844             gen_load_fpr32(ctx, fp1, ft);
10845             gen_load_fpr32(ctx, fp2, fr);
10846             gen_helper_float_nmsub_s(fp2, tcg_env, fp0, fp1, fp2);
10847             gen_store_fpr32(ctx, fp2, fd);
10848         }
10849         break;
10850     case OPC_NMSUB_D:
10851         check_cop1x(ctx);
10852         check_cp1_registers(ctx, fd | fs | ft | fr);
10853         {
10854             TCGv_i64 fp0 = tcg_temp_new_i64();
10855             TCGv_i64 fp1 = tcg_temp_new_i64();
10856             TCGv_i64 fp2 = tcg_temp_new_i64();
10857 
10858             gen_load_fpr64(ctx, fp0, fs);
10859             gen_load_fpr64(ctx, fp1, ft);
10860             gen_load_fpr64(ctx, fp2, fr);
10861             gen_helper_float_nmsub_d(fp2, tcg_env, fp0, fp1, fp2);
10862             gen_store_fpr64(ctx, fp2, fd);
10863         }
10864         break;
10865     case OPC_NMSUB_PS:
10866         check_ps(ctx);
10867         {
10868             TCGv_i64 fp0 = tcg_temp_new_i64();
10869             TCGv_i64 fp1 = tcg_temp_new_i64();
10870             TCGv_i64 fp2 = tcg_temp_new_i64();
10871 
10872             gen_load_fpr64(ctx, fp0, fs);
10873             gen_load_fpr64(ctx, fp1, ft);
10874             gen_load_fpr64(ctx, fp2, fr);
10875             gen_helper_float_nmsub_ps(fp2, tcg_env, fp0, fp1, fp2);
10876             gen_store_fpr64(ctx, fp2, fd);
10877         }
10878         break;
10879     default:
10880         MIPS_INVAL("flt3_arith");
10881         gen_reserved_instruction(ctx);
10882         return;
10883     }
10884 }
10885 
10886 void gen_rdhwr(DisasContext *ctx, int rt, int rd, int sel)
10887 {
10888     TCGv t0;
10889 
10890 #if !defined(CONFIG_USER_ONLY)
10891     /*
10892      * The Linux kernel will emulate rdhwr if it's not supported natively.
10893      * Therefore only check the ISA in system mode.
10894      */
10895     check_insn(ctx, ISA_MIPS_R2);
10896 #endif
10897     t0 = tcg_temp_new();
10898 
10899     switch (rd) {
10900     case 0:
10901         gen_helper_rdhwr_cpunum(t0, tcg_env);
10902         gen_store_gpr(t0, rt);
10903         break;
10904     case 1:
10905         gen_helper_rdhwr_synci_step(t0, tcg_env);
10906         gen_store_gpr(t0, rt);
10907         break;
10908     case 2:
10909         translator_io_start(&ctx->base);
10910         gen_helper_rdhwr_cc(t0, tcg_env);
10911         gen_store_gpr(t0, rt);
10912         /*
10913          * Break the TB to be able to take timer interrupts immediately
10914          * after reading count. DISAS_STOP isn't sufficient, we need to ensure
10915          * we break completely out of translated code.
10916          */
10917         gen_save_pc(ctx->base.pc_next + 4);
10918         ctx->base.is_jmp = DISAS_EXIT;
10919         break;
10920     case 3:
10921         gen_helper_rdhwr_ccres(t0, tcg_env);
10922         gen_store_gpr(t0, rt);
10923         break;
10924     case 4:
10925         check_insn(ctx, ISA_MIPS_R6);
10926         if (sel != 0) {
10927             /*
10928              * Performance counter registers are not implemented other than
10929              * control register 0.
10930              */
10931             generate_exception(ctx, EXCP_RI);
10932         }
10933         gen_helper_rdhwr_performance(t0, tcg_env);
10934         gen_store_gpr(t0, rt);
10935         break;
10936     case 5:
10937         check_insn(ctx, ISA_MIPS_R6);
10938         gen_helper_rdhwr_xnp(t0, tcg_env);
10939         gen_store_gpr(t0, rt);
10940         break;
10941     case 29:
10942 #if defined(CONFIG_USER_ONLY)
10943         tcg_gen_ld_tl(t0, tcg_env,
10944                       offsetof(CPUMIPSState, active_tc.CP0_UserLocal));
10945         gen_store_gpr(t0, rt);
10946         break;
10947 #else
10948         if ((ctx->hflags & MIPS_HFLAG_CP0) ||
10949             (ctx->hflags & MIPS_HFLAG_HWRENA_ULR)) {
10950             tcg_gen_ld_tl(t0, tcg_env,
10951                           offsetof(CPUMIPSState, active_tc.CP0_UserLocal));
10952             gen_store_gpr(t0, rt);
10953         } else {
10954             gen_reserved_instruction(ctx);
10955         }
10956         break;
10957 #endif
10958     default:            /* Invalid */
10959         MIPS_INVAL("rdhwr");
10960         gen_reserved_instruction(ctx);
10961         break;
10962     }
10963 }
10964 
10965 static inline void clear_branch_hflags(DisasContext *ctx)
10966 {
10967     ctx->hflags &= ~MIPS_HFLAG_BMASK;
10968     if (ctx->base.is_jmp == DISAS_NEXT) {
10969         save_cpu_state(ctx, 0);
10970     } else {
10971         /*
10972          * It is not safe to save ctx->hflags as hflags may be changed
10973          * in execution time by the instruction in delay / forbidden slot.
10974          */
10975         tcg_gen_andi_i32(hflags, hflags, ~MIPS_HFLAG_BMASK);
10976     }
10977 }
10978 
10979 static void gen_branch(DisasContext *ctx, int insn_bytes)
10980 {
10981     if (ctx->hflags & MIPS_HFLAG_BMASK) {
10982         int proc_hflags = ctx->hflags & MIPS_HFLAG_BMASK;
10983         /* Branches completion */
10984         clear_branch_hflags(ctx);
10985         ctx->base.is_jmp = DISAS_NORETURN;
10986         switch (proc_hflags & MIPS_HFLAG_BMASK_BASE) {
10987         case MIPS_HFLAG_FBNSLOT:
10988             gen_goto_tb(ctx, 0, ctx->base.pc_next + insn_bytes);
10989             break;
10990         case MIPS_HFLAG_B:
10991             /* unconditional branch */
10992             if (proc_hflags & MIPS_HFLAG_BX) {
10993                 tcg_gen_xori_i32(hflags, hflags, MIPS_HFLAG_M16);
10994             }
10995             gen_goto_tb(ctx, 0, ctx->btarget);
10996             break;
10997         case MIPS_HFLAG_BL:
10998             /* blikely taken case */
10999             gen_goto_tb(ctx, 0, ctx->btarget);
11000             break;
11001         case MIPS_HFLAG_BC:
11002             /* Conditional branch */
11003             {
11004                 TCGLabel *l1 = gen_new_label();
11005 
11006                 tcg_gen_brcondi_tl(TCG_COND_NE, bcond, 0, l1);
11007                 gen_goto_tb(ctx, 1, ctx->base.pc_next + insn_bytes);
11008                 gen_set_label(l1);
11009                 gen_goto_tb(ctx, 0, ctx->btarget);
11010             }
11011             break;
11012         case MIPS_HFLAG_BR:
11013             /* unconditional branch to register */
11014             if (ctx->insn_flags & (ASE_MIPS16 | ASE_MICROMIPS)) {
11015                 TCGv t0 = tcg_temp_new();
11016                 TCGv_i32 t1 = tcg_temp_new_i32();
11017 
11018                 tcg_gen_andi_tl(t0, btarget, 0x1);
11019                 tcg_gen_trunc_tl_i32(t1, t0);
11020                 tcg_gen_andi_i32(hflags, hflags, ~(uint32_t)MIPS_HFLAG_M16);
11021                 tcg_gen_shli_i32(t1, t1, MIPS_HFLAG_M16_SHIFT);
11022                 tcg_gen_or_i32(hflags, hflags, t1);
11023 
11024                 tcg_gen_andi_tl(cpu_PC, btarget, ~(target_ulong)0x1);
11025             } else {
11026                 tcg_gen_mov_tl(cpu_PC, btarget);
11027             }
11028             tcg_gen_lookup_and_goto_ptr();
11029             break;
11030         default:
11031             LOG_DISAS("unknown branch 0x%x\n", proc_hflags);
11032             gen_reserved_instruction(ctx);
11033         }
11034     }
11035 }
11036 
11037 /* Compact Branches */
11038 static void gen_compute_compact_branch(DisasContext *ctx, uint32_t opc,
11039                                        int rs, int rt, int32_t offset)
11040 {
11041     int bcond_compute = 0;
11042     TCGv t0 = tcg_temp_new();
11043     TCGv t1 = tcg_temp_new();
11044     int m16_lowbit = (ctx->hflags & MIPS_HFLAG_M16) != 0;
11045 
11046     if (ctx->hflags & MIPS_HFLAG_BMASK) {
11047 #ifdef MIPS_DEBUG_DISAS
11048         LOG_DISAS("Branch in delay / forbidden slot at PC 0x%016"
11049                   VADDR_PRIx "\n", ctx->base.pc_next);
11050 #endif
11051         gen_reserved_instruction(ctx);
11052         return;
11053     }
11054 
11055     /* Load needed operands and calculate btarget */
11056     switch (opc) {
11057     /* compact branch */
11058     case OPC_BOVC: /* OPC_BEQZALC, OPC_BEQC */
11059     case OPC_BNVC: /* OPC_BNEZALC, OPC_BNEC */
11060         gen_load_gpr(t0, rs);
11061         gen_load_gpr(t1, rt);
11062         bcond_compute = 1;
11063         ctx->btarget = addr_add(ctx, ctx->base.pc_next + 4, offset);
11064         if (rs <= rt && rs == 0) {
11065             /* OPC_BEQZALC, OPC_BNEZALC */
11066             tcg_gen_movi_tl(cpu_gpr[31], ctx->base.pc_next + 4 + m16_lowbit);
11067         }
11068         break;
11069     case OPC_BLEZC: /* OPC_BGEZC, OPC_BGEC */
11070     case OPC_BGTZC: /* OPC_BLTZC, OPC_BLTC */
11071         gen_load_gpr(t0, rs);
11072         gen_load_gpr(t1, rt);
11073         bcond_compute = 1;
11074         ctx->btarget = addr_add(ctx, ctx->base.pc_next + 4, offset);
11075         break;
11076     case OPC_BLEZALC: /* OPC_BGEZALC, OPC_BGEUC */
11077     case OPC_BGTZALC: /* OPC_BLTZALC, OPC_BLTUC */
11078         if (rs == 0 || rs == rt) {
11079             /* OPC_BLEZALC, OPC_BGEZALC */
11080             /* OPC_BGTZALC, OPC_BLTZALC */
11081             tcg_gen_movi_tl(cpu_gpr[31], ctx->base.pc_next + 4 + m16_lowbit);
11082         }
11083         gen_load_gpr(t0, rs);
11084         gen_load_gpr(t1, rt);
11085         bcond_compute = 1;
11086         ctx->btarget = addr_add(ctx, ctx->base.pc_next + 4, offset);
11087         break;
11088     case OPC_BC:
11089     case OPC_BALC:
11090         ctx->btarget = addr_add(ctx, ctx->base.pc_next + 4, offset);
11091         break;
11092     case OPC_BEQZC:
11093     case OPC_BNEZC:
11094         if (rs != 0) {
11095             /* OPC_BEQZC, OPC_BNEZC */
11096             gen_load_gpr(t0, rs);
11097             bcond_compute = 1;
11098             ctx->btarget = addr_add(ctx, ctx->base.pc_next + 4, offset);
11099         } else {
11100             /* OPC_JIC, OPC_JIALC */
11101             TCGv tbase = tcg_temp_new();
11102 
11103             gen_load_gpr(tbase, rt);
11104             gen_op_addr_addi(ctx, btarget, tbase, offset);
11105         }
11106         break;
11107     default:
11108         MIPS_INVAL("Compact branch/jump");
11109         gen_reserved_instruction(ctx);
11110         return;
11111     }
11112 
11113     if (bcond_compute == 0) {
11114         /* Unconditional compact branch */
11115         switch (opc) {
11116         case OPC_JIALC:
11117             tcg_gen_movi_tl(cpu_gpr[31], ctx->base.pc_next + 4 + m16_lowbit);
11118             /* Fallthrough */
11119         case OPC_JIC:
11120             ctx->hflags |= MIPS_HFLAG_BR;
11121             break;
11122         case OPC_BALC:
11123             tcg_gen_movi_tl(cpu_gpr[31], ctx->base.pc_next + 4 + m16_lowbit);
11124             /* Fallthrough */
11125         case OPC_BC:
11126             ctx->hflags |= MIPS_HFLAG_B;
11127             break;
11128         default:
11129             MIPS_INVAL("Compact branch/jump");
11130             gen_reserved_instruction(ctx);
11131             return;
11132         }
11133 
11134         /* Generating branch here as compact branches don't have delay slot */
11135         gen_branch(ctx, 4);
11136     } else {
11137         /* Conditional compact branch */
11138         TCGLabel *fs = gen_new_label();
11139         save_cpu_state(ctx, 0);
11140 
11141         switch (opc) {
11142         case OPC_BLEZALC: /* OPC_BGEZALC, OPC_BGEUC */
11143             if (rs == 0 && rt != 0) {
11144                 /* OPC_BLEZALC */
11145                 tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_LE), t1, 0, fs);
11146             } else if (rs != 0 && rt != 0 && rs == rt) {
11147                 /* OPC_BGEZALC */
11148                 tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_GE), t1, 0, fs);
11149             } else {
11150                 /* OPC_BGEUC */
11151                 tcg_gen_brcond_tl(tcg_invert_cond(TCG_COND_GEU), t0, t1, fs);
11152             }
11153             break;
11154         case OPC_BGTZALC: /* OPC_BLTZALC, OPC_BLTUC */
11155             if (rs == 0 && rt != 0) {
11156                 /* OPC_BGTZALC */
11157                 tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_GT), t1, 0, fs);
11158             } else if (rs != 0 && rt != 0 && rs == rt) {
11159                 /* OPC_BLTZALC */
11160                 tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_LT), t1, 0, fs);
11161             } else {
11162                 /* OPC_BLTUC */
11163                 tcg_gen_brcond_tl(tcg_invert_cond(TCG_COND_LTU), t0, t1, fs);
11164             }
11165             break;
11166         case OPC_BLEZC: /* OPC_BGEZC, OPC_BGEC */
11167             if (rs == 0 && rt != 0) {
11168                 /* OPC_BLEZC */
11169                 tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_LE), t1, 0, fs);
11170             } else if (rs != 0 && rt != 0 && rs == rt) {
11171                 /* OPC_BGEZC */
11172                 tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_GE), t1, 0, fs);
11173             } else {
11174                 /* OPC_BGEC */
11175                 tcg_gen_brcond_tl(tcg_invert_cond(TCG_COND_GE), t0, t1, fs);
11176             }
11177             break;
11178         case OPC_BGTZC: /* OPC_BLTZC, OPC_BLTC */
11179             if (rs == 0 && rt != 0) {
11180                 /* OPC_BGTZC */
11181                 tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_GT), t1, 0, fs);
11182             } else if (rs != 0 && rt != 0 && rs == rt) {
11183                 /* OPC_BLTZC */
11184                 tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_LT), t1, 0, fs);
11185             } else {
11186                 /* OPC_BLTC */
11187                 tcg_gen_brcond_tl(tcg_invert_cond(TCG_COND_LT), t0, t1, fs);
11188             }
11189             break;
11190         case OPC_BOVC: /* OPC_BEQZALC, OPC_BEQC */
11191         case OPC_BNVC: /* OPC_BNEZALC, OPC_BNEC */
11192             if (rs >= rt) {
11193                 /* OPC_BOVC, OPC_BNVC */
11194                 TCGv t2 = tcg_temp_new();
11195                 TCGv t3 = tcg_temp_new();
11196                 TCGv t4 = tcg_temp_new();
11197                 TCGv input_overflow = tcg_temp_new();
11198 
11199                 gen_load_gpr(t0, rs);
11200                 gen_load_gpr(t1, rt);
11201                 tcg_gen_ext32s_tl(t2, t0);
11202                 tcg_gen_setcond_tl(TCG_COND_NE, input_overflow, t2, t0);
11203                 tcg_gen_ext32s_tl(t3, t1);
11204                 tcg_gen_setcond_tl(TCG_COND_NE, t4, t3, t1);
11205                 tcg_gen_or_tl(input_overflow, input_overflow, t4);
11206 
11207                 tcg_gen_add_tl(t4, t2, t3);
11208                 tcg_gen_ext32s_tl(t4, t4);
11209                 tcg_gen_xor_tl(t2, t2, t3);
11210                 tcg_gen_xor_tl(t3, t4, t3);
11211                 tcg_gen_andc_tl(t2, t3, t2);
11212                 tcg_gen_setcondi_tl(TCG_COND_LT, t4, t2, 0);
11213                 tcg_gen_or_tl(t4, t4, input_overflow);
11214                 if (opc == OPC_BOVC) {
11215                     /* OPC_BOVC */
11216                     tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_NE), t4, 0, fs);
11217                 } else {
11218                     /* OPC_BNVC */
11219                     tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_EQ), t4, 0, fs);
11220                 }
11221             } else if (rs < rt && rs == 0) {
11222                 /* OPC_BEQZALC, OPC_BNEZALC */
11223                 if (opc == OPC_BEQZALC) {
11224                     /* OPC_BEQZALC */
11225                     tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_EQ), t1, 0, fs);
11226                 } else {
11227                     /* OPC_BNEZALC */
11228                     tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_NE), t1, 0, fs);
11229                 }
11230             } else {
11231                 /* OPC_BEQC, OPC_BNEC */
11232                 if (opc == OPC_BEQC) {
11233                     /* OPC_BEQC */
11234                     tcg_gen_brcond_tl(tcg_invert_cond(TCG_COND_EQ), t0, t1, fs);
11235                 } else {
11236                     /* OPC_BNEC */
11237                     tcg_gen_brcond_tl(tcg_invert_cond(TCG_COND_NE), t0, t1, fs);
11238                 }
11239             }
11240             break;
11241         case OPC_BEQZC:
11242             tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_EQ), t0, 0, fs);
11243             break;
11244         case OPC_BNEZC:
11245             tcg_gen_brcondi_tl(tcg_invert_cond(TCG_COND_NE), t0, 0, fs);
11246             break;
11247         default:
11248             MIPS_INVAL("Compact conditional branch/jump");
11249             gen_reserved_instruction(ctx);
11250             return;
11251         }
11252 
11253         /* Generating branch here as compact branches don't have delay slot */
11254         gen_goto_tb(ctx, 1, ctx->btarget);
11255         gen_set_label(fs);
11256 
11257         ctx->hflags |= MIPS_HFLAG_FBNSLOT;
11258     }
11259 }
11260 
11261 void gen_addiupc(DisasContext *ctx, int rx, int imm,
11262                  int is_64_bit, int extended)
11263 {
11264     target_ulong npc;
11265 
11266     if (extended && (ctx->hflags & MIPS_HFLAG_BMASK)) {
11267         gen_reserved_instruction(ctx);
11268         return;
11269     }
11270 
11271     npc = pc_relative_pc(ctx) + imm;
11272     if (!is_64_bit) {
11273         npc = (int32_t)npc;
11274     }
11275     tcg_gen_movi_tl(cpu_gpr[rx], npc);
11276 }
11277 
11278 static void gen_cache_operation(DisasContext *ctx, uint32_t op, int base,
11279                                 int16_t offset)
11280 {
11281     TCGv_i32 t0 = tcg_constant_i32(op);
11282     TCGv t1 = tcg_temp_new();
11283     gen_base_offset_addr(ctx, t1, base, offset);
11284     gen_helper_cache(tcg_env, t1, t0);
11285 }
11286 
11287 static inline bool is_uhi(DisasContext *ctx, int sdbbp_code)
11288 {
11289 #ifdef CONFIG_USER_ONLY
11290     return false;
11291 #else
11292     bool is_user = (ctx->hflags & MIPS_HFLAG_KSU) == MIPS_HFLAG_UM;
11293     return semihosting_enabled(is_user) && sdbbp_code == 1;
11294 #endif
11295 }
11296 
11297 void gen_ldxs(DisasContext *ctx, int base, int index, int rd)
11298 {
11299     TCGv t0 = tcg_temp_new();
11300     TCGv t1 = tcg_temp_new();
11301 
11302     gen_load_gpr(t0, base);
11303 
11304     if (index != 0) {
11305         gen_load_gpr(t1, index);
11306         tcg_gen_shli_tl(t1, t1, 2);
11307         gen_op_addr_add(ctx, t0, t1, t0);
11308     }
11309 
11310     tcg_gen_qemu_ld_tl(t1, t0, ctx->mem_idx, mo_endian(ctx) | MO_SL);
11311     gen_store_gpr(t1, rd);
11312 }
11313 
11314 static void gen_sync(int stype)
11315 {
11316     TCGBar tcg_mo = TCG_BAR_SC;
11317 
11318     switch (stype) {
11319     case 0x4: /* SYNC_WMB */
11320         tcg_mo |= TCG_MO_ST_ST;
11321         break;
11322     case 0x10: /* SYNC_MB */
11323         tcg_mo |= TCG_MO_ALL;
11324         break;
11325     case 0x11: /* SYNC_ACQUIRE */
11326         tcg_mo |= TCG_MO_LD_LD | TCG_MO_LD_ST;
11327         break;
11328     case 0x12: /* SYNC_RELEASE */
11329         tcg_mo |= TCG_MO_ST_ST | TCG_MO_LD_ST;
11330         break;
11331     case 0x13: /* SYNC_RMB */
11332         tcg_mo |= TCG_MO_LD_LD;
11333         break;
11334     default:
11335         tcg_mo |= TCG_MO_ALL;
11336         break;
11337     }
11338 
11339     tcg_gen_mb(tcg_mo);
11340 }
11341 
11342 /* ISA extensions (ASEs) */
11343 
11344 /* MIPS16 extension to MIPS32 */
11345 #include "mips16e_translate.c.inc"
11346 
11347 /* microMIPS extension to MIPS32/MIPS64 */
11348 
11349 /*
11350  * Values for microMIPS fmt field.  Variable-width, depending on which
11351  * formats the instruction supports.
11352  */
11353 enum {
11354     FMT_SD_S = 0,
11355     FMT_SD_D = 1,
11356 
11357     FMT_SDPS_S = 0,
11358     FMT_SDPS_D = 1,
11359     FMT_SDPS_PS = 2,
11360 
11361     FMT_SWL_S = 0,
11362     FMT_SWL_W = 1,
11363     FMT_SWL_L = 2,
11364 
11365     FMT_DWL_D = 0,
11366     FMT_DWL_W = 1,
11367     FMT_DWL_L = 2
11368 };
11369 
11370 #include "micromips_translate.c.inc"
11371 
11372 #include "nanomips_translate.c.inc"
11373 
11374 /* MIPSDSP functions. */
11375 
11376 /* Indexed load is not for DSP only */
11377 static void gen_mips_lx(DisasContext *ctx, uint32_t opc,
11378                         int rd, int base, int offset)
11379 {
11380     TCGv t0;
11381 
11382     if (!(ctx->insn_flags & INSN_OCTEON)) {
11383         check_dsp(ctx);
11384     }
11385     t0 = tcg_temp_new();
11386 
11387     if (base == 0) {
11388         gen_load_gpr(t0, offset);
11389     } else if (offset == 0) {
11390         gen_load_gpr(t0, base);
11391     } else {
11392         gen_op_addr_add(ctx, t0, cpu_gpr[base], cpu_gpr[offset]);
11393     }
11394 
11395     switch (opc) {
11396     case OPC_LBUX:
11397         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, MO_UB);
11398         gen_store_gpr(t0, rd);
11399         break;
11400     case OPC_LHX:
11401         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, mo_endian(ctx) | MO_SW);
11402         gen_store_gpr(t0, rd);
11403         break;
11404     case OPC_LWX:
11405         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, mo_endian(ctx) | MO_SL);
11406         gen_store_gpr(t0, rd);
11407         break;
11408 #if defined(TARGET_MIPS64)
11409     case OPC_LDX:
11410         tcg_gen_qemu_ld_tl(t0, t0, ctx->mem_idx, mo_endian(ctx) | MO_UQ);
11411         gen_store_gpr(t0, rd);
11412         break;
11413 #endif
11414     }
11415 }
11416 
11417 static void gen_mipsdsp_arith(DisasContext *ctx, uint32_t op1, uint32_t op2,
11418                               int ret, int v1, int v2)
11419 {
11420     TCGv v1_t;
11421     TCGv v2_t;
11422 
11423     if (ret == 0) {
11424         /* Treat as NOP. */
11425         return;
11426     }
11427 
11428     v1_t = tcg_temp_new();
11429     v2_t = tcg_temp_new();
11430 
11431     gen_load_gpr(v1_t, v1);
11432     gen_load_gpr(v2_t, v2);
11433 
11434     switch (op1) {
11435     case OPC_ADDUH_QB_DSP:
11436         check_dsp_r2(ctx);
11437         switch (op2) {
11438         case OPC_ADDUH_QB:
11439             gen_helper_adduh_qb(cpu_gpr[ret], v1_t, v2_t);
11440             break;
11441         case OPC_ADDUH_R_QB:
11442             gen_helper_adduh_r_qb(cpu_gpr[ret], v1_t, v2_t);
11443             break;
11444         case OPC_ADDQH_PH:
11445             gen_helper_addqh_ph(cpu_gpr[ret], v1_t, v2_t);
11446             break;
11447         case OPC_ADDQH_R_PH:
11448             gen_helper_addqh_r_ph(cpu_gpr[ret], v1_t, v2_t);
11449             break;
11450         case OPC_ADDQH_W:
11451             gen_helper_addqh_w(cpu_gpr[ret], v1_t, v2_t);
11452             break;
11453         case OPC_ADDQH_R_W:
11454             gen_helper_addqh_r_w(cpu_gpr[ret], v1_t, v2_t);
11455             break;
11456         case OPC_SUBUH_QB:
11457             gen_helper_subuh_qb(cpu_gpr[ret], v1_t, v2_t);
11458             break;
11459         case OPC_SUBUH_R_QB:
11460             gen_helper_subuh_r_qb(cpu_gpr[ret], v1_t, v2_t);
11461             break;
11462         case OPC_SUBQH_PH:
11463             gen_helper_subqh_ph(cpu_gpr[ret], v1_t, v2_t);
11464             break;
11465         case OPC_SUBQH_R_PH:
11466             gen_helper_subqh_r_ph(cpu_gpr[ret], v1_t, v2_t);
11467             break;
11468         case OPC_SUBQH_W:
11469             gen_helper_subqh_w(cpu_gpr[ret], v1_t, v2_t);
11470             break;
11471         case OPC_SUBQH_R_W:
11472             gen_helper_subqh_r_w(cpu_gpr[ret], v1_t, v2_t);
11473             break;
11474         }
11475         break;
11476     case OPC_ABSQ_S_PH_DSP:
11477         switch (op2) {
11478         case OPC_ABSQ_S_QB:
11479             check_dsp_r2(ctx);
11480             gen_helper_absq_s_qb(cpu_gpr[ret], v2_t, tcg_env);
11481             break;
11482         case OPC_ABSQ_S_PH:
11483             check_dsp(ctx);
11484             gen_helper_absq_s_ph(cpu_gpr[ret], v2_t, tcg_env);
11485             break;
11486         case OPC_ABSQ_S_W:
11487             check_dsp(ctx);
11488             gen_helper_absq_s_w(cpu_gpr[ret], v2_t, tcg_env);
11489             break;
11490         case OPC_PRECEQ_W_PHL:
11491             check_dsp(ctx);
11492             tcg_gen_andi_tl(cpu_gpr[ret], v2_t, 0xFFFF0000);
11493             tcg_gen_ext32s_tl(cpu_gpr[ret], cpu_gpr[ret]);
11494             break;
11495         case OPC_PRECEQ_W_PHR:
11496             check_dsp(ctx);
11497             tcg_gen_andi_tl(cpu_gpr[ret], v2_t, 0x0000FFFF);
11498             tcg_gen_shli_tl(cpu_gpr[ret], cpu_gpr[ret], 16);
11499             tcg_gen_ext32s_tl(cpu_gpr[ret], cpu_gpr[ret]);
11500             break;
11501         case OPC_PRECEQU_PH_QBL:
11502             check_dsp(ctx);
11503             gen_helper_precequ_ph_qbl(cpu_gpr[ret], v2_t);
11504             break;
11505         case OPC_PRECEQU_PH_QBR:
11506             check_dsp(ctx);
11507             gen_helper_precequ_ph_qbr(cpu_gpr[ret], v2_t);
11508             break;
11509         case OPC_PRECEQU_PH_QBLA:
11510             check_dsp(ctx);
11511             gen_helper_precequ_ph_qbla(cpu_gpr[ret], v2_t);
11512             break;
11513         case OPC_PRECEQU_PH_QBRA:
11514             check_dsp(ctx);
11515             gen_helper_precequ_ph_qbra(cpu_gpr[ret], v2_t);
11516             break;
11517         case OPC_PRECEU_PH_QBL:
11518             check_dsp(ctx);
11519             gen_helper_preceu_ph_qbl(cpu_gpr[ret], v2_t);
11520             break;
11521         case OPC_PRECEU_PH_QBR:
11522             check_dsp(ctx);
11523             gen_helper_preceu_ph_qbr(cpu_gpr[ret], v2_t);
11524             break;
11525         case OPC_PRECEU_PH_QBLA:
11526             check_dsp(ctx);
11527             gen_helper_preceu_ph_qbla(cpu_gpr[ret], v2_t);
11528             break;
11529         case OPC_PRECEU_PH_QBRA:
11530             check_dsp(ctx);
11531             gen_helper_preceu_ph_qbra(cpu_gpr[ret], v2_t);
11532             break;
11533         }
11534         break;
11535     case OPC_ADDU_QB_DSP:
11536         switch (op2) {
11537         case OPC_ADDQ_PH:
11538             check_dsp(ctx);
11539             gen_helper_addq_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11540             break;
11541         case OPC_ADDQ_S_PH:
11542             check_dsp(ctx);
11543             gen_helper_addq_s_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11544             break;
11545         case OPC_ADDQ_S_W:
11546             check_dsp(ctx);
11547             gen_helper_addq_s_w(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11548             break;
11549         case OPC_ADDU_QB:
11550             check_dsp(ctx);
11551             gen_helper_addu_qb(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11552             break;
11553         case OPC_ADDU_S_QB:
11554             check_dsp(ctx);
11555             gen_helper_addu_s_qb(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11556             break;
11557         case OPC_ADDU_PH:
11558             check_dsp_r2(ctx);
11559             gen_helper_addu_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11560             break;
11561         case OPC_ADDU_S_PH:
11562             check_dsp_r2(ctx);
11563             gen_helper_addu_s_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11564             break;
11565         case OPC_SUBQ_PH:
11566             check_dsp(ctx);
11567             gen_helper_subq_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11568             break;
11569         case OPC_SUBQ_S_PH:
11570             check_dsp(ctx);
11571             gen_helper_subq_s_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11572             break;
11573         case OPC_SUBQ_S_W:
11574             check_dsp(ctx);
11575             gen_helper_subq_s_w(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11576             break;
11577         case OPC_SUBU_QB:
11578             check_dsp(ctx);
11579             gen_helper_subu_qb(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11580             break;
11581         case OPC_SUBU_S_QB:
11582             check_dsp(ctx);
11583             gen_helper_subu_s_qb(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11584             break;
11585         case OPC_SUBU_PH:
11586             check_dsp_r2(ctx);
11587             gen_helper_subu_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11588             break;
11589         case OPC_SUBU_S_PH:
11590             check_dsp_r2(ctx);
11591             gen_helper_subu_s_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11592             break;
11593         case OPC_ADDSC:
11594             check_dsp(ctx);
11595             gen_helper_addsc(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11596             break;
11597         case OPC_ADDWC:
11598             check_dsp(ctx);
11599             gen_helper_addwc(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11600             break;
11601         case OPC_MODSUB:
11602             check_dsp(ctx);
11603             gen_helper_modsub(cpu_gpr[ret], v1_t, v2_t);
11604             break;
11605         case OPC_RADDU_W_QB:
11606             check_dsp(ctx);
11607             gen_helper_raddu_w_qb(cpu_gpr[ret], v1_t);
11608             break;
11609         }
11610         break;
11611     case OPC_CMPU_EQ_QB_DSP:
11612         switch (op2) {
11613         case OPC_PRECR_QB_PH:
11614             check_dsp_r2(ctx);
11615             gen_helper_precr_qb_ph(cpu_gpr[ret], v1_t, v2_t);
11616             break;
11617         case OPC_PRECRQ_QB_PH:
11618             check_dsp(ctx);
11619             gen_helper_precrq_qb_ph(cpu_gpr[ret], v1_t, v2_t);
11620             break;
11621         case OPC_PRECR_SRA_PH_W:
11622             check_dsp_r2(ctx);
11623             {
11624                 TCGv_i32 sa_t = tcg_constant_i32(v2);
11625                 gen_helper_precr_sra_ph_w(cpu_gpr[ret], sa_t, v1_t,
11626                                           cpu_gpr[ret]);
11627                 break;
11628             }
11629         case OPC_PRECR_SRA_R_PH_W:
11630             check_dsp_r2(ctx);
11631             {
11632                 TCGv_i32 sa_t = tcg_constant_i32(v2);
11633                 gen_helper_precr_sra_r_ph_w(cpu_gpr[ret], sa_t, v1_t,
11634                                             cpu_gpr[ret]);
11635                 break;
11636             }
11637         case OPC_PRECRQ_PH_W:
11638             check_dsp(ctx);
11639             gen_helper_precrq_ph_w(cpu_gpr[ret], v1_t, v2_t);
11640             break;
11641         case OPC_PRECRQ_RS_PH_W:
11642             check_dsp(ctx);
11643             gen_helper_precrq_rs_ph_w(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11644             break;
11645         case OPC_PRECRQU_S_QB_PH:
11646             check_dsp(ctx);
11647             gen_helper_precrqu_s_qb_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11648             break;
11649         }
11650         break;
11651 #ifdef TARGET_MIPS64
11652     case OPC_ABSQ_S_QH_DSP:
11653         switch (op2) {
11654         case OPC_PRECEQ_L_PWL:
11655             check_dsp(ctx);
11656             tcg_gen_andi_tl(cpu_gpr[ret], v2_t, 0xFFFFFFFF00000000ull);
11657             break;
11658         case OPC_PRECEQ_L_PWR:
11659             check_dsp(ctx);
11660             tcg_gen_shli_tl(cpu_gpr[ret], v2_t, 32);
11661             break;
11662         case OPC_PRECEQ_PW_QHL:
11663             check_dsp(ctx);
11664             gen_helper_preceq_pw_qhl(cpu_gpr[ret], v2_t);
11665             break;
11666         case OPC_PRECEQ_PW_QHR:
11667             check_dsp(ctx);
11668             gen_helper_preceq_pw_qhr(cpu_gpr[ret], v2_t);
11669             break;
11670         case OPC_PRECEQ_PW_QHLA:
11671             check_dsp(ctx);
11672             gen_helper_preceq_pw_qhla(cpu_gpr[ret], v2_t);
11673             break;
11674         case OPC_PRECEQ_PW_QHRA:
11675             check_dsp(ctx);
11676             gen_helper_preceq_pw_qhra(cpu_gpr[ret], v2_t);
11677             break;
11678         case OPC_PRECEQU_QH_OBL:
11679             check_dsp(ctx);
11680             gen_helper_precequ_qh_obl(cpu_gpr[ret], v2_t);
11681             break;
11682         case OPC_PRECEQU_QH_OBR:
11683             check_dsp(ctx);
11684             gen_helper_precequ_qh_obr(cpu_gpr[ret], v2_t);
11685             break;
11686         case OPC_PRECEQU_QH_OBLA:
11687             check_dsp(ctx);
11688             gen_helper_precequ_qh_obla(cpu_gpr[ret], v2_t);
11689             break;
11690         case OPC_PRECEQU_QH_OBRA:
11691             check_dsp(ctx);
11692             gen_helper_precequ_qh_obra(cpu_gpr[ret], v2_t);
11693             break;
11694         case OPC_PRECEU_QH_OBL:
11695             check_dsp(ctx);
11696             gen_helper_preceu_qh_obl(cpu_gpr[ret], v2_t);
11697             break;
11698         case OPC_PRECEU_QH_OBR:
11699             check_dsp(ctx);
11700             gen_helper_preceu_qh_obr(cpu_gpr[ret], v2_t);
11701             break;
11702         case OPC_PRECEU_QH_OBLA:
11703             check_dsp(ctx);
11704             gen_helper_preceu_qh_obla(cpu_gpr[ret], v2_t);
11705             break;
11706         case OPC_PRECEU_QH_OBRA:
11707             check_dsp(ctx);
11708             gen_helper_preceu_qh_obra(cpu_gpr[ret], v2_t);
11709             break;
11710         case OPC_ABSQ_S_OB:
11711             check_dsp_r2(ctx);
11712             gen_helper_absq_s_ob(cpu_gpr[ret], v2_t, tcg_env);
11713             break;
11714         case OPC_ABSQ_S_PW:
11715             check_dsp(ctx);
11716             gen_helper_absq_s_pw(cpu_gpr[ret], v2_t, tcg_env);
11717             break;
11718         case OPC_ABSQ_S_QH:
11719             check_dsp(ctx);
11720             gen_helper_absq_s_qh(cpu_gpr[ret], v2_t, tcg_env);
11721             break;
11722         }
11723         break;
11724     case OPC_ADDU_OB_DSP:
11725         switch (op2) {
11726         case OPC_RADDU_L_OB:
11727             check_dsp(ctx);
11728             gen_helper_raddu_l_ob(cpu_gpr[ret], v1_t);
11729             break;
11730         case OPC_SUBQ_PW:
11731             check_dsp(ctx);
11732             gen_helper_subq_pw(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11733             break;
11734         case OPC_SUBQ_S_PW:
11735             check_dsp(ctx);
11736             gen_helper_subq_s_pw(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11737             break;
11738         case OPC_SUBQ_QH:
11739             check_dsp(ctx);
11740             gen_helper_subq_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11741             break;
11742         case OPC_SUBQ_S_QH:
11743             check_dsp(ctx);
11744             gen_helper_subq_s_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11745             break;
11746         case OPC_SUBU_OB:
11747             check_dsp(ctx);
11748             gen_helper_subu_ob(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11749             break;
11750         case OPC_SUBU_S_OB:
11751             check_dsp(ctx);
11752             gen_helper_subu_s_ob(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11753             break;
11754         case OPC_SUBU_QH:
11755             check_dsp_r2(ctx);
11756             gen_helper_subu_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11757             break;
11758         case OPC_SUBU_S_QH:
11759             check_dsp_r2(ctx);
11760             gen_helper_subu_s_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11761             break;
11762         case OPC_SUBUH_OB:
11763             check_dsp_r2(ctx);
11764             gen_helper_subuh_ob(cpu_gpr[ret], v1_t, v2_t);
11765             break;
11766         case OPC_SUBUH_R_OB:
11767             check_dsp_r2(ctx);
11768             gen_helper_subuh_r_ob(cpu_gpr[ret], v1_t, v2_t);
11769             break;
11770         case OPC_ADDQ_PW:
11771             check_dsp(ctx);
11772             gen_helper_addq_pw(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11773             break;
11774         case OPC_ADDQ_S_PW:
11775             check_dsp(ctx);
11776             gen_helper_addq_s_pw(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11777             break;
11778         case OPC_ADDQ_QH:
11779             check_dsp(ctx);
11780             gen_helper_addq_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11781             break;
11782         case OPC_ADDQ_S_QH:
11783             check_dsp(ctx);
11784             gen_helper_addq_s_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11785             break;
11786         case OPC_ADDU_OB:
11787             check_dsp(ctx);
11788             gen_helper_addu_ob(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11789             break;
11790         case OPC_ADDU_S_OB:
11791             check_dsp(ctx);
11792             gen_helper_addu_s_ob(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11793             break;
11794         case OPC_ADDU_QH:
11795             check_dsp_r2(ctx);
11796             gen_helper_addu_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11797             break;
11798         case OPC_ADDU_S_QH:
11799             check_dsp_r2(ctx);
11800             gen_helper_addu_s_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11801             break;
11802         case OPC_ADDUH_OB:
11803             check_dsp_r2(ctx);
11804             gen_helper_adduh_ob(cpu_gpr[ret], v1_t, v2_t);
11805             break;
11806         case OPC_ADDUH_R_OB:
11807             check_dsp_r2(ctx);
11808             gen_helper_adduh_r_ob(cpu_gpr[ret], v1_t, v2_t);
11809             break;
11810         }
11811         break;
11812     case OPC_CMPU_EQ_OB_DSP:
11813         switch (op2) {
11814         case OPC_PRECR_OB_QH:
11815             check_dsp_r2(ctx);
11816             gen_helper_precr_ob_qh(cpu_gpr[ret], v1_t, v2_t);
11817             break;
11818         case OPC_PRECR_SRA_QH_PW:
11819             check_dsp_r2(ctx);
11820             {
11821                 TCGv_i32 ret_t = tcg_constant_i32(ret);
11822                 gen_helper_precr_sra_qh_pw(v2_t, v1_t, v2_t, ret_t);
11823                 break;
11824             }
11825         case OPC_PRECR_SRA_R_QH_PW:
11826             check_dsp_r2(ctx);
11827             {
11828                 TCGv_i32 sa_v = tcg_constant_i32(ret);
11829                 gen_helper_precr_sra_r_qh_pw(v2_t, v1_t, v2_t, sa_v);
11830                 break;
11831             }
11832         case OPC_PRECRQ_OB_QH:
11833             check_dsp(ctx);
11834             gen_helper_precrq_ob_qh(cpu_gpr[ret], v1_t, v2_t);
11835             break;
11836         case OPC_PRECRQ_PW_L:
11837             check_dsp(ctx);
11838             gen_helper_precrq_pw_l(cpu_gpr[ret], v1_t, v2_t);
11839             break;
11840         case OPC_PRECRQ_QH_PW:
11841             check_dsp(ctx);
11842             gen_helper_precrq_qh_pw(cpu_gpr[ret], v1_t, v2_t);
11843             break;
11844         case OPC_PRECRQ_RS_QH_PW:
11845             check_dsp(ctx);
11846             gen_helper_precrq_rs_qh_pw(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11847             break;
11848         case OPC_PRECRQU_S_OB_QH:
11849             check_dsp(ctx);
11850             gen_helper_precrqu_s_ob_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11851             break;
11852         }
11853         break;
11854 #endif
11855     }
11856 }
11857 
11858 static void gen_mipsdsp_shift(DisasContext *ctx, uint32_t opc,
11859                               int ret, int v1, int v2)
11860 {
11861     uint32_t op2;
11862     TCGv t0;
11863     TCGv v1_t;
11864     TCGv v2_t;
11865 
11866     if (ret == 0) {
11867         /* Treat as NOP. */
11868         return;
11869     }
11870 
11871     t0 = tcg_temp_new();
11872     v1_t = tcg_temp_new();
11873     v2_t = tcg_temp_new();
11874 
11875     tcg_gen_movi_tl(t0, v1);
11876     gen_load_gpr(v1_t, v1);
11877     gen_load_gpr(v2_t, v2);
11878 
11879     switch (opc) {
11880     case OPC_SHLL_QB_DSP:
11881         {
11882             op2 = MASK_SHLL_QB(ctx->opcode);
11883             switch (op2) {
11884             case OPC_SHLL_QB:
11885                 check_dsp(ctx);
11886                 gen_helper_shll_qb(cpu_gpr[ret], t0, v2_t, tcg_env);
11887                 break;
11888             case OPC_SHLLV_QB:
11889                 check_dsp(ctx);
11890                 gen_helper_shll_qb(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11891                 break;
11892             case OPC_SHLL_PH:
11893                 check_dsp(ctx);
11894                 gen_helper_shll_ph(cpu_gpr[ret], t0, v2_t, tcg_env);
11895                 break;
11896             case OPC_SHLLV_PH:
11897                 check_dsp(ctx);
11898                 gen_helper_shll_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11899                 break;
11900             case OPC_SHLL_S_PH:
11901                 check_dsp(ctx);
11902                 gen_helper_shll_s_ph(cpu_gpr[ret], t0, v2_t, tcg_env);
11903                 break;
11904             case OPC_SHLLV_S_PH:
11905                 check_dsp(ctx);
11906                 gen_helper_shll_s_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11907                 break;
11908             case OPC_SHLL_S_W:
11909                 check_dsp(ctx);
11910                 gen_helper_shll_s_w(cpu_gpr[ret], t0, v2_t, tcg_env);
11911                 break;
11912             case OPC_SHLLV_S_W:
11913                 check_dsp(ctx);
11914                 gen_helper_shll_s_w(cpu_gpr[ret], v1_t, v2_t, tcg_env);
11915                 break;
11916             case OPC_SHRL_QB:
11917                 check_dsp(ctx);
11918                 gen_helper_shrl_qb(cpu_gpr[ret], t0, v2_t);
11919                 break;
11920             case OPC_SHRLV_QB:
11921                 check_dsp(ctx);
11922                 gen_helper_shrl_qb(cpu_gpr[ret], v1_t, v2_t);
11923                 break;
11924             case OPC_SHRL_PH:
11925                 check_dsp_r2(ctx);
11926                 gen_helper_shrl_ph(cpu_gpr[ret], t0, v2_t);
11927                 break;
11928             case OPC_SHRLV_PH:
11929                 check_dsp_r2(ctx);
11930                 gen_helper_shrl_ph(cpu_gpr[ret], v1_t, v2_t);
11931                 break;
11932             case OPC_SHRA_QB:
11933                 check_dsp_r2(ctx);
11934                 gen_helper_shra_qb(cpu_gpr[ret], t0, v2_t);
11935                 break;
11936             case OPC_SHRA_R_QB:
11937                 check_dsp_r2(ctx);
11938                 gen_helper_shra_r_qb(cpu_gpr[ret], t0, v2_t);
11939                 break;
11940             case OPC_SHRAV_QB:
11941                 check_dsp_r2(ctx);
11942                 gen_helper_shra_qb(cpu_gpr[ret], v1_t, v2_t);
11943                 break;
11944             case OPC_SHRAV_R_QB:
11945                 check_dsp_r2(ctx);
11946                 gen_helper_shra_r_qb(cpu_gpr[ret], v1_t, v2_t);
11947                 break;
11948             case OPC_SHRA_PH:
11949                 check_dsp(ctx);
11950                 gen_helper_shra_ph(cpu_gpr[ret], t0, v2_t);
11951                 break;
11952             case OPC_SHRA_R_PH:
11953                 check_dsp(ctx);
11954                 gen_helper_shra_r_ph(cpu_gpr[ret], t0, v2_t);
11955                 break;
11956             case OPC_SHRAV_PH:
11957                 check_dsp(ctx);
11958                 gen_helper_shra_ph(cpu_gpr[ret], v1_t, v2_t);
11959                 break;
11960             case OPC_SHRAV_R_PH:
11961                 check_dsp(ctx);
11962                 gen_helper_shra_r_ph(cpu_gpr[ret], v1_t, v2_t);
11963                 break;
11964             case OPC_SHRA_R_W:
11965                 check_dsp(ctx);
11966                 gen_helper_shra_r_w(cpu_gpr[ret], t0, v2_t);
11967                 break;
11968             case OPC_SHRAV_R_W:
11969                 check_dsp(ctx);
11970                 gen_helper_shra_r_w(cpu_gpr[ret], v1_t, v2_t);
11971                 break;
11972             default:            /* Invalid */
11973                 MIPS_INVAL("MASK SHLL.QB");
11974                 gen_reserved_instruction(ctx);
11975                 break;
11976             }
11977             break;
11978         }
11979 #ifdef TARGET_MIPS64
11980     case OPC_SHLL_OB_DSP:
11981         op2 = MASK_SHLL_OB(ctx->opcode);
11982         switch (op2) {
11983         case OPC_SHLL_PW:
11984             check_dsp(ctx);
11985             gen_helper_shll_pw(cpu_gpr[ret], v2_t, t0, tcg_env);
11986             break;
11987         case OPC_SHLLV_PW:
11988             check_dsp(ctx);
11989             gen_helper_shll_pw(cpu_gpr[ret], v2_t, v1_t, tcg_env);
11990             break;
11991         case OPC_SHLL_S_PW:
11992             check_dsp(ctx);
11993             gen_helper_shll_s_pw(cpu_gpr[ret], v2_t, t0, tcg_env);
11994             break;
11995         case OPC_SHLLV_S_PW:
11996             check_dsp(ctx);
11997             gen_helper_shll_s_pw(cpu_gpr[ret], v2_t, v1_t, tcg_env);
11998             break;
11999         case OPC_SHLL_OB:
12000             check_dsp(ctx);
12001             gen_helper_shll_ob(cpu_gpr[ret], v2_t, t0, tcg_env);
12002             break;
12003         case OPC_SHLLV_OB:
12004             check_dsp(ctx);
12005             gen_helper_shll_ob(cpu_gpr[ret], v2_t, v1_t, tcg_env);
12006             break;
12007         case OPC_SHLL_QH:
12008             check_dsp(ctx);
12009             gen_helper_shll_qh(cpu_gpr[ret], v2_t, t0, tcg_env);
12010             break;
12011         case OPC_SHLLV_QH:
12012             check_dsp(ctx);
12013             gen_helper_shll_qh(cpu_gpr[ret], v2_t, v1_t, tcg_env);
12014             break;
12015         case OPC_SHLL_S_QH:
12016             check_dsp(ctx);
12017             gen_helper_shll_s_qh(cpu_gpr[ret], v2_t, t0, tcg_env);
12018             break;
12019         case OPC_SHLLV_S_QH:
12020             check_dsp(ctx);
12021             gen_helper_shll_s_qh(cpu_gpr[ret], v2_t, v1_t, tcg_env);
12022             break;
12023         case OPC_SHRA_OB:
12024             check_dsp_r2(ctx);
12025             gen_helper_shra_ob(cpu_gpr[ret], v2_t, t0);
12026             break;
12027         case OPC_SHRAV_OB:
12028             check_dsp_r2(ctx);
12029             gen_helper_shra_ob(cpu_gpr[ret], v2_t, v1_t);
12030             break;
12031         case OPC_SHRA_R_OB:
12032             check_dsp_r2(ctx);
12033             gen_helper_shra_r_ob(cpu_gpr[ret], v2_t, t0);
12034             break;
12035         case OPC_SHRAV_R_OB:
12036             check_dsp_r2(ctx);
12037             gen_helper_shra_r_ob(cpu_gpr[ret], v2_t, v1_t);
12038             break;
12039         case OPC_SHRA_PW:
12040             check_dsp(ctx);
12041             gen_helper_shra_pw(cpu_gpr[ret], v2_t, t0);
12042             break;
12043         case OPC_SHRAV_PW:
12044             check_dsp(ctx);
12045             gen_helper_shra_pw(cpu_gpr[ret], v2_t, v1_t);
12046             break;
12047         case OPC_SHRA_R_PW:
12048             check_dsp(ctx);
12049             gen_helper_shra_r_pw(cpu_gpr[ret], v2_t, t0);
12050             break;
12051         case OPC_SHRAV_R_PW:
12052             check_dsp(ctx);
12053             gen_helper_shra_r_pw(cpu_gpr[ret], v2_t, v1_t);
12054             break;
12055         case OPC_SHRA_QH:
12056             check_dsp(ctx);
12057             gen_helper_shra_qh(cpu_gpr[ret], v2_t, t0);
12058             break;
12059         case OPC_SHRAV_QH:
12060             check_dsp(ctx);
12061             gen_helper_shra_qh(cpu_gpr[ret], v2_t, v1_t);
12062             break;
12063         case OPC_SHRA_R_QH:
12064             check_dsp(ctx);
12065             gen_helper_shra_r_qh(cpu_gpr[ret], v2_t, t0);
12066             break;
12067         case OPC_SHRAV_R_QH:
12068             check_dsp(ctx);
12069             gen_helper_shra_r_qh(cpu_gpr[ret], v2_t, v1_t);
12070             break;
12071         case OPC_SHRL_OB:
12072             check_dsp(ctx);
12073             gen_helper_shrl_ob(cpu_gpr[ret], v2_t, t0);
12074             break;
12075         case OPC_SHRLV_OB:
12076             check_dsp(ctx);
12077             gen_helper_shrl_ob(cpu_gpr[ret], v2_t, v1_t);
12078             break;
12079         case OPC_SHRL_QH:
12080             check_dsp_r2(ctx);
12081             gen_helper_shrl_qh(cpu_gpr[ret], v2_t, t0);
12082             break;
12083         case OPC_SHRLV_QH:
12084             check_dsp_r2(ctx);
12085             gen_helper_shrl_qh(cpu_gpr[ret], v2_t, v1_t);
12086             break;
12087         default:            /* Invalid */
12088             MIPS_INVAL("MASK SHLL.OB");
12089             gen_reserved_instruction(ctx);
12090             break;
12091         }
12092         break;
12093 #endif
12094     }
12095 }
12096 
12097 static void gen_mipsdsp_multiply(DisasContext *ctx, uint32_t op1, uint32_t op2,
12098                                  int ret, int v1, int v2, int check_ret)
12099 {
12100     TCGv_i32 t0;
12101     TCGv v1_t;
12102     TCGv v2_t;
12103 
12104     if ((ret == 0) && (check_ret == 1)) {
12105         /* Treat as NOP. */
12106         return;
12107     }
12108 
12109     t0 = tcg_temp_new_i32();
12110     v1_t = tcg_temp_new();
12111     v2_t = tcg_temp_new();
12112 
12113     tcg_gen_movi_i32(t0, ret);
12114     gen_load_gpr(v1_t, v1);
12115     gen_load_gpr(v2_t, v2);
12116 
12117     switch (op1) {
12118     case OPC_MUL_PH_DSP:
12119         check_dsp_r2(ctx);
12120         switch (op2) {
12121         case  OPC_MUL_PH:
12122             gen_helper_mul_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12123             break;
12124         case  OPC_MUL_S_PH:
12125             gen_helper_mul_s_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12126             break;
12127         case OPC_MULQ_S_W:
12128             gen_helper_mulq_s_w(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12129             break;
12130         case OPC_MULQ_RS_W:
12131             gen_helper_mulq_rs_w(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12132             break;
12133         }
12134         break;
12135     case OPC_DPA_W_PH_DSP:
12136         switch (op2) {
12137         case OPC_DPAU_H_QBL:
12138             check_dsp(ctx);
12139             gen_helper_dpau_h_qbl(t0, v1_t, v2_t, tcg_env);
12140             break;
12141         case OPC_DPAU_H_QBR:
12142             check_dsp(ctx);
12143             gen_helper_dpau_h_qbr(t0, v1_t, v2_t, tcg_env);
12144             break;
12145         case OPC_DPSU_H_QBL:
12146             check_dsp(ctx);
12147             gen_helper_dpsu_h_qbl(t0, v1_t, v2_t, tcg_env);
12148             break;
12149         case OPC_DPSU_H_QBR:
12150             check_dsp(ctx);
12151             gen_helper_dpsu_h_qbr(t0, v1_t, v2_t, tcg_env);
12152             break;
12153         case OPC_DPA_W_PH:
12154             check_dsp_r2(ctx);
12155             gen_helper_dpa_w_ph(t0, v1_t, v2_t, tcg_env);
12156             break;
12157         case OPC_DPAX_W_PH:
12158             check_dsp_r2(ctx);
12159             gen_helper_dpax_w_ph(t0, v1_t, v2_t, tcg_env);
12160             break;
12161         case OPC_DPAQ_S_W_PH:
12162             check_dsp(ctx);
12163             gen_helper_dpaq_s_w_ph(t0, v1_t, v2_t, tcg_env);
12164             break;
12165         case OPC_DPAQX_S_W_PH:
12166             check_dsp_r2(ctx);
12167             gen_helper_dpaqx_s_w_ph(t0, v1_t, v2_t, tcg_env);
12168             break;
12169         case OPC_DPAQX_SA_W_PH:
12170             check_dsp_r2(ctx);
12171             gen_helper_dpaqx_sa_w_ph(t0, v1_t, v2_t, tcg_env);
12172             break;
12173         case OPC_DPS_W_PH:
12174             check_dsp_r2(ctx);
12175             gen_helper_dps_w_ph(t0, v1_t, v2_t, tcg_env);
12176             break;
12177         case OPC_DPSX_W_PH:
12178             check_dsp_r2(ctx);
12179             gen_helper_dpsx_w_ph(t0, v1_t, v2_t, tcg_env);
12180             break;
12181         case OPC_DPSQ_S_W_PH:
12182             check_dsp(ctx);
12183             gen_helper_dpsq_s_w_ph(t0, v1_t, v2_t, tcg_env);
12184             break;
12185         case OPC_DPSQX_S_W_PH:
12186             check_dsp_r2(ctx);
12187             gen_helper_dpsqx_s_w_ph(t0, v1_t, v2_t, tcg_env);
12188             break;
12189         case OPC_DPSQX_SA_W_PH:
12190             check_dsp_r2(ctx);
12191             gen_helper_dpsqx_sa_w_ph(t0, v1_t, v2_t, tcg_env);
12192             break;
12193         case OPC_MULSAQ_S_W_PH:
12194             check_dsp(ctx);
12195             gen_helper_mulsaq_s_w_ph(t0, v1_t, v2_t, tcg_env);
12196             break;
12197         case OPC_DPAQ_SA_L_W:
12198             check_dsp(ctx);
12199             gen_helper_dpaq_sa_l_w(t0, v1_t, v2_t, tcg_env);
12200             break;
12201         case OPC_DPSQ_SA_L_W:
12202             check_dsp(ctx);
12203             gen_helper_dpsq_sa_l_w(t0, v1_t, v2_t, tcg_env);
12204             break;
12205         case OPC_MAQ_S_W_PHL:
12206             check_dsp(ctx);
12207             gen_helper_maq_s_w_phl(t0, v1_t, v2_t, tcg_env);
12208             break;
12209         case OPC_MAQ_S_W_PHR:
12210             check_dsp(ctx);
12211             gen_helper_maq_s_w_phr(t0, v1_t, v2_t, tcg_env);
12212             break;
12213         case OPC_MAQ_SA_W_PHL:
12214             check_dsp(ctx);
12215             gen_helper_maq_sa_w_phl(t0, v1_t, v2_t, tcg_env);
12216             break;
12217         case OPC_MAQ_SA_W_PHR:
12218             check_dsp(ctx);
12219             gen_helper_maq_sa_w_phr(t0, v1_t, v2_t, tcg_env);
12220             break;
12221         case OPC_MULSA_W_PH:
12222             check_dsp_r2(ctx);
12223             gen_helper_mulsa_w_ph(t0, v1_t, v2_t, tcg_env);
12224             break;
12225         }
12226         break;
12227 #ifdef TARGET_MIPS64
12228     case OPC_DPAQ_W_QH_DSP:
12229         {
12230             int ac = ret & 0x03;
12231             tcg_gen_movi_i32(t0, ac);
12232 
12233             switch (op2) {
12234             case OPC_DMADD:
12235                 check_dsp(ctx);
12236                 gen_helper_dmadd(v1_t, v2_t, t0, tcg_env);
12237                 break;
12238             case OPC_DMADDU:
12239                 check_dsp(ctx);
12240                 gen_helper_dmaddu(v1_t, v2_t, t0, tcg_env);
12241                 break;
12242             case OPC_DMSUB:
12243                 check_dsp(ctx);
12244                 gen_helper_dmsub(v1_t, v2_t, t0, tcg_env);
12245                 break;
12246             case OPC_DMSUBU:
12247                 check_dsp(ctx);
12248                 gen_helper_dmsubu(v1_t, v2_t, t0, tcg_env);
12249                 break;
12250             case OPC_DPA_W_QH:
12251                 check_dsp_r2(ctx);
12252                 gen_helper_dpa_w_qh(v1_t, v2_t, t0, tcg_env);
12253                 break;
12254             case OPC_DPAQ_S_W_QH:
12255                 check_dsp(ctx);
12256                 gen_helper_dpaq_s_w_qh(v1_t, v2_t, t0, tcg_env);
12257                 break;
12258             case OPC_DPAQ_SA_L_PW:
12259                 check_dsp(ctx);
12260                 gen_helper_dpaq_sa_l_pw(v1_t, v2_t, t0, tcg_env);
12261                 break;
12262             case OPC_DPAU_H_OBL:
12263                 check_dsp(ctx);
12264                 gen_helper_dpau_h_obl(v1_t, v2_t, t0, tcg_env);
12265                 break;
12266             case OPC_DPAU_H_OBR:
12267                 check_dsp(ctx);
12268                 gen_helper_dpau_h_obr(v1_t, v2_t, t0, tcg_env);
12269                 break;
12270             case OPC_DPS_W_QH:
12271                 check_dsp_r2(ctx);
12272                 gen_helper_dps_w_qh(v1_t, v2_t, t0, tcg_env);
12273                 break;
12274             case OPC_DPSQ_S_W_QH:
12275                 check_dsp(ctx);
12276                 gen_helper_dpsq_s_w_qh(v1_t, v2_t, t0, tcg_env);
12277                 break;
12278             case OPC_DPSQ_SA_L_PW:
12279                 check_dsp(ctx);
12280                 gen_helper_dpsq_sa_l_pw(v1_t, v2_t, t0, tcg_env);
12281                 break;
12282             case OPC_DPSU_H_OBL:
12283                 check_dsp(ctx);
12284                 gen_helper_dpsu_h_obl(v1_t, v2_t, t0, tcg_env);
12285                 break;
12286             case OPC_DPSU_H_OBR:
12287                 check_dsp(ctx);
12288                 gen_helper_dpsu_h_obr(v1_t, v2_t, t0, tcg_env);
12289                 break;
12290             case OPC_MAQ_S_L_PWL:
12291                 check_dsp(ctx);
12292                 gen_helper_maq_s_l_pwl(v1_t, v2_t, t0, tcg_env);
12293                 break;
12294             case OPC_MAQ_S_L_PWR:
12295                 check_dsp(ctx);
12296                 gen_helper_maq_s_l_pwr(v1_t, v2_t, t0, tcg_env);
12297                 break;
12298             case OPC_MAQ_S_W_QHLL:
12299                 check_dsp(ctx);
12300                 gen_helper_maq_s_w_qhll(v1_t, v2_t, t0, tcg_env);
12301                 break;
12302             case OPC_MAQ_SA_W_QHLL:
12303                 check_dsp(ctx);
12304                 gen_helper_maq_sa_w_qhll(v1_t, v2_t, t0, tcg_env);
12305                 break;
12306             case OPC_MAQ_S_W_QHLR:
12307                 check_dsp(ctx);
12308                 gen_helper_maq_s_w_qhlr(v1_t, v2_t, t0, tcg_env);
12309                 break;
12310             case OPC_MAQ_SA_W_QHLR:
12311                 check_dsp(ctx);
12312                 gen_helper_maq_sa_w_qhlr(v1_t, v2_t, t0, tcg_env);
12313                 break;
12314             case OPC_MAQ_S_W_QHRL:
12315                 check_dsp(ctx);
12316                 gen_helper_maq_s_w_qhrl(v1_t, v2_t, t0, tcg_env);
12317                 break;
12318             case OPC_MAQ_SA_W_QHRL:
12319                 check_dsp(ctx);
12320                 gen_helper_maq_sa_w_qhrl(v1_t, v2_t, t0, tcg_env);
12321                 break;
12322             case OPC_MAQ_S_W_QHRR:
12323                 check_dsp(ctx);
12324                 gen_helper_maq_s_w_qhrr(v1_t, v2_t, t0, tcg_env);
12325                 break;
12326             case OPC_MAQ_SA_W_QHRR:
12327                 check_dsp(ctx);
12328                 gen_helper_maq_sa_w_qhrr(v1_t, v2_t, t0, tcg_env);
12329                 break;
12330             case OPC_MULSAQ_S_L_PW:
12331                 check_dsp(ctx);
12332                 gen_helper_mulsaq_s_l_pw(v1_t, v2_t, t0, tcg_env);
12333                 break;
12334             case OPC_MULSAQ_S_W_QH:
12335                 check_dsp(ctx);
12336                 gen_helper_mulsaq_s_w_qh(v1_t, v2_t, t0, tcg_env);
12337                 break;
12338             }
12339         }
12340         break;
12341 #endif
12342     case OPC_ADDU_QB_DSP:
12343         switch (op2) {
12344         case OPC_MULEU_S_PH_QBL:
12345             check_dsp(ctx);
12346             gen_helper_muleu_s_ph_qbl(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12347             break;
12348         case OPC_MULEU_S_PH_QBR:
12349             check_dsp(ctx);
12350             gen_helper_muleu_s_ph_qbr(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12351             break;
12352         case OPC_MULQ_RS_PH:
12353             check_dsp(ctx);
12354             gen_helper_mulq_rs_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12355             break;
12356         case OPC_MULEQ_S_W_PHL:
12357             check_dsp(ctx);
12358             gen_helper_muleq_s_w_phl(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12359             break;
12360         case OPC_MULEQ_S_W_PHR:
12361             check_dsp(ctx);
12362             gen_helper_muleq_s_w_phr(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12363             break;
12364         case OPC_MULQ_S_PH:
12365             check_dsp_r2(ctx);
12366             gen_helper_mulq_s_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12367             break;
12368         }
12369         break;
12370 #ifdef TARGET_MIPS64
12371     case OPC_ADDU_OB_DSP:
12372         switch (op2) {
12373         case OPC_MULEQ_S_PW_QHL:
12374             check_dsp(ctx);
12375             gen_helper_muleq_s_pw_qhl(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12376             break;
12377         case OPC_MULEQ_S_PW_QHR:
12378             check_dsp(ctx);
12379             gen_helper_muleq_s_pw_qhr(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12380             break;
12381         case OPC_MULEU_S_QH_OBL:
12382             check_dsp(ctx);
12383             gen_helper_muleu_s_qh_obl(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12384             break;
12385         case OPC_MULEU_S_QH_OBR:
12386             check_dsp(ctx);
12387             gen_helper_muleu_s_qh_obr(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12388             break;
12389         case OPC_MULQ_RS_QH:
12390             check_dsp(ctx);
12391             gen_helper_mulq_rs_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12392             break;
12393         }
12394         break;
12395 #endif
12396     }
12397 }
12398 
12399 static void gen_mipsdsp_bitinsn(DisasContext *ctx, uint32_t op1, uint32_t op2,
12400                                 int ret, int val)
12401 {
12402     int16_t imm;
12403     TCGv t0;
12404     TCGv val_t;
12405 
12406     if (ret == 0) {
12407         /* Treat as NOP. */
12408         return;
12409     }
12410 
12411     t0 = tcg_temp_new();
12412     val_t = tcg_temp_new();
12413     gen_load_gpr(val_t, val);
12414 
12415     switch (op1) {
12416     case OPC_ABSQ_S_PH_DSP:
12417         switch (op2) {
12418         case OPC_BITREV:
12419             check_dsp(ctx);
12420             gen_helper_bitrev(cpu_gpr[ret], val_t);
12421             break;
12422         case OPC_REPL_QB:
12423             check_dsp(ctx);
12424             {
12425                 target_long result;
12426                 imm = (ctx->opcode >> 16) & 0xFF;
12427                 result = (uint32_t)imm << 24 |
12428                          (uint32_t)imm << 16 |
12429                          (uint32_t)imm << 8  |
12430                          (uint32_t)imm;
12431                 result = (int32_t)result;
12432                 tcg_gen_movi_tl(cpu_gpr[ret], result);
12433             }
12434             break;
12435         case OPC_REPLV_QB:
12436             check_dsp(ctx);
12437             tcg_gen_ext8u_tl(cpu_gpr[ret], val_t);
12438             tcg_gen_shli_tl(t0, cpu_gpr[ret], 8);
12439             tcg_gen_or_tl(cpu_gpr[ret], cpu_gpr[ret], t0);
12440             tcg_gen_shli_tl(t0, cpu_gpr[ret], 16);
12441             tcg_gen_or_tl(cpu_gpr[ret], cpu_gpr[ret], t0);
12442             tcg_gen_ext32s_tl(cpu_gpr[ret], cpu_gpr[ret]);
12443             break;
12444         case OPC_REPL_PH:
12445             check_dsp(ctx);
12446             {
12447                 imm = (ctx->opcode >> 16) & 0x03FF;
12448                 imm = (int16_t)(imm << 6) >> 6;
12449                 tcg_gen_movi_tl(cpu_gpr[ret], \
12450                                 (target_long)((int32_t)imm << 16 | \
12451                                 (uint16_t)imm));
12452             }
12453             break;
12454         case OPC_REPLV_PH:
12455             check_dsp(ctx);
12456             tcg_gen_ext16u_tl(cpu_gpr[ret], val_t);
12457             tcg_gen_shli_tl(t0, cpu_gpr[ret], 16);
12458             tcg_gen_or_tl(cpu_gpr[ret], cpu_gpr[ret], t0);
12459             tcg_gen_ext32s_tl(cpu_gpr[ret], cpu_gpr[ret]);
12460             break;
12461         }
12462         break;
12463 #ifdef TARGET_MIPS64
12464     case OPC_ABSQ_S_QH_DSP:
12465         switch (op2) {
12466         case OPC_REPL_OB:
12467             check_dsp(ctx);
12468             {
12469                 target_long temp;
12470 
12471                 imm = (ctx->opcode >> 16) & 0xFF;
12472                 temp = ((uint64_t)imm << 8) | (uint64_t)imm;
12473                 temp = (temp << 16) | temp;
12474                 temp = (temp << 32) | temp;
12475                 tcg_gen_movi_tl(cpu_gpr[ret], temp);
12476                 break;
12477             }
12478         case OPC_REPL_PW:
12479             check_dsp(ctx);
12480             {
12481                 target_long temp;
12482 
12483                 imm = (ctx->opcode >> 16) & 0x03FF;
12484                 imm = (int16_t)(imm << 6) >> 6;
12485                 temp = ((target_long)imm << 32) \
12486                        | ((target_long)imm & 0xFFFFFFFF);
12487                 tcg_gen_movi_tl(cpu_gpr[ret], temp);
12488                 break;
12489             }
12490         case OPC_REPL_QH:
12491             check_dsp(ctx);
12492             {
12493                 target_long temp;
12494 
12495                 imm = (ctx->opcode >> 16) & 0x03FF;
12496                 imm = (int16_t)(imm << 6) >> 6;
12497 
12498                 temp = ((uint64_t)(uint16_t)imm << 48) |
12499                        ((uint64_t)(uint16_t)imm << 32) |
12500                        ((uint64_t)(uint16_t)imm << 16) |
12501                        (uint64_t)(uint16_t)imm;
12502                 tcg_gen_movi_tl(cpu_gpr[ret], temp);
12503                 break;
12504             }
12505         case OPC_REPLV_OB:
12506             check_dsp(ctx);
12507             tcg_gen_ext8u_tl(cpu_gpr[ret], val_t);
12508             tcg_gen_shli_tl(t0, cpu_gpr[ret], 8);
12509             tcg_gen_or_tl(cpu_gpr[ret], cpu_gpr[ret], t0);
12510             tcg_gen_shli_tl(t0, cpu_gpr[ret], 16);
12511             tcg_gen_or_tl(cpu_gpr[ret], cpu_gpr[ret], t0);
12512             tcg_gen_shli_tl(t0, cpu_gpr[ret], 32);
12513             tcg_gen_or_tl(cpu_gpr[ret], cpu_gpr[ret], t0);
12514             break;
12515         case OPC_REPLV_PW:
12516             check_dsp(ctx);
12517             tcg_gen_ext32u_i64(cpu_gpr[ret], val_t);
12518             tcg_gen_shli_tl(t0, cpu_gpr[ret], 32);
12519             tcg_gen_or_tl(cpu_gpr[ret], cpu_gpr[ret], t0);
12520             break;
12521         case OPC_REPLV_QH:
12522             check_dsp(ctx);
12523             tcg_gen_ext16u_tl(cpu_gpr[ret], val_t);
12524             tcg_gen_shli_tl(t0, cpu_gpr[ret], 16);
12525             tcg_gen_or_tl(cpu_gpr[ret], cpu_gpr[ret], t0);
12526             tcg_gen_shli_tl(t0, cpu_gpr[ret], 32);
12527             tcg_gen_or_tl(cpu_gpr[ret], cpu_gpr[ret], t0);
12528             break;
12529         }
12530         break;
12531 #endif
12532     }
12533 }
12534 
12535 static void gen_mipsdsp_add_cmp_pick(DisasContext *ctx,
12536                                      uint32_t op1, uint32_t op2,
12537                                      int ret, int v1, int v2, int check_ret)
12538 {
12539     TCGv t1;
12540     TCGv v1_t;
12541     TCGv v2_t;
12542 
12543     if ((ret == 0) && (check_ret == 1)) {
12544         /* Treat as NOP. */
12545         return;
12546     }
12547 
12548     t1 = tcg_temp_new();
12549     v1_t = tcg_temp_new();
12550     v2_t = tcg_temp_new();
12551 
12552     gen_load_gpr(v1_t, v1);
12553     gen_load_gpr(v2_t, v2);
12554 
12555     switch (op1) {
12556     case OPC_CMPU_EQ_QB_DSP:
12557         switch (op2) {
12558         case OPC_CMPU_EQ_QB:
12559             check_dsp(ctx);
12560             gen_helper_cmpu_eq_qb(v1_t, v2_t, tcg_env);
12561             break;
12562         case OPC_CMPU_LT_QB:
12563             check_dsp(ctx);
12564             gen_helper_cmpu_lt_qb(v1_t, v2_t, tcg_env);
12565             break;
12566         case OPC_CMPU_LE_QB:
12567             check_dsp(ctx);
12568             gen_helper_cmpu_le_qb(v1_t, v2_t, tcg_env);
12569             break;
12570         case OPC_CMPGU_EQ_QB:
12571             check_dsp(ctx);
12572             gen_helper_cmpgu_eq_qb(cpu_gpr[ret], v1_t, v2_t);
12573             break;
12574         case OPC_CMPGU_LT_QB:
12575             check_dsp(ctx);
12576             gen_helper_cmpgu_lt_qb(cpu_gpr[ret], v1_t, v2_t);
12577             break;
12578         case OPC_CMPGU_LE_QB:
12579             check_dsp(ctx);
12580             gen_helper_cmpgu_le_qb(cpu_gpr[ret], v1_t, v2_t);
12581             break;
12582         case OPC_CMPGDU_EQ_QB:
12583             check_dsp_r2(ctx);
12584             gen_helper_cmpgu_eq_qb(t1, v1_t, v2_t);
12585             tcg_gen_mov_tl(cpu_gpr[ret], t1);
12586             tcg_gen_andi_tl(cpu_dspctrl, cpu_dspctrl, 0xF0FFFFFF);
12587             tcg_gen_shli_tl(t1, t1, 24);
12588             tcg_gen_or_tl(cpu_dspctrl, cpu_dspctrl, t1);
12589             break;
12590         case OPC_CMPGDU_LT_QB:
12591             check_dsp_r2(ctx);
12592             gen_helper_cmpgu_lt_qb(t1, v1_t, v2_t);
12593             tcg_gen_mov_tl(cpu_gpr[ret], t1);
12594             tcg_gen_andi_tl(cpu_dspctrl, cpu_dspctrl, 0xF0FFFFFF);
12595             tcg_gen_shli_tl(t1, t1, 24);
12596             tcg_gen_or_tl(cpu_dspctrl, cpu_dspctrl, t1);
12597             break;
12598         case OPC_CMPGDU_LE_QB:
12599             check_dsp_r2(ctx);
12600             gen_helper_cmpgu_le_qb(t1, v1_t, v2_t);
12601             tcg_gen_mov_tl(cpu_gpr[ret], t1);
12602             tcg_gen_andi_tl(cpu_dspctrl, cpu_dspctrl, 0xF0FFFFFF);
12603             tcg_gen_shli_tl(t1, t1, 24);
12604             tcg_gen_or_tl(cpu_dspctrl, cpu_dspctrl, t1);
12605             break;
12606         case OPC_CMP_EQ_PH:
12607             check_dsp(ctx);
12608             gen_helper_cmp_eq_ph(v1_t, v2_t, tcg_env);
12609             break;
12610         case OPC_CMP_LT_PH:
12611             check_dsp(ctx);
12612             gen_helper_cmp_lt_ph(v1_t, v2_t, tcg_env);
12613             break;
12614         case OPC_CMP_LE_PH:
12615             check_dsp(ctx);
12616             gen_helper_cmp_le_ph(v1_t, v2_t, tcg_env);
12617             break;
12618         case OPC_PICK_QB:
12619             check_dsp(ctx);
12620             gen_helper_pick_qb(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12621             break;
12622         case OPC_PICK_PH:
12623             check_dsp(ctx);
12624             gen_helper_pick_ph(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12625             break;
12626         case OPC_PACKRL_PH:
12627             check_dsp(ctx);
12628             gen_helper_packrl_ph(cpu_gpr[ret], v1_t, v2_t);
12629             break;
12630         }
12631         break;
12632 #ifdef TARGET_MIPS64
12633     case OPC_CMPU_EQ_OB_DSP:
12634         switch (op2) {
12635         case OPC_CMP_EQ_PW:
12636             check_dsp(ctx);
12637             gen_helper_cmp_eq_pw(v1_t, v2_t, tcg_env);
12638             break;
12639         case OPC_CMP_LT_PW:
12640             check_dsp(ctx);
12641             gen_helper_cmp_lt_pw(v1_t, v2_t, tcg_env);
12642             break;
12643         case OPC_CMP_LE_PW:
12644             check_dsp(ctx);
12645             gen_helper_cmp_le_pw(v1_t, v2_t, tcg_env);
12646             break;
12647         case OPC_CMP_EQ_QH:
12648             check_dsp(ctx);
12649             gen_helper_cmp_eq_qh(v1_t, v2_t, tcg_env);
12650             break;
12651         case OPC_CMP_LT_QH:
12652             check_dsp(ctx);
12653             gen_helper_cmp_lt_qh(v1_t, v2_t, tcg_env);
12654             break;
12655         case OPC_CMP_LE_QH:
12656             check_dsp(ctx);
12657             gen_helper_cmp_le_qh(v1_t, v2_t, tcg_env);
12658             break;
12659         case OPC_CMPGDU_EQ_OB:
12660             check_dsp_r2(ctx);
12661             gen_helper_cmpgdu_eq_ob(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12662             break;
12663         case OPC_CMPGDU_LT_OB:
12664             check_dsp_r2(ctx);
12665             gen_helper_cmpgdu_lt_ob(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12666             break;
12667         case OPC_CMPGDU_LE_OB:
12668             check_dsp_r2(ctx);
12669             gen_helper_cmpgdu_le_ob(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12670             break;
12671         case OPC_CMPGU_EQ_OB:
12672             check_dsp(ctx);
12673             gen_helper_cmpgu_eq_ob(cpu_gpr[ret], v1_t, v2_t);
12674             break;
12675         case OPC_CMPGU_LT_OB:
12676             check_dsp(ctx);
12677             gen_helper_cmpgu_lt_ob(cpu_gpr[ret], v1_t, v2_t);
12678             break;
12679         case OPC_CMPGU_LE_OB:
12680             check_dsp(ctx);
12681             gen_helper_cmpgu_le_ob(cpu_gpr[ret], v1_t, v2_t);
12682             break;
12683         case OPC_CMPU_EQ_OB:
12684             check_dsp(ctx);
12685             gen_helper_cmpu_eq_ob(v1_t, v2_t, tcg_env);
12686             break;
12687         case OPC_CMPU_LT_OB:
12688             check_dsp(ctx);
12689             gen_helper_cmpu_lt_ob(v1_t, v2_t, tcg_env);
12690             break;
12691         case OPC_CMPU_LE_OB:
12692             check_dsp(ctx);
12693             gen_helper_cmpu_le_ob(v1_t, v2_t, tcg_env);
12694             break;
12695         case OPC_PACKRL_PW:
12696             check_dsp(ctx);
12697             gen_helper_packrl_pw(cpu_gpr[ret], v1_t, v2_t);
12698             break;
12699         case OPC_PICK_OB:
12700             check_dsp(ctx);
12701             gen_helper_pick_ob(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12702             break;
12703         case OPC_PICK_PW:
12704             check_dsp(ctx);
12705             gen_helper_pick_pw(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12706             break;
12707         case OPC_PICK_QH:
12708             check_dsp(ctx);
12709             gen_helper_pick_qh(cpu_gpr[ret], v1_t, v2_t, tcg_env);
12710             break;
12711         }
12712         break;
12713 #endif
12714     }
12715 }
12716 
12717 static void gen_mipsdsp_append(CPUMIPSState *env, DisasContext *ctx,
12718                                uint32_t op1, int rt, int rs, int sa)
12719 {
12720     TCGv t0;
12721 
12722     check_dsp_r2(ctx);
12723 
12724     if (rt == 0) {
12725         /* Treat as NOP. */
12726         return;
12727     }
12728 
12729     t0 = tcg_temp_new();
12730     gen_load_gpr(t0, rs);
12731 
12732     switch (op1) {
12733     case OPC_APPEND_DSP:
12734         switch (MASK_APPEND(ctx->opcode)) {
12735         case OPC_APPEND:
12736             if (sa != 0) {
12737                 tcg_gen_deposit_tl(cpu_gpr[rt], t0, cpu_gpr[rt], sa, 32 - sa);
12738             }
12739             tcg_gen_ext32s_tl(cpu_gpr[rt], cpu_gpr[rt]);
12740             break;
12741         case OPC_PREPEND:
12742             if (sa != 0) {
12743                 tcg_gen_ext32u_tl(cpu_gpr[rt], cpu_gpr[rt]);
12744                 tcg_gen_shri_tl(cpu_gpr[rt], cpu_gpr[rt], sa);
12745                 tcg_gen_shli_tl(t0, t0, 32 - sa);
12746                 tcg_gen_or_tl(cpu_gpr[rt], cpu_gpr[rt], t0);
12747             }
12748             tcg_gen_ext32s_tl(cpu_gpr[rt], cpu_gpr[rt]);
12749             break;
12750         case OPC_BALIGN:
12751             sa &= 3;
12752             if (sa != 0 && sa != 2) {
12753                 tcg_gen_shli_tl(cpu_gpr[rt], cpu_gpr[rt], 8 * sa);
12754                 tcg_gen_ext32u_tl(t0, t0);
12755                 tcg_gen_shri_tl(t0, t0, 8 * (4 - sa));
12756                 tcg_gen_or_tl(cpu_gpr[rt], cpu_gpr[rt], t0);
12757             }
12758             tcg_gen_ext32s_tl(cpu_gpr[rt], cpu_gpr[rt]);
12759             break;
12760         default:            /* Invalid */
12761             MIPS_INVAL("MASK APPEND");
12762             gen_reserved_instruction(ctx);
12763             break;
12764         }
12765         break;
12766 #ifdef TARGET_MIPS64
12767     case OPC_DAPPEND_DSP:
12768         switch (MASK_DAPPEND(ctx->opcode)) {
12769         case OPC_DAPPEND:
12770             if (sa != 0) {
12771                 tcg_gen_deposit_tl(cpu_gpr[rt], t0, cpu_gpr[rt], sa, 64 - sa);
12772             }
12773             break;
12774         case OPC_PREPENDD:
12775             tcg_gen_shri_tl(cpu_gpr[rt], cpu_gpr[rt], 0x20 | sa);
12776             tcg_gen_shli_tl(t0, t0, 64 - (0x20 | sa));
12777             tcg_gen_or_tl(cpu_gpr[rt], t0, t0);
12778             break;
12779         case OPC_PREPENDW:
12780             if (sa != 0) {
12781                 tcg_gen_shri_tl(cpu_gpr[rt], cpu_gpr[rt], sa);
12782                 tcg_gen_shli_tl(t0, t0, 64 - sa);
12783                 tcg_gen_or_tl(cpu_gpr[rt], cpu_gpr[rt], t0);
12784             }
12785             break;
12786         case OPC_DBALIGN:
12787             sa &= 7;
12788             if (sa != 0 && sa != 2 && sa != 4) {
12789                 tcg_gen_shli_tl(cpu_gpr[rt], cpu_gpr[rt], 8 * sa);
12790                 tcg_gen_shri_tl(t0, t0, 8 * (8 - sa));
12791                 tcg_gen_or_tl(cpu_gpr[rt], cpu_gpr[rt], t0);
12792             }
12793             break;
12794         default:            /* Invalid */
12795             MIPS_INVAL("MASK DAPPEND");
12796             gen_reserved_instruction(ctx);
12797             break;
12798         }
12799         break;
12800 #endif
12801     }
12802 }
12803 
12804 static void gen_mipsdsp_accinsn(DisasContext *ctx, uint32_t op1, uint32_t op2,
12805                                 int ret, int v1, int v2, int check_ret)
12806 
12807 {
12808     TCGv t0;
12809     TCGv t1;
12810     TCGv v1_t;
12811     int16_t imm;
12812 
12813     if ((ret == 0) && (check_ret == 1)) {
12814         /* Treat as NOP. */
12815         return;
12816     }
12817 
12818     t0 = tcg_temp_new();
12819     t1 = tcg_temp_new();
12820     v1_t = tcg_temp_new();
12821 
12822     gen_load_gpr(v1_t, v1);
12823 
12824     switch (op1) {
12825     case OPC_EXTR_W_DSP:
12826         check_dsp(ctx);
12827         switch (op2) {
12828         case OPC_EXTR_W:
12829             tcg_gen_movi_tl(t0, v2);
12830             tcg_gen_movi_tl(t1, v1);
12831             gen_helper_extr_w(cpu_gpr[ret], t0, t1, tcg_env);
12832             break;
12833         case OPC_EXTR_R_W:
12834             tcg_gen_movi_tl(t0, v2);
12835             tcg_gen_movi_tl(t1, v1);
12836             gen_helper_extr_r_w(cpu_gpr[ret], t0, t1, tcg_env);
12837             break;
12838         case OPC_EXTR_RS_W:
12839             tcg_gen_movi_tl(t0, v2);
12840             tcg_gen_movi_tl(t1, v1);
12841             gen_helper_extr_rs_w(cpu_gpr[ret], t0, t1, tcg_env);
12842             break;
12843         case OPC_EXTR_S_H:
12844             tcg_gen_movi_tl(t0, v2);
12845             tcg_gen_movi_tl(t1, v1);
12846             gen_helper_extr_s_h(cpu_gpr[ret], t0, t1, tcg_env);
12847             break;
12848         case OPC_EXTRV_S_H:
12849             tcg_gen_movi_tl(t0, v2);
12850             gen_helper_extr_s_h(cpu_gpr[ret], t0, v1_t, tcg_env);
12851             break;
12852         case OPC_EXTRV_W:
12853             tcg_gen_movi_tl(t0, v2);
12854             gen_helper_extr_w(cpu_gpr[ret], t0, v1_t, tcg_env);
12855             break;
12856         case OPC_EXTRV_R_W:
12857             tcg_gen_movi_tl(t0, v2);
12858             gen_helper_extr_r_w(cpu_gpr[ret], t0, v1_t, tcg_env);
12859             break;
12860         case OPC_EXTRV_RS_W:
12861             tcg_gen_movi_tl(t0, v2);
12862             gen_helper_extr_rs_w(cpu_gpr[ret], t0, v1_t, tcg_env);
12863             break;
12864         case OPC_EXTP:
12865             tcg_gen_movi_tl(t0, v2);
12866             tcg_gen_movi_tl(t1, v1);
12867             gen_helper_extp(cpu_gpr[ret], t0, t1, tcg_env);
12868             break;
12869         case OPC_EXTPV:
12870             tcg_gen_movi_tl(t0, v2);
12871             gen_helper_extp(cpu_gpr[ret], t0, v1_t, tcg_env);
12872             break;
12873         case OPC_EXTPDP:
12874             tcg_gen_movi_tl(t0, v2);
12875             tcg_gen_movi_tl(t1, v1);
12876             gen_helper_extpdp(cpu_gpr[ret], t0, t1, tcg_env);
12877             break;
12878         case OPC_EXTPDPV:
12879             tcg_gen_movi_tl(t0, v2);
12880             gen_helper_extpdp(cpu_gpr[ret], t0, v1_t, tcg_env);
12881             break;
12882         case OPC_SHILO:
12883             imm = (ctx->opcode >> 20) & 0x3F;
12884             tcg_gen_movi_tl(t0, ret);
12885             tcg_gen_movi_tl(t1, imm);
12886             gen_helper_shilo(t0, t1, tcg_env);
12887             break;
12888         case OPC_SHILOV:
12889             tcg_gen_movi_tl(t0, ret);
12890             gen_helper_shilo(t0, v1_t, tcg_env);
12891             break;
12892         case OPC_MTHLIP:
12893             tcg_gen_movi_tl(t0, ret);
12894             gen_helper_mthlip(t0, v1_t, tcg_env);
12895             break;
12896         case OPC_WRDSP:
12897             imm = (ctx->opcode >> 11) & 0x3FF;
12898             tcg_gen_movi_tl(t0, imm);
12899             gen_helper_wrdsp(v1_t, t0, tcg_env);
12900             break;
12901         case OPC_RDDSP:
12902             imm = (ctx->opcode >> 16) & 0x03FF;
12903             tcg_gen_movi_tl(t0, imm);
12904             gen_helper_rddsp(cpu_gpr[ret], t0, tcg_env);
12905             break;
12906         }
12907         break;
12908 #ifdef TARGET_MIPS64
12909     case OPC_DEXTR_W_DSP:
12910         check_dsp(ctx);
12911         switch (op2) {
12912         case OPC_DMTHLIP:
12913             tcg_gen_movi_tl(t0, ret);
12914             gen_helper_dmthlip(v1_t, t0, tcg_env);
12915             break;
12916         case OPC_DSHILO:
12917             {
12918                 int shift = (ctx->opcode >> 19) & 0x7F;
12919                 int ac = (ctx->opcode >> 11) & 0x03;
12920                 tcg_gen_movi_tl(t0, shift);
12921                 tcg_gen_movi_tl(t1, ac);
12922                 gen_helper_dshilo(t0, t1, tcg_env);
12923                 break;
12924             }
12925         case OPC_DSHILOV:
12926             {
12927                 int ac = (ctx->opcode >> 11) & 0x03;
12928                 tcg_gen_movi_tl(t0, ac);
12929                 gen_helper_dshilo(v1_t, t0, tcg_env);
12930                 break;
12931             }
12932         case OPC_DEXTP:
12933             tcg_gen_movi_tl(t0, v2);
12934             tcg_gen_movi_tl(t1, v1);
12935 
12936             gen_helper_dextp(cpu_gpr[ret], t0, t1, tcg_env);
12937             break;
12938         case OPC_DEXTPV:
12939             tcg_gen_movi_tl(t0, v2);
12940             gen_helper_dextp(cpu_gpr[ret], t0, v1_t, tcg_env);
12941             break;
12942         case OPC_DEXTPDP:
12943             tcg_gen_movi_tl(t0, v2);
12944             tcg_gen_movi_tl(t1, v1);
12945             gen_helper_dextpdp(cpu_gpr[ret], t0, t1, tcg_env);
12946             break;
12947         case OPC_DEXTPDPV:
12948             tcg_gen_movi_tl(t0, v2);
12949             gen_helper_dextpdp(cpu_gpr[ret], t0, v1_t, tcg_env);
12950             break;
12951         case OPC_DEXTR_L:
12952             tcg_gen_movi_tl(t0, v2);
12953             tcg_gen_movi_tl(t1, v1);
12954             gen_helper_dextr_l(cpu_gpr[ret], t0, t1, tcg_env);
12955             break;
12956         case OPC_DEXTR_R_L:
12957             tcg_gen_movi_tl(t0, v2);
12958             tcg_gen_movi_tl(t1, v1);
12959             gen_helper_dextr_r_l(cpu_gpr[ret], t0, t1, tcg_env);
12960             break;
12961         case OPC_DEXTR_RS_L:
12962             tcg_gen_movi_tl(t0, v2);
12963             tcg_gen_movi_tl(t1, v1);
12964             gen_helper_dextr_rs_l(cpu_gpr[ret], t0, t1, tcg_env);
12965             break;
12966         case OPC_DEXTR_W:
12967             tcg_gen_movi_tl(t0, v2);
12968             tcg_gen_movi_tl(t1, v1);
12969             gen_helper_dextr_w(cpu_gpr[ret], t0, t1, tcg_env);
12970             break;
12971         case OPC_DEXTR_R_W:
12972             tcg_gen_movi_tl(t0, v2);
12973             tcg_gen_movi_tl(t1, v1);
12974             gen_helper_dextr_r_w(cpu_gpr[ret], t0, t1, tcg_env);
12975             break;
12976         case OPC_DEXTR_RS_W:
12977             tcg_gen_movi_tl(t0, v2);
12978             tcg_gen_movi_tl(t1, v1);
12979             gen_helper_dextr_rs_w(cpu_gpr[ret], t0, t1, tcg_env);
12980             break;
12981         case OPC_DEXTR_S_H:
12982             tcg_gen_movi_tl(t0, v2);
12983             tcg_gen_movi_tl(t1, v1);
12984             gen_helper_dextr_s_h(cpu_gpr[ret], t0, t1, tcg_env);
12985             break;
12986         case OPC_DEXTRV_S_H:
12987             tcg_gen_movi_tl(t0, v2);
12988             gen_helper_dextr_s_h(cpu_gpr[ret], t0, v1_t, tcg_env);
12989             break;
12990         case OPC_DEXTRV_L:
12991             tcg_gen_movi_tl(t0, v2);
12992             gen_helper_dextr_l(cpu_gpr[ret], t0, v1_t, tcg_env);
12993             break;
12994         case OPC_DEXTRV_R_L:
12995             tcg_gen_movi_tl(t0, v2);
12996             gen_helper_dextr_r_l(cpu_gpr[ret], t0, v1_t, tcg_env);
12997             break;
12998         case OPC_DEXTRV_RS_L:
12999             tcg_gen_movi_tl(t0, v2);
13000             gen_helper_dextr_rs_l(cpu_gpr[ret], t0, v1_t, tcg_env);
13001             break;
13002         case OPC_DEXTRV_W:
13003             tcg_gen_movi_tl(t0, v2);
13004             gen_helper_dextr_w(cpu_gpr[ret], t0, v1_t, tcg_env);
13005             break;
13006         case OPC_DEXTRV_R_W:
13007             tcg_gen_movi_tl(t0, v2);
13008             gen_helper_dextr_r_w(cpu_gpr[ret], t0, v1_t, tcg_env);
13009             break;
13010         case OPC_DEXTRV_RS_W:
13011             tcg_gen_movi_tl(t0, v2);
13012             gen_helper_dextr_rs_w(cpu_gpr[ret], t0, v1_t, tcg_env);
13013             break;
13014         }
13015         break;
13016 #endif
13017     }
13018 }
13019 
13020 /* End MIPSDSP functions. */
13021 
13022 static void decode_opc_special_r6(CPUMIPSState *env, DisasContext *ctx)
13023 {
13024     int rs, rt, rd, sa;
13025     uint32_t op1, op2;
13026 
13027     rs = (ctx->opcode >> 21) & 0x1f;
13028     rt = (ctx->opcode >> 16) & 0x1f;
13029     rd = (ctx->opcode >> 11) & 0x1f;
13030     sa = (ctx->opcode >> 6) & 0x1f;
13031 
13032     op1 = MASK_SPECIAL(ctx->opcode);
13033     switch (op1) {
13034     case OPC_MULT:
13035     case OPC_MULTU:
13036     case OPC_DIV:
13037     case OPC_DIVU:
13038         op2 = MASK_R6_MULDIV(ctx->opcode);
13039         switch (op2) {
13040         case R6_OPC_MUL:
13041         case R6_OPC_MUH:
13042         case R6_OPC_MULU:
13043         case R6_OPC_MUHU:
13044         case R6_OPC_DIV:
13045         case R6_OPC_MOD:
13046         case R6_OPC_DIVU:
13047         case R6_OPC_MODU:
13048             gen_r6_muldiv(ctx, op2, rd, rs, rt);
13049             break;
13050         default:
13051             MIPS_INVAL("special_r6 muldiv");
13052             gen_reserved_instruction(ctx);
13053             break;
13054         }
13055         break;
13056     case OPC_SELEQZ:
13057     case OPC_SELNEZ:
13058         gen_cond_move(ctx, op1, rd, rs, rt);
13059         break;
13060     case R6_OPC_CLO:
13061     case R6_OPC_CLZ:
13062         if (rt == 0 && sa == 1) {
13063             /*
13064              * Major opcode and function field is shared with preR6 MFHI/MTHI.
13065              * We need additionally to check other fields.
13066              */
13067             gen_cl(ctx, op1, rd, rs);
13068         } else {
13069             gen_reserved_instruction(ctx);
13070         }
13071         break;
13072     case R6_OPC_SDBBP:
13073         if (is_uhi(ctx, extract32(ctx->opcode, 6, 20))) {
13074             ctx->base.is_jmp = DISAS_SEMIHOST;
13075         } else {
13076             if (ctx->hflags & MIPS_HFLAG_SBRI) {
13077                 gen_reserved_instruction(ctx);
13078             } else {
13079                 generate_exception_end(ctx, EXCP_DBp);
13080             }
13081         }
13082         break;
13083 #if defined(TARGET_MIPS64)
13084     case R6_OPC_DCLO:
13085     case R6_OPC_DCLZ:
13086         if (rt == 0 && sa == 1) {
13087             /*
13088              * Major opcode and function field is shared with preR6 MFHI/MTHI.
13089              * We need additionally to check other fields.
13090              */
13091             check_mips_64(ctx);
13092             gen_cl(ctx, op1, rd, rs);
13093         } else {
13094             gen_reserved_instruction(ctx);
13095         }
13096         break;
13097     case OPC_DMULT:
13098     case OPC_DMULTU:
13099     case OPC_DDIV:
13100     case OPC_DDIVU:
13101 
13102         op2 = MASK_R6_MULDIV(ctx->opcode);
13103         switch (op2) {
13104         case R6_OPC_DMUL:
13105         case R6_OPC_DMUH:
13106         case R6_OPC_DMULU:
13107         case R6_OPC_DMUHU:
13108         case R6_OPC_DDIV:
13109         case R6_OPC_DMOD:
13110         case R6_OPC_DDIVU:
13111         case R6_OPC_DMODU:
13112             check_mips_64(ctx);
13113             gen_r6_muldiv(ctx, op2, rd, rs, rt);
13114             break;
13115         default:
13116             MIPS_INVAL("special_r6 muldiv");
13117             gen_reserved_instruction(ctx);
13118             break;
13119         }
13120         break;
13121 #endif
13122     default:            /* Invalid */
13123         MIPS_INVAL("special_r6");
13124         gen_reserved_instruction(ctx);
13125         break;
13126     }
13127 }
13128 
13129 static void decode_opc_special_tx79(CPUMIPSState *env, DisasContext *ctx)
13130 {
13131     int rs = extract32(ctx->opcode, 21, 5);
13132     int rt = extract32(ctx->opcode, 16, 5);
13133     int rd = extract32(ctx->opcode, 11, 5);
13134     uint32_t op1 = MASK_SPECIAL(ctx->opcode);
13135 
13136     switch (op1) {
13137     case OPC_MOVN:         /* Conditional move */
13138     case OPC_MOVZ:
13139         gen_cond_move(ctx, op1, rd, rs, rt);
13140         break;
13141     case OPC_MFHI:          /* Move from HI/LO */
13142     case OPC_MFLO:
13143         gen_HILO(ctx, op1, 0, rd);
13144         break;
13145     case OPC_MTHI:
13146     case OPC_MTLO:          /* Move to HI/LO */
13147         gen_HILO(ctx, op1, 0, rs);
13148         break;
13149     case OPC_MULT:
13150     case OPC_MULTU:
13151         gen_mul_txx9(ctx, op1, rd, rs, rt);
13152         break;
13153     case OPC_DIV:
13154     case OPC_DIVU:
13155         gen_muldiv(ctx, op1, 0, rs, rt);
13156         break;
13157 #if defined(TARGET_MIPS64)
13158     case OPC_DMULT:
13159     case OPC_DMULTU:
13160     case OPC_DDIV:
13161     case OPC_DDIVU:
13162         check_insn_opc_user_only(ctx, INSN_R5900);
13163         gen_muldiv(ctx, op1, 0, rs, rt);
13164         break;
13165 #endif
13166     case OPC_JR:
13167         gen_compute_branch(ctx, op1, 4, rs, 0, 0, 4);
13168         break;
13169     default:            /* Invalid */
13170         MIPS_INVAL("special_tx79");
13171         gen_reserved_instruction(ctx);
13172         break;
13173     }
13174 }
13175 
13176 static void decode_opc_special_legacy(CPUMIPSState *env, DisasContext *ctx)
13177 {
13178     int rs, rt, rd;
13179     uint32_t op1;
13180 
13181     rs = (ctx->opcode >> 21) & 0x1f;
13182     rt = (ctx->opcode >> 16) & 0x1f;
13183     rd = (ctx->opcode >> 11) & 0x1f;
13184 
13185     op1 = MASK_SPECIAL(ctx->opcode);
13186     switch (op1) {
13187     case OPC_MOVN:         /* Conditional move */
13188     case OPC_MOVZ:
13189         check_insn(ctx, ISA_MIPS4 | ISA_MIPS_R1 |
13190                    INSN_LOONGSON2E | INSN_LOONGSON2F);
13191         gen_cond_move(ctx, op1, rd, rs, rt);
13192         break;
13193     case OPC_MFHI:          /* Move from HI/LO */
13194     case OPC_MFLO:
13195         gen_HILO(ctx, op1, rs & 3, rd);
13196         break;
13197     case OPC_MTHI:
13198     case OPC_MTLO:          /* Move to HI/LO */
13199         gen_HILO(ctx, op1, rd & 3, rs);
13200         break;
13201     case OPC_MOVCI:
13202         check_insn(ctx, ISA_MIPS4 | ISA_MIPS_R1);
13203         if (env->CP0_Config1 & (1 << CP0C1_FP)) {
13204             check_cp1_enabled(ctx);
13205             gen_movci(ctx, rd, rs, (ctx->opcode >> 18) & 0x7,
13206                       (ctx->opcode >> 16) & 1);
13207         } else {
13208             generate_exception_err(ctx, EXCP_CpU, 1);
13209         }
13210         break;
13211     case OPC_MULT:
13212     case OPC_MULTU:
13213         gen_muldiv(ctx, op1, rd & 3, rs, rt);
13214         break;
13215     case OPC_DIV:
13216     case OPC_DIVU:
13217         gen_muldiv(ctx, op1, 0, rs, rt);
13218         break;
13219 #if defined(TARGET_MIPS64)
13220     case OPC_DMULT:
13221     case OPC_DMULTU:
13222     case OPC_DDIV:
13223     case OPC_DDIVU:
13224         check_insn(ctx, ISA_MIPS3);
13225         check_mips_64(ctx);
13226         gen_muldiv(ctx, op1, 0, rs, rt);
13227         break;
13228 #endif
13229     case OPC_JR:
13230         gen_compute_branch(ctx, op1, 4, rs, 0, 0, 4);
13231         break;
13232     case OPC_SPIM:
13233 #ifdef MIPS_STRICT_STANDARD
13234         MIPS_INVAL("SPIM");
13235         gen_reserved_instruction(ctx);
13236 #else
13237         /* Implemented as RI exception for now. */
13238         MIPS_INVAL("spim (unofficial)");
13239         gen_reserved_instruction(ctx);
13240 #endif
13241         break;
13242     default:            /* Invalid */
13243         MIPS_INVAL("special_legacy");
13244         gen_reserved_instruction(ctx);
13245         break;
13246     }
13247 }
13248 
13249 static void decode_opc_special(CPUMIPSState *env, DisasContext *ctx)
13250 {
13251     int rs, rt, rd, sa;
13252     uint32_t op1;
13253 
13254     rs = (ctx->opcode >> 21) & 0x1f;
13255     rt = (ctx->opcode >> 16) & 0x1f;
13256     rd = (ctx->opcode >> 11) & 0x1f;
13257     sa = (ctx->opcode >> 6) & 0x1f;
13258 
13259     op1 = MASK_SPECIAL(ctx->opcode);
13260     switch (op1) {
13261     case OPC_SLL:          /* Shift with immediate */
13262         if (sa == 5 && rd == 0 &&
13263             rs == 0 && rt == 0) { /* PAUSE */
13264             if ((ctx->insn_flags & ISA_MIPS_R6) &&
13265                 (ctx->hflags & MIPS_HFLAG_BMASK)) {
13266                 gen_reserved_instruction(ctx);
13267                 break;
13268             }
13269         }
13270         /* Fallthrough */
13271     case OPC_SRA:
13272         gen_shift_imm(ctx, op1, rd, rt, sa);
13273         break;
13274     case OPC_SRL:
13275         switch ((ctx->opcode >> 21) & 0x1f) {
13276         case 1:
13277             /* rotr is decoded as srl on non-R2 CPUs */
13278             if (ctx->insn_flags & ISA_MIPS_R2) {
13279                 op1 = OPC_ROTR;
13280             }
13281             /* Fallthrough */
13282         case 0:
13283             gen_shift_imm(ctx, op1, rd, rt, sa);
13284             break;
13285         default:
13286             gen_reserved_instruction(ctx);
13287             break;
13288         }
13289         break;
13290     case OPC_ADD:
13291     case OPC_ADDU:
13292     case OPC_SUB:
13293     case OPC_SUBU:
13294         gen_arith(ctx, op1, rd, rs, rt);
13295         break;
13296     case OPC_SLLV:         /* Shifts */
13297     case OPC_SRAV:
13298         gen_shift(ctx, op1, rd, rs, rt);
13299         break;
13300     case OPC_SRLV:
13301         switch ((ctx->opcode >> 6) & 0x1f) {
13302         case 1:
13303             /* rotrv is decoded as srlv on non-R2 CPUs */
13304             if (ctx->insn_flags & ISA_MIPS_R2) {
13305                 op1 = OPC_ROTRV;
13306             }
13307             /* Fallthrough */
13308         case 0:
13309             gen_shift(ctx, op1, rd, rs, rt);
13310             break;
13311         default:
13312             gen_reserved_instruction(ctx);
13313             break;
13314         }
13315         break;
13316     case OPC_SLT:          /* Set on less than */
13317     case OPC_SLTU:
13318         gen_slt(ctx, op1, rd, rs, rt);
13319         break;
13320     case OPC_AND:          /* Logic*/
13321     case OPC_OR:
13322     case OPC_NOR:
13323     case OPC_XOR:
13324         gen_logic(ctx, op1, rd, rs, rt);
13325         break;
13326     case OPC_JALR:
13327         gen_compute_branch(ctx, op1, 4, rs, rd, sa, 4);
13328         break;
13329     case OPC_TGE: /* Traps */
13330     case OPC_TGEU:
13331     case OPC_TLT:
13332     case OPC_TLTU:
13333     case OPC_TEQ:
13334     case OPC_TNE:
13335         check_insn(ctx, ISA_MIPS2);
13336         gen_trap(ctx, op1, rs, rt, -1, extract32(ctx->opcode, 6, 10));
13337         break;
13338     case OPC_PMON:
13339         /* Pmon entry point, also R4010 selsl */
13340 #ifdef MIPS_STRICT_STANDARD
13341         MIPS_INVAL("PMON / selsl");
13342         gen_reserved_instruction(ctx);
13343 #else
13344         gen_helper_pmon(tcg_env, tcg_constant_i32(sa));
13345 #endif
13346         break;
13347     case OPC_SYSCALL:
13348         generate_exception_end(ctx, EXCP_SYSCALL);
13349         break;
13350     case OPC_BREAK:
13351         generate_exception_break(ctx, extract32(ctx->opcode, 6, 20));
13352         break;
13353     case OPC_SYNC:
13354         check_insn(ctx, ISA_MIPS2);
13355         gen_sync(extract32(ctx->opcode, 6, 5));
13356         break;
13357 
13358 #if defined(TARGET_MIPS64)
13359         /* MIPS64 specific opcodes */
13360     case OPC_DSLL:
13361     case OPC_DSRA:
13362     case OPC_DSLL32:
13363     case OPC_DSRA32:
13364         check_insn(ctx, ISA_MIPS3);
13365         check_mips_64(ctx);
13366         gen_shift_imm(ctx, op1, rd, rt, sa);
13367         break;
13368     case OPC_DSRL:
13369         switch ((ctx->opcode >> 21) & 0x1f) {
13370         case 1:
13371             /* drotr is decoded as dsrl on non-R2 CPUs */
13372             if (ctx->insn_flags & ISA_MIPS_R2) {
13373                 op1 = OPC_DROTR;
13374             }
13375             /* Fallthrough */
13376         case 0:
13377             check_insn(ctx, ISA_MIPS3);
13378             check_mips_64(ctx);
13379             gen_shift_imm(ctx, op1, rd, rt, sa);
13380             break;
13381         default:
13382             gen_reserved_instruction(ctx);
13383             break;
13384         }
13385         break;
13386     case OPC_DSRL32:
13387         switch ((ctx->opcode >> 21) & 0x1f) {
13388         case 1:
13389             /* drotr32 is decoded as dsrl32 on non-R2 CPUs */
13390             if (ctx->insn_flags & ISA_MIPS_R2) {
13391                 op1 = OPC_DROTR32;
13392             }
13393             /* Fallthrough */
13394         case 0:
13395             check_insn(ctx, ISA_MIPS3);
13396             check_mips_64(ctx);
13397             gen_shift_imm(ctx, op1, rd, rt, sa);
13398             break;
13399         default:
13400             gen_reserved_instruction(ctx);
13401             break;
13402         }
13403         break;
13404     case OPC_DADD:
13405     case OPC_DADDU:
13406     case OPC_DSUB:
13407     case OPC_DSUBU:
13408         check_insn(ctx, ISA_MIPS3);
13409         check_mips_64(ctx);
13410         gen_arith(ctx, op1, rd, rs, rt);
13411         break;
13412     case OPC_DSLLV:
13413     case OPC_DSRAV:
13414         check_insn(ctx, ISA_MIPS3);
13415         check_mips_64(ctx);
13416         gen_shift(ctx, op1, rd, rs, rt);
13417         break;
13418     case OPC_DSRLV:
13419         switch ((ctx->opcode >> 6) & 0x1f) {
13420         case 1:
13421             /* drotrv is decoded as dsrlv on non-R2 CPUs */
13422             if (ctx->insn_flags & ISA_MIPS_R2) {
13423                 op1 = OPC_DROTRV;
13424             }
13425             /* Fallthrough */
13426         case 0:
13427             check_insn(ctx, ISA_MIPS3);
13428             check_mips_64(ctx);
13429             gen_shift(ctx, op1, rd, rs, rt);
13430             break;
13431         default:
13432             gen_reserved_instruction(ctx);
13433             break;
13434         }
13435         break;
13436 #endif
13437     default:
13438         if (ctx->insn_flags & ISA_MIPS_R6) {
13439             decode_opc_special_r6(env, ctx);
13440         } else if (ctx->insn_flags & INSN_R5900) {
13441             decode_opc_special_tx79(env, ctx);
13442         } else {
13443             decode_opc_special_legacy(env, ctx);
13444         }
13445     }
13446 }
13447 
13448 
13449 static void decode_opc_special2_legacy(CPUMIPSState *env, DisasContext *ctx)
13450 {
13451     int rs, rt, rd;
13452     uint32_t op1;
13453 
13454     rs = (ctx->opcode >> 21) & 0x1f;
13455     rt = (ctx->opcode >> 16) & 0x1f;
13456     rd = (ctx->opcode >> 11) & 0x1f;
13457 
13458     op1 = MASK_SPECIAL2(ctx->opcode);
13459     switch (op1) {
13460     case OPC_MADD: /* Multiply and add/sub */
13461     case OPC_MADDU:
13462     case OPC_MSUB:
13463     case OPC_MSUBU:
13464         check_insn(ctx, ISA_MIPS_R1);
13465         gen_muldiv(ctx, op1, rd & 3, rs, rt);
13466         break;
13467     case OPC_MUL:
13468         gen_arith(ctx, op1, rd, rs, rt);
13469         break;
13470     case OPC_MULT_G_2F:
13471     case OPC_MULTU_G_2F:
13472         check_insn(ctx, INSN_LOONGSON2F | ASE_LEXT);
13473         gen_loongson_integer(ctx, op1, rd, rs, rt);
13474         break;
13475     case OPC_CLO:
13476     case OPC_CLZ:
13477         check_insn(ctx, ISA_MIPS_R1);
13478         gen_cl(ctx, op1, rd, rs);
13479         break;
13480     case OPC_SDBBP:
13481         if (is_uhi(ctx, extract32(ctx->opcode, 6, 20))) {
13482             ctx->base.is_jmp = DISAS_SEMIHOST;
13483         } else {
13484             /*
13485              * XXX: not clear which exception should be raised
13486              *      when in debug mode...
13487              */
13488             check_insn(ctx, ISA_MIPS_R1);
13489             generate_exception_end(ctx, EXCP_DBp);
13490         }
13491         break;
13492 #if defined(TARGET_MIPS64)
13493     case OPC_DCLO:
13494     case OPC_DCLZ:
13495         check_insn(ctx, ISA_MIPS_R1);
13496         check_mips_64(ctx);
13497         gen_cl(ctx, op1, rd, rs);
13498         break;
13499     case OPC_DMULT_G_2F:
13500     case OPC_DMULTU_G_2F:
13501         check_insn(ctx, INSN_LOONGSON2F | ASE_LEXT);
13502         gen_loongson_integer(ctx, op1, rd, rs, rt);
13503         break;
13504 #endif
13505     default:            /* Invalid */
13506         MIPS_INVAL("special2_legacy");
13507         gen_reserved_instruction(ctx);
13508         break;
13509     }
13510 }
13511 
13512 static void decode_opc_special3_r6(CPUMIPSState *env, DisasContext *ctx)
13513 {
13514     int rs, rt, rd, sa;
13515     uint32_t op1, op2;
13516     int16_t imm;
13517 
13518     rs = (ctx->opcode >> 21) & 0x1f;
13519     rt = (ctx->opcode >> 16) & 0x1f;
13520     rd = (ctx->opcode >> 11) & 0x1f;
13521     sa = (ctx->opcode >> 6) & 0x1f;
13522     imm = (int16_t)ctx->opcode >> 7;
13523 
13524     op1 = MASK_SPECIAL3(ctx->opcode);
13525     switch (op1) {
13526     case R6_OPC_PREF:
13527         if (rt >= 24) {
13528             /* hint codes 24-31 are reserved and signal RI */
13529             gen_reserved_instruction(ctx);
13530         }
13531         /* Treat as NOP. */
13532         break;
13533     case R6_OPC_CACHE:
13534         check_cp0_enabled(ctx);
13535         if (ctx->hflags & MIPS_HFLAG_ITC_CACHE) {
13536             gen_cache_operation(ctx, rt, rs, imm);
13537         }
13538         break;
13539     case R6_OPC_SC:
13540         gen_st_cond(ctx, rt, rs, imm, mo_endian(ctx) | MO_SL, false);
13541         break;
13542     case R6_OPC_LL:
13543         gen_ld(ctx, op1, rt, rs, imm);
13544         break;
13545     case OPC_BSHFL:
13546         {
13547             if (rd == 0) {
13548                 /* Treat as NOP. */
13549                 break;
13550             }
13551             op2 = MASK_BSHFL(ctx->opcode);
13552             switch (op2) {
13553             case OPC_ALIGN:
13554             case OPC_ALIGN_1:
13555             case OPC_ALIGN_2:
13556             case OPC_ALIGN_3:
13557                 gen_align(ctx, 32, rd, rs, rt, sa & 3);
13558                 break;
13559             case OPC_BITSWAP:
13560                 gen_bitswap(ctx, op2, rd, rt);
13561                 break;
13562             }
13563         }
13564         break;
13565 #ifndef CONFIG_USER_ONLY
13566     case OPC_GINV:
13567         if (unlikely(ctx->gi <= 1)) {
13568             gen_reserved_instruction(ctx);
13569         }
13570         check_cp0_enabled(ctx);
13571         switch ((ctx->opcode >> 6) & 3) {
13572         case 0:    /* GINVI */
13573             /* Treat as NOP. */
13574             break;
13575         case 2:    /* GINVT */
13576             gen_helper_0e1i(ginvt, cpu_gpr[rs], extract32(ctx->opcode, 8, 2));
13577             break;
13578         default:
13579             gen_reserved_instruction(ctx);
13580             break;
13581         }
13582         break;
13583 #endif
13584 #if defined(TARGET_MIPS64)
13585     case R6_OPC_SCD:
13586         gen_st_cond(ctx, rt, rs, imm, mo_endian(ctx) | MO_UQ, false);
13587         break;
13588     case R6_OPC_LLD:
13589         gen_ld(ctx, op1, rt, rs, imm);
13590         break;
13591     case OPC_DBSHFL:
13592         check_mips_64(ctx);
13593         {
13594             if (rd == 0) {
13595                 /* Treat as NOP. */
13596                 break;
13597             }
13598             op2 = MASK_DBSHFL(ctx->opcode);
13599             switch (op2) {
13600             case OPC_DALIGN:
13601             case OPC_DALIGN_1:
13602             case OPC_DALIGN_2:
13603             case OPC_DALIGN_3:
13604             case OPC_DALIGN_4:
13605             case OPC_DALIGN_5:
13606             case OPC_DALIGN_6:
13607             case OPC_DALIGN_7:
13608                 gen_align(ctx, 64, rd, rs, rt, sa & 7);
13609                 break;
13610             case OPC_DBITSWAP:
13611                 gen_bitswap(ctx, op2, rd, rt);
13612                 break;
13613             }
13614 
13615         }
13616         break;
13617 #endif
13618     default:            /* Invalid */
13619         MIPS_INVAL("special3_r6");
13620         gen_reserved_instruction(ctx);
13621         break;
13622     }
13623 }
13624 
13625 static void decode_opc_special3_legacy(CPUMIPSState *env, DisasContext *ctx)
13626 {
13627     int rs, rt, rd;
13628     uint32_t op1, op2;
13629 
13630     rs = (ctx->opcode >> 21) & 0x1f;
13631     rt = (ctx->opcode >> 16) & 0x1f;
13632     rd = (ctx->opcode >> 11) & 0x1f;
13633 
13634     op1 = MASK_SPECIAL3(ctx->opcode);
13635     switch (op1) {
13636     case OPC_MULT_G_2E:
13637     case OPC_MULTU_G_2E:
13638         /*
13639          * OPC_MULT_G_2E, OPC_ADDUH_QB_DSP, OPC_MUL_PH_DSP have
13640          * the same mask and op1.
13641          */
13642         if ((ctx->insn_flags & ASE_DSP_R2) && (op1 == OPC_MUL_PH_DSP)) {
13643             op2 = MASK_ADDUH_QB(ctx->opcode);
13644             switch (op2) {
13645             case OPC_ADDUH_QB:
13646             case OPC_ADDUH_R_QB:
13647             case OPC_ADDQH_PH:
13648             case OPC_ADDQH_R_PH:
13649             case OPC_ADDQH_W:
13650             case OPC_ADDQH_R_W:
13651             case OPC_SUBUH_QB:
13652             case OPC_SUBUH_R_QB:
13653             case OPC_SUBQH_PH:
13654             case OPC_SUBQH_R_PH:
13655             case OPC_SUBQH_W:
13656             case OPC_SUBQH_R_W:
13657                 gen_mipsdsp_arith(ctx, op1, op2, rd, rs, rt);
13658                 break;
13659             case OPC_MUL_PH:
13660             case OPC_MUL_S_PH:
13661             case OPC_MULQ_S_W:
13662             case OPC_MULQ_RS_W:
13663                 gen_mipsdsp_multiply(ctx, op1, op2, rd, rs, rt, 1);
13664                 break;
13665             default:
13666                 MIPS_INVAL("MASK ADDUH.QB");
13667                 gen_reserved_instruction(ctx);
13668                 break;
13669             }
13670         } else if (ctx->insn_flags & INSN_LOONGSON2E) {
13671             gen_loongson_integer(ctx, op1, rd, rs, rt);
13672         } else {
13673             gen_reserved_instruction(ctx);
13674         }
13675         break;
13676     case OPC_LX_DSP:
13677         op2 = MASK_LX(ctx->opcode);
13678         switch (op2) {
13679 #if defined(TARGET_MIPS64)
13680         case OPC_LDX:
13681 #endif
13682         case OPC_LBUX:
13683         case OPC_LHX:
13684         case OPC_LWX:
13685             gen_mips_lx(ctx, op2, rd, rs, rt);
13686             break;
13687         default:            /* Invalid */
13688             MIPS_INVAL("MASK LX");
13689             gen_reserved_instruction(ctx);
13690             break;
13691         }
13692         break;
13693     case OPC_ABSQ_S_PH_DSP:
13694         op2 = MASK_ABSQ_S_PH(ctx->opcode);
13695         switch (op2) {
13696         case OPC_ABSQ_S_QB:
13697         case OPC_ABSQ_S_PH:
13698         case OPC_ABSQ_S_W:
13699         case OPC_PRECEQ_W_PHL:
13700         case OPC_PRECEQ_W_PHR:
13701         case OPC_PRECEQU_PH_QBL:
13702         case OPC_PRECEQU_PH_QBR:
13703         case OPC_PRECEQU_PH_QBLA:
13704         case OPC_PRECEQU_PH_QBRA:
13705         case OPC_PRECEU_PH_QBL:
13706         case OPC_PRECEU_PH_QBR:
13707         case OPC_PRECEU_PH_QBLA:
13708         case OPC_PRECEU_PH_QBRA:
13709             gen_mipsdsp_arith(ctx, op1, op2, rd, rs, rt);
13710             break;
13711         case OPC_BITREV:
13712         case OPC_REPL_QB:
13713         case OPC_REPLV_QB:
13714         case OPC_REPL_PH:
13715         case OPC_REPLV_PH:
13716             gen_mipsdsp_bitinsn(ctx, op1, op2, rd, rt);
13717             break;
13718         default:
13719             MIPS_INVAL("MASK ABSQ_S.PH");
13720             gen_reserved_instruction(ctx);
13721             break;
13722         }
13723         break;
13724     case OPC_ADDU_QB_DSP:
13725         op2 = MASK_ADDU_QB(ctx->opcode);
13726         switch (op2) {
13727         case OPC_ADDQ_PH:
13728         case OPC_ADDQ_S_PH:
13729         case OPC_ADDQ_S_W:
13730         case OPC_ADDU_QB:
13731         case OPC_ADDU_S_QB:
13732         case OPC_ADDU_PH:
13733         case OPC_ADDU_S_PH:
13734         case OPC_SUBQ_PH:
13735         case OPC_SUBQ_S_PH:
13736         case OPC_SUBQ_S_W:
13737         case OPC_SUBU_QB:
13738         case OPC_SUBU_S_QB:
13739         case OPC_SUBU_PH:
13740         case OPC_SUBU_S_PH:
13741         case OPC_ADDSC:
13742         case OPC_ADDWC:
13743         case OPC_MODSUB:
13744         case OPC_RADDU_W_QB:
13745             gen_mipsdsp_arith(ctx, op1, op2, rd, rs, rt);
13746             break;
13747         case OPC_MULEU_S_PH_QBL:
13748         case OPC_MULEU_S_PH_QBR:
13749         case OPC_MULQ_RS_PH:
13750         case OPC_MULEQ_S_W_PHL:
13751         case OPC_MULEQ_S_W_PHR:
13752         case OPC_MULQ_S_PH:
13753             gen_mipsdsp_multiply(ctx, op1, op2, rd, rs, rt, 1);
13754             break;
13755         default:            /* Invalid */
13756             MIPS_INVAL("MASK ADDU.QB");
13757             gen_reserved_instruction(ctx);
13758             break;
13759 
13760         }
13761         break;
13762     case OPC_CMPU_EQ_QB_DSP:
13763         op2 = MASK_CMPU_EQ_QB(ctx->opcode);
13764         switch (op2) {
13765         case OPC_PRECR_SRA_PH_W:
13766         case OPC_PRECR_SRA_R_PH_W:
13767             gen_mipsdsp_arith(ctx, op1, op2, rt, rs, rd);
13768             break;
13769         case OPC_PRECR_QB_PH:
13770         case OPC_PRECRQ_QB_PH:
13771         case OPC_PRECRQ_PH_W:
13772         case OPC_PRECRQ_RS_PH_W:
13773         case OPC_PRECRQU_S_QB_PH:
13774             gen_mipsdsp_arith(ctx, op1, op2, rd, rs, rt);
13775             break;
13776         case OPC_CMPU_EQ_QB:
13777         case OPC_CMPU_LT_QB:
13778         case OPC_CMPU_LE_QB:
13779         case OPC_CMP_EQ_PH:
13780         case OPC_CMP_LT_PH:
13781         case OPC_CMP_LE_PH:
13782             gen_mipsdsp_add_cmp_pick(ctx, op1, op2, rd, rs, rt, 0);
13783             break;
13784         case OPC_CMPGU_EQ_QB:
13785         case OPC_CMPGU_LT_QB:
13786         case OPC_CMPGU_LE_QB:
13787         case OPC_CMPGDU_EQ_QB:
13788         case OPC_CMPGDU_LT_QB:
13789         case OPC_CMPGDU_LE_QB:
13790         case OPC_PICK_QB:
13791         case OPC_PICK_PH:
13792         case OPC_PACKRL_PH:
13793             gen_mipsdsp_add_cmp_pick(ctx, op1, op2, rd, rs, rt, 1);
13794             break;
13795         default:            /* Invalid */
13796             MIPS_INVAL("MASK CMPU.EQ.QB");
13797             gen_reserved_instruction(ctx);
13798             break;
13799         }
13800         break;
13801     case OPC_SHLL_QB_DSP:
13802         gen_mipsdsp_shift(ctx, op1, rd, rs, rt);
13803         break;
13804     case OPC_DPA_W_PH_DSP:
13805         op2 = MASK_DPA_W_PH(ctx->opcode);
13806         switch (op2) {
13807         case OPC_DPAU_H_QBL:
13808         case OPC_DPAU_H_QBR:
13809         case OPC_DPSU_H_QBL:
13810         case OPC_DPSU_H_QBR:
13811         case OPC_DPA_W_PH:
13812         case OPC_DPAX_W_PH:
13813         case OPC_DPAQ_S_W_PH:
13814         case OPC_DPAQX_S_W_PH:
13815         case OPC_DPAQX_SA_W_PH:
13816         case OPC_DPS_W_PH:
13817         case OPC_DPSX_W_PH:
13818         case OPC_DPSQ_S_W_PH:
13819         case OPC_DPSQX_S_W_PH:
13820         case OPC_DPSQX_SA_W_PH:
13821         case OPC_MULSAQ_S_W_PH:
13822         case OPC_DPAQ_SA_L_W:
13823         case OPC_DPSQ_SA_L_W:
13824         case OPC_MAQ_S_W_PHL:
13825         case OPC_MAQ_S_W_PHR:
13826         case OPC_MAQ_SA_W_PHL:
13827         case OPC_MAQ_SA_W_PHR:
13828         case OPC_MULSA_W_PH:
13829             gen_mipsdsp_multiply(ctx, op1, op2, rd, rs, rt, 0);
13830             break;
13831         default:            /* Invalid */
13832             MIPS_INVAL("MASK DPAW.PH");
13833             gen_reserved_instruction(ctx);
13834             break;
13835         }
13836         break;
13837     case OPC_INSV_DSP:
13838         op2 = MASK_INSV(ctx->opcode);
13839         switch (op2) {
13840         case OPC_INSV:
13841             check_dsp(ctx);
13842             {
13843                 TCGv t0, t1;
13844 
13845                 if (rt == 0) {
13846                     break;
13847                 }
13848 
13849                 t0 = tcg_temp_new();
13850                 t1 = tcg_temp_new();
13851 
13852                 gen_load_gpr(t0, rt);
13853                 gen_load_gpr(t1, rs);
13854 
13855                 gen_helper_insv(cpu_gpr[rt], tcg_env, t1, t0);
13856                 break;
13857             }
13858         default:            /* Invalid */
13859             MIPS_INVAL("MASK INSV");
13860             gen_reserved_instruction(ctx);
13861             break;
13862         }
13863         break;
13864     case OPC_APPEND_DSP:
13865         gen_mipsdsp_append(env, ctx, op1, rt, rs, rd);
13866         break;
13867     case OPC_EXTR_W_DSP:
13868         op2 = MASK_EXTR_W(ctx->opcode);
13869         switch (op2) {
13870         case OPC_EXTR_W:
13871         case OPC_EXTR_R_W:
13872         case OPC_EXTR_RS_W:
13873         case OPC_EXTR_S_H:
13874         case OPC_EXTRV_S_H:
13875         case OPC_EXTRV_W:
13876         case OPC_EXTRV_R_W:
13877         case OPC_EXTRV_RS_W:
13878         case OPC_EXTP:
13879         case OPC_EXTPV:
13880         case OPC_EXTPDP:
13881         case OPC_EXTPDPV:
13882             gen_mipsdsp_accinsn(ctx, op1, op2, rt, rs, rd, 1);
13883             break;
13884         case OPC_RDDSP:
13885             gen_mipsdsp_accinsn(ctx, op1, op2, rd, rs, rt, 1);
13886             break;
13887         case OPC_SHILO:
13888         case OPC_SHILOV:
13889         case OPC_MTHLIP:
13890         case OPC_WRDSP:
13891             gen_mipsdsp_accinsn(ctx, op1, op2, rd, rs, rt, 0);
13892             break;
13893         default:            /* Invalid */
13894             MIPS_INVAL("MASK EXTR.W");
13895             gen_reserved_instruction(ctx);
13896             break;
13897         }
13898         break;
13899 #if defined(TARGET_MIPS64)
13900     case OPC_DMULT_G_2E:
13901     case OPC_DMULTU_G_2E:
13902         check_insn(ctx, INSN_LOONGSON2E);
13903         gen_loongson_integer(ctx, op1, rd, rs, rt);
13904         break;
13905     case OPC_ABSQ_S_QH_DSP:
13906         op2 = MASK_ABSQ_S_QH(ctx->opcode);
13907         switch (op2) {
13908         case OPC_PRECEQ_L_PWL:
13909         case OPC_PRECEQ_L_PWR:
13910         case OPC_PRECEQ_PW_QHL:
13911         case OPC_PRECEQ_PW_QHR:
13912         case OPC_PRECEQ_PW_QHLA:
13913         case OPC_PRECEQ_PW_QHRA:
13914         case OPC_PRECEQU_QH_OBL:
13915         case OPC_PRECEQU_QH_OBR:
13916         case OPC_PRECEQU_QH_OBLA:
13917         case OPC_PRECEQU_QH_OBRA:
13918         case OPC_PRECEU_QH_OBL:
13919         case OPC_PRECEU_QH_OBR:
13920         case OPC_PRECEU_QH_OBLA:
13921         case OPC_PRECEU_QH_OBRA:
13922         case OPC_ABSQ_S_OB:
13923         case OPC_ABSQ_S_PW:
13924         case OPC_ABSQ_S_QH:
13925             gen_mipsdsp_arith(ctx, op1, op2, rd, rs, rt);
13926             break;
13927         case OPC_REPL_OB:
13928         case OPC_REPL_PW:
13929         case OPC_REPL_QH:
13930         case OPC_REPLV_OB:
13931         case OPC_REPLV_PW:
13932         case OPC_REPLV_QH:
13933             gen_mipsdsp_bitinsn(ctx, op1, op2, rd, rt);
13934             break;
13935         default:            /* Invalid */
13936             MIPS_INVAL("MASK ABSQ_S.QH");
13937             gen_reserved_instruction(ctx);
13938             break;
13939         }
13940         break;
13941     case OPC_ADDU_OB_DSP:
13942         op2 = MASK_ADDU_OB(ctx->opcode);
13943         switch (op2) {
13944         case OPC_RADDU_L_OB:
13945         case OPC_SUBQ_PW:
13946         case OPC_SUBQ_S_PW:
13947         case OPC_SUBQ_QH:
13948         case OPC_SUBQ_S_QH:
13949         case OPC_SUBU_OB:
13950         case OPC_SUBU_S_OB:
13951         case OPC_SUBU_QH:
13952         case OPC_SUBU_S_QH:
13953         case OPC_SUBUH_OB:
13954         case OPC_SUBUH_R_OB:
13955         case OPC_ADDQ_PW:
13956         case OPC_ADDQ_S_PW:
13957         case OPC_ADDQ_QH:
13958         case OPC_ADDQ_S_QH:
13959         case OPC_ADDU_OB:
13960         case OPC_ADDU_S_OB:
13961         case OPC_ADDU_QH:
13962         case OPC_ADDU_S_QH:
13963         case OPC_ADDUH_OB:
13964         case OPC_ADDUH_R_OB:
13965             gen_mipsdsp_arith(ctx, op1, op2, rd, rs, rt);
13966             break;
13967         case OPC_MULEQ_S_PW_QHL:
13968         case OPC_MULEQ_S_PW_QHR:
13969         case OPC_MULEU_S_QH_OBL:
13970         case OPC_MULEU_S_QH_OBR:
13971         case OPC_MULQ_RS_QH:
13972             gen_mipsdsp_multiply(ctx, op1, op2, rd, rs, rt, 1);
13973             break;
13974         default:            /* Invalid */
13975             MIPS_INVAL("MASK ADDU.OB");
13976             gen_reserved_instruction(ctx);
13977             break;
13978         }
13979         break;
13980     case OPC_CMPU_EQ_OB_DSP:
13981         op2 = MASK_CMPU_EQ_OB(ctx->opcode);
13982         switch (op2) {
13983         case OPC_PRECR_SRA_QH_PW:
13984         case OPC_PRECR_SRA_R_QH_PW:
13985             /* Return value is rt. */
13986             gen_mipsdsp_arith(ctx, op1, op2, rt, rs, rd);
13987             break;
13988         case OPC_PRECR_OB_QH:
13989         case OPC_PRECRQ_OB_QH:
13990         case OPC_PRECRQ_PW_L:
13991         case OPC_PRECRQ_QH_PW:
13992         case OPC_PRECRQ_RS_QH_PW:
13993         case OPC_PRECRQU_S_OB_QH:
13994             gen_mipsdsp_arith(ctx, op1, op2, rd, rs, rt);
13995             break;
13996         case OPC_CMPU_EQ_OB:
13997         case OPC_CMPU_LT_OB:
13998         case OPC_CMPU_LE_OB:
13999         case OPC_CMP_EQ_QH:
14000         case OPC_CMP_LT_QH:
14001         case OPC_CMP_LE_QH:
14002         case OPC_CMP_EQ_PW:
14003         case OPC_CMP_LT_PW:
14004         case OPC_CMP_LE_PW:
14005             gen_mipsdsp_add_cmp_pick(ctx, op1, op2, rd, rs, rt, 0);
14006             break;
14007         case OPC_CMPGDU_EQ_OB:
14008         case OPC_CMPGDU_LT_OB:
14009         case OPC_CMPGDU_LE_OB:
14010         case OPC_CMPGU_EQ_OB:
14011         case OPC_CMPGU_LT_OB:
14012         case OPC_CMPGU_LE_OB:
14013         case OPC_PACKRL_PW:
14014         case OPC_PICK_OB:
14015         case OPC_PICK_PW:
14016         case OPC_PICK_QH:
14017             gen_mipsdsp_add_cmp_pick(ctx, op1, op2, rd, rs, rt, 1);
14018             break;
14019         default:            /* Invalid */
14020             MIPS_INVAL("MASK CMPU_EQ.OB");
14021             gen_reserved_instruction(ctx);
14022             break;
14023         }
14024         break;
14025     case OPC_DAPPEND_DSP:
14026         gen_mipsdsp_append(env, ctx, op1, rt, rs, rd);
14027         break;
14028     case OPC_DEXTR_W_DSP:
14029         op2 = MASK_DEXTR_W(ctx->opcode);
14030         switch (op2) {
14031         case OPC_DEXTP:
14032         case OPC_DEXTPDP:
14033         case OPC_DEXTPDPV:
14034         case OPC_DEXTPV:
14035         case OPC_DEXTR_L:
14036         case OPC_DEXTR_R_L:
14037         case OPC_DEXTR_RS_L:
14038         case OPC_DEXTR_W:
14039         case OPC_DEXTR_R_W:
14040         case OPC_DEXTR_RS_W:
14041         case OPC_DEXTR_S_H:
14042         case OPC_DEXTRV_L:
14043         case OPC_DEXTRV_R_L:
14044         case OPC_DEXTRV_RS_L:
14045         case OPC_DEXTRV_S_H:
14046         case OPC_DEXTRV_W:
14047         case OPC_DEXTRV_R_W:
14048         case OPC_DEXTRV_RS_W:
14049             gen_mipsdsp_accinsn(ctx, op1, op2, rt, rs, rd, 1);
14050             break;
14051         case OPC_DMTHLIP:
14052         case OPC_DSHILO:
14053         case OPC_DSHILOV:
14054             gen_mipsdsp_accinsn(ctx, op1, op2, rd, rs, rt, 0);
14055             break;
14056         default:            /* Invalid */
14057             MIPS_INVAL("MASK EXTR.W");
14058             gen_reserved_instruction(ctx);
14059             break;
14060         }
14061         break;
14062     case OPC_DPAQ_W_QH_DSP:
14063         op2 = MASK_DPAQ_W_QH(ctx->opcode);
14064         switch (op2) {
14065         case OPC_DPAU_H_OBL:
14066         case OPC_DPAU_H_OBR:
14067         case OPC_DPSU_H_OBL:
14068         case OPC_DPSU_H_OBR:
14069         case OPC_DPA_W_QH:
14070         case OPC_DPAQ_S_W_QH:
14071         case OPC_DPS_W_QH:
14072         case OPC_DPSQ_S_W_QH:
14073         case OPC_MULSAQ_S_W_QH:
14074         case OPC_DPAQ_SA_L_PW:
14075         case OPC_DPSQ_SA_L_PW:
14076         case OPC_MULSAQ_S_L_PW:
14077             gen_mipsdsp_multiply(ctx, op1, op2, rd, rs, rt, 0);
14078             break;
14079         case OPC_MAQ_S_W_QHLL:
14080         case OPC_MAQ_S_W_QHLR:
14081         case OPC_MAQ_S_W_QHRL:
14082         case OPC_MAQ_S_W_QHRR:
14083         case OPC_MAQ_SA_W_QHLL:
14084         case OPC_MAQ_SA_W_QHLR:
14085         case OPC_MAQ_SA_W_QHRL:
14086         case OPC_MAQ_SA_W_QHRR:
14087         case OPC_MAQ_S_L_PWL:
14088         case OPC_MAQ_S_L_PWR:
14089         case OPC_DMADD:
14090         case OPC_DMADDU:
14091         case OPC_DMSUB:
14092         case OPC_DMSUBU:
14093             gen_mipsdsp_multiply(ctx, op1, op2, rd, rs, rt, 0);
14094             break;
14095         default:            /* Invalid */
14096             MIPS_INVAL("MASK DPAQ.W.QH");
14097             gen_reserved_instruction(ctx);
14098             break;
14099         }
14100         break;
14101     case OPC_DINSV_DSP:
14102         op2 = MASK_INSV(ctx->opcode);
14103         switch (op2) {
14104         case OPC_DINSV:
14105         {
14106             TCGv t0, t1;
14107 
14108             check_dsp(ctx);
14109 
14110             if (rt == 0) {
14111                 break;
14112             }
14113 
14114             t0 = tcg_temp_new();
14115             t1 = tcg_temp_new();
14116 
14117             gen_load_gpr(t0, rt);
14118             gen_load_gpr(t1, rs);
14119 
14120             gen_helper_dinsv(cpu_gpr[rt], tcg_env, t1, t0);
14121             break;
14122         }
14123         default:            /* Invalid */
14124             MIPS_INVAL("MASK DINSV");
14125             gen_reserved_instruction(ctx);
14126             break;
14127         }
14128         break;
14129     case OPC_SHLL_OB_DSP:
14130         gen_mipsdsp_shift(ctx, op1, rd, rs, rt);
14131         break;
14132 #endif
14133     default:            /* Invalid */
14134         MIPS_INVAL("special3_legacy");
14135         gen_reserved_instruction(ctx);
14136         break;
14137     }
14138 }
14139 
14140 
14141 #if defined(TARGET_MIPS64)
14142 
14143 static void decode_mmi(CPUMIPSState *env, DisasContext *ctx)
14144 {
14145     uint32_t opc = MASK_MMI(ctx->opcode);
14146     int rs = extract32(ctx->opcode, 21, 5);
14147     int rt = extract32(ctx->opcode, 16, 5);
14148     int rd = extract32(ctx->opcode, 11, 5);
14149 
14150     switch (opc) {
14151     case MMI_OPC_MULT1:
14152     case MMI_OPC_MULTU1:
14153     case MMI_OPC_MADD:
14154     case MMI_OPC_MADDU:
14155     case MMI_OPC_MADD1:
14156     case MMI_OPC_MADDU1:
14157         gen_mul_txx9(ctx, opc, rd, rs, rt);
14158         break;
14159     case MMI_OPC_DIV1:
14160     case MMI_OPC_DIVU1:
14161         gen_div1_tx79(ctx, opc, rs, rt);
14162         break;
14163     default:
14164         MIPS_INVAL("TX79 MMI class");
14165         gen_reserved_instruction(ctx);
14166         break;
14167     }
14168 }
14169 
14170 static void gen_mmi_sq(DisasContext *ctx, int base, int rt, int offset)
14171 {
14172     gen_reserved_instruction(ctx);    /* TODO: MMI_OPC_SQ */
14173 }
14174 
14175 /*
14176  * The TX79-specific instruction Store Quadword
14177  *
14178  * +--------+-------+-------+------------------------+
14179  * | 011111 |  base |   rt  |           offset       | SQ
14180  * +--------+-------+-------+------------------------+
14181  *      6       5       5                 16
14182  *
14183  * has the same opcode as the Read Hardware Register instruction
14184  *
14185  * +--------+-------+-------+-------+-------+--------+
14186  * | 011111 | 00000 |   rt  |   rd  | 00000 | 111011 | RDHWR
14187  * +--------+-------+-------+-------+-------+--------+
14188  *      6       5       5       5       5        6
14189  *
14190  * that is required, trapped and emulated by the Linux kernel. However, all
14191  * RDHWR encodings yield address error exceptions on the TX79 since the SQ
14192  * offset is odd. Therefore all valid SQ instructions can execute normally.
14193  * In user mode, QEMU must verify the upper and lower 11 bits to distinguish
14194  * between SQ and RDHWR, as the Linux kernel does.
14195  */
14196 static void decode_mmi_sq(CPUMIPSState *env, DisasContext *ctx)
14197 {
14198     int base = extract32(ctx->opcode, 21, 5);
14199     int rt = extract32(ctx->opcode, 16, 5);
14200     int offset = extract32(ctx->opcode, 0, 16);
14201 
14202 #ifdef CONFIG_USER_ONLY
14203     uint32_t op1 = MASK_SPECIAL3(ctx->opcode);
14204     uint32_t op2 = extract32(ctx->opcode, 6, 5);
14205 
14206     if (base == 0 && op2 == 0 && op1 == OPC_RDHWR) {
14207         int rd = extract32(ctx->opcode, 11, 5);
14208 
14209         gen_rdhwr(ctx, rt, rd, 0);
14210         return;
14211     }
14212 #endif
14213 
14214     gen_mmi_sq(ctx, base, rt, offset);
14215 }
14216 
14217 #endif
14218 
14219 static void decode_opc_special3(CPUMIPSState *env, DisasContext *ctx)
14220 {
14221     int rs, rt, rd, sa;
14222     uint32_t op1, op2;
14223     int16_t imm;
14224 
14225     rs = (ctx->opcode >> 21) & 0x1f;
14226     rt = (ctx->opcode >> 16) & 0x1f;
14227     rd = (ctx->opcode >> 11) & 0x1f;
14228     sa = (ctx->opcode >> 6) & 0x1f;
14229     imm = sextract32(ctx->opcode, 7, 9);
14230 
14231     op1 = MASK_SPECIAL3(ctx->opcode);
14232 
14233     /*
14234      * EVA loads and stores overlap Loongson 2E instructions decoded by
14235      * decode_opc_special3_legacy(), so be careful to allow their decoding when
14236      * EVA is absent.
14237      */
14238     if (ctx->eva) {
14239         switch (op1) {
14240         case OPC_LWLE:
14241         case OPC_LWRE:
14242         case OPC_LBUE:
14243         case OPC_LHUE:
14244         case OPC_LBE:
14245         case OPC_LHE:
14246         case OPC_LLE:
14247         case OPC_LWE:
14248             check_cp0_enabled(ctx);
14249             gen_ld(ctx, op1, rt, rs, imm);
14250             return;
14251         case OPC_SWLE:
14252         case OPC_SWRE:
14253         case OPC_SBE:
14254         case OPC_SHE:
14255         case OPC_SWE:
14256             check_cp0_enabled(ctx);
14257             gen_st(ctx, op1, rt, rs, imm);
14258             return;
14259         case OPC_SCE:
14260             check_cp0_enabled(ctx);
14261             gen_st_cond(ctx, rt, rs, imm, mo_endian(ctx) | MO_SL, true);
14262             return;
14263         case OPC_CACHEE:
14264             check_eva(ctx);
14265             check_cp0_enabled(ctx);
14266             if (ctx->hflags & MIPS_HFLAG_ITC_CACHE) {
14267                 gen_cache_operation(ctx, rt, rs, imm);
14268             }
14269             return;
14270         case OPC_PREFE:
14271             check_cp0_enabled(ctx);
14272             /* Treat as NOP. */
14273             return;
14274         }
14275     }
14276 
14277     switch (op1) {
14278     case OPC_EXT:
14279     case OPC_INS:
14280         check_insn(ctx, ISA_MIPS_R2);
14281         gen_bitops(ctx, op1, rt, rs, sa, rd);
14282         break;
14283     case OPC_BSHFL:
14284         op2 = MASK_BSHFL(ctx->opcode);
14285         switch (op2) {
14286         case OPC_ALIGN:
14287         case OPC_ALIGN_1:
14288         case OPC_ALIGN_2:
14289         case OPC_ALIGN_3:
14290         case OPC_BITSWAP:
14291             check_insn(ctx, ISA_MIPS_R6);
14292             decode_opc_special3_r6(env, ctx);
14293             break;
14294         default:
14295             check_insn(ctx, ISA_MIPS_R2);
14296             gen_bshfl(ctx, op2, rt, rd);
14297             break;
14298         }
14299         break;
14300 #if defined(TARGET_MIPS64)
14301     case OPC_DEXTM:
14302     case OPC_DEXTU:
14303     case OPC_DEXT:
14304     case OPC_DINSM:
14305     case OPC_DINSU:
14306     case OPC_DINS:
14307         check_insn(ctx, ISA_MIPS_R2);
14308         check_mips_64(ctx);
14309         gen_bitops(ctx, op1, rt, rs, sa, rd);
14310         break;
14311     case OPC_DBSHFL:
14312         op2 = MASK_DBSHFL(ctx->opcode);
14313         switch (op2) {
14314         case OPC_DALIGN:
14315         case OPC_DALIGN_1:
14316         case OPC_DALIGN_2:
14317         case OPC_DALIGN_3:
14318         case OPC_DALIGN_4:
14319         case OPC_DALIGN_5:
14320         case OPC_DALIGN_6:
14321         case OPC_DALIGN_7:
14322         case OPC_DBITSWAP:
14323             check_insn(ctx, ISA_MIPS_R6);
14324             decode_opc_special3_r6(env, ctx);
14325             break;
14326         default:
14327             check_insn(ctx, ISA_MIPS_R2);
14328             check_mips_64(ctx);
14329             op2 = MASK_DBSHFL(ctx->opcode);
14330             gen_bshfl(ctx, op2, rt, rd);
14331             break;
14332         }
14333         break;
14334 #endif
14335     case OPC_RDHWR:
14336         gen_rdhwr(ctx, rt, rd, extract32(ctx->opcode, 6, 3));
14337         break;
14338     case OPC_FORK:
14339         check_mt(ctx);
14340         {
14341             TCGv t0 = tcg_temp_new();
14342             TCGv t1 = tcg_temp_new();
14343 
14344             gen_load_gpr(t0, rt);
14345             gen_load_gpr(t1, rs);
14346             gen_helper_fork(t0, t1);
14347         }
14348         break;
14349     case OPC_YIELD:
14350         check_mt(ctx);
14351         {
14352             TCGv t0 = tcg_temp_new();
14353 
14354             gen_load_gpr(t0, rs);
14355             gen_helper_yield(t0, tcg_env, t0);
14356             gen_store_gpr(t0, rd);
14357         }
14358         break;
14359     default:
14360         if (ctx->insn_flags & ISA_MIPS_R6) {
14361             decode_opc_special3_r6(env, ctx);
14362         } else {
14363             decode_opc_special3_legacy(env, ctx);
14364         }
14365     }
14366 }
14367 
14368 static bool decode_opc_legacy(CPUMIPSState *env, DisasContext *ctx)
14369 {
14370     int32_t offset;
14371     int rs, rt, rd, sa;
14372     uint32_t op, op1;
14373     int16_t imm;
14374 
14375     op = MASK_OP_MAJOR(ctx->opcode);
14376     rs = (ctx->opcode >> 21) & 0x1f;
14377     rt = (ctx->opcode >> 16) & 0x1f;
14378     rd = (ctx->opcode >> 11) & 0x1f;
14379     sa = (ctx->opcode >> 6) & 0x1f;
14380     imm = (int16_t)ctx->opcode;
14381     switch (op) {
14382     case OPC_SPECIAL:
14383         decode_opc_special(env, ctx);
14384         break;
14385     case OPC_SPECIAL2:
14386 #if defined(TARGET_MIPS64)
14387         if ((ctx->insn_flags & INSN_R5900) && (ctx->insn_flags & ASE_MMI)) {
14388             decode_mmi(env, ctx);
14389             break;
14390         }
14391 #endif
14392         if (TARGET_LONG_BITS == 32 && (ctx->insn_flags & ASE_MXU)) {
14393             if (decode_ase_mxu(ctx, ctx->opcode)) {
14394                 break;
14395             }
14396         }
14397         decode_opc_special2_legacy(env, ctx);
14398         break;
14399     case OPC_SPECIAL3:
14400 #if defined(TARGET_MIPS64)
14401         if (ctx->insn_flags & INSN_R5900) {
14402             decode_mmi_sq(env, ctx);    /* MMI_OPC_SQ */
14403         } else {
14404             decode_opc_special3(env, ctx);
14405         }
14406 #else
14407         decode_opc_special3(env, ctx);
14408 #endif
14409         break;
14410     case OPC_REGIMM:
14411         op1 = MASK_REGIMM(ctx->opcode);
14412         switch (op1) {
14413         case OPC_BLTZL: /* REGIMM branches */
14414         case OPC_BGEZL:
14415         case OPC_BLTZALL:
14416         case OPC_BGEZALL:
14417             check_insn(ctx, ISA_MIPS2);
14418             check_insn_opc_removed(ctx, ISA_MIPS_R6);
14419             /* Fallthrough */
14420         case OPC_BLTZ:
14421         case OPC_BGEZ:
14422             gen_compute_branch(ctx, op1, 4, rs, -1, imm << 2, 4);
14423             break;
14424         case OPC_BLTZAL:
14425         case OPC_BGEZAL:
14426             if (ctx->insn_flags & ISA_MIPS_R6) {
14427                 if (rs == 0) {
14428                     /* OPC_NAL, OPC_BAL */
14429                     gen_compute_branch(ctx, op1, 4, 0, -1, imm << 2, 4);
14430                 } else {
14431                     gen_reserved_instruction(ctx);
14432                 }
14433             } else {
14434                 gen_compute_branch(ctx, op1, 4, rs, -1, imm << 2, 4);
14435             }
14436             break;
14437         case OPC_TGEI: /* REGIMM traps */
14438         case OPC_TGEIU:
14439         case OPC_TLTI:
14440         case OPC_TLTIU:
14441         case OPC_TEQI:
14442         case OPC_TNEI:
14443             check_insn(ctx, ISA_MIPS2);
14444             check_insn_opc_removed(ctx, ISA_MIPS_R6);
14445             gen_trap(ctx, op1, rs, -1, imm, 0);
14446             break;
14447         case OPC_SIGRIE:
14448             check_insn(ctx, ISA_MIPS_R6);
14449             gen_reserved_instruction(ctx);
14450             break;
14451         case OPC_SYNCI:
14452             check_insn(ctx, ISA_MIPS_R2);
14453             /*
14454              * Break the TB to be able to sync copied instructions
14455              * immediately.
14456              */
14457             ctx->base.is_jmp = DISAS_STOP;
14458             break;
14459         case OPC_BPOSGE32:    /* MIPS DSP branch */
14460 #if defined(TARGET_MIPS64)
14461         case OPC_BPOSGE64:
14462 #endif
14463             check_dsp(ctx);
14464             gen_compute_branch(ctx, op1, 4, -1, -2, (int32_t)imm << 2, 4);
14465             break;
14466 #if defined(TARGET_MIPS64)
14467         case OPC_DAHI:
14468             check_insn(ctx, ISA_MIPS_R6);
14469             check_mips_64(ctx);
14470             if (rs != 0) {
14471                 tcg_gen_addi_tl(cpu_gpr[rs], cpu_gpr[rs], (int64_t)imm << 32);
14472             }
14473             break;
14474         case OPC_DATI:
14475             check_insn(ctx, ISA_MIPS_R6);
14476             check_mips_64(ctx);
14477             if (rs != 0) {
14478                 tcg_gen_addi_tl(cpu_gpr[rs], cpu_gpr[rs], (int64_t)imm << 48);
14479             }
14480             break;
14481 #endif
14482         default:            /* Invalid */
14483             MIPS_INVAL("regimm");
14484             gen_reserved_instruction(ctx);
14485             break;
14486         }
14487         break;
14488     case OPC_CP0:
14489         check_cp0_enabled(ctx);
14490         op1 = MASK_CP0(ctx->opcode);
14491         switch (op1) {
14492         case OPC_MFC0:
14493         case OPC_MTC0:
14494         case OPC_MFTR:
14495         case OPC_MTTR:
14496         case OPC_MFHC0:
14497         case OPC_MTHC0:
14498 #if defined(TARGET_MIPS64)
14499         case OPC_DMFC0:
14500         case OPC_DMTC0:
14501 #endif
14502 #ifndef CONFIG_USER_ONLY
14503             gen_cp0(env, ctx, op1, rt, rd);
14504 #endif /* !CONFIG_USER_ONLY */
14505             break;
14506         case OPC_C0:
14507         case OPC_C0_1:
14508         case OPC_C0_2:
14509         case OPC_C0_3:
14510         case OPC_C0_4:
14511         case OPC_C0_5:
14512         case OPC_C0_6:
14513         case OPC_C0_7:
14514         case OPC_C0_8:
14515         case OPC_C0_9:
14516         case OPC_C0_A:
14517         case OPC_C0_B:
14518         case OPC_C0_C:
14519         case OPC_C0_D:
14520         case OPC_C0_E:
14521         case OPC_C0_F:
14522 #ifndef CONFIG_USER_ONLY
14523             gen_cp0(env, ctx, MASK_C0(ctx->opcode), rt, rd);
14524 #endif /* !CONFIG_USER_ONLY */
14525             break;
14526         case OPC_MFMC0:
14527 #ifndef CONFIG_USER_ONLY
14528             {
14529                 uint32_t op2;
14530                 TCGv t0 = tcg_temp_new();
14531 
14532                 op2 = MASK_MFMC0(ctx->opcode);
14533                 switch (op2) {
14534                 case OPC_DMT:
14535                     check_cp0_mt(ctx);
14536                     gen_helper_dmt(t0);
14537                     gen_store_gpr(t0, rt);
14538                     break;
14539                 case OPC_EMT:
14540                     check_cp0_mt(ctx);
14541                     gen_helper_emt(t0);
14542                     gen_store_gpr(t0, rt);
14543                     break;
14544                 case OPC_DVPE:
14545                     check_cp0_mt(ctx);
14546                     gen_helper_dvpe(t0, tcg_env);
14547                     gen_store_gpr(t0, rt);
14548                     break;
14549                 case OPC_EVPE:
14550                     check_cp0_mt(ctx);
14551                     gen_helper_evpe(t0, tcg_env);
14552                     gen_store_gpr(t0, rt);
14553                     break;
14554                 case OPC_DVP:
14555                     check_insn(ctx, ISA_MIPS_R6);
14556                     if (ctx->vp) {
14557                         gen_helper_dvp(t0, tcg_env);
14558                         gen_store_gpr(t0, rt);
14559                     }
14560                     break;
14561                 case OPC_EVP:
14562                     check_insn(ctx, ISA_MIPS_R6);
14563                     if (ctx->vp) {
14564                         gen_helper_evp(t0, tcg_env);
14565                         gen_store_gpr(t0, rt);
14566                     }
14567                     break;
14568                 case OPC_DI:
14569                     check_insn(ctx, ISA_MIPS_R2);
14570                     save_cpu_state(ctx, 1);
14571                     gen_helper_di(t0, tcg_env);
14572                     gen_store_gpr(t0, rt);
14573                     /*
14574                      * Stop translation as we may have switched
14575                      * the execution mode.
14576                      */
14577                     ctx->base.is_jmp = DISAS_STOP;
14578                     break;
14579                 case OPC_EI:
14580                     check_insn(ctx, ISA_MIPS_R2);
14581                     save_cpu_state(ctx, 1);
14582                     gen_helper_ei(t0, tcg_env);
14583                     gen_store_gpr(t0, rt);
14584                     /*
14585                      * DISAS_STOP isn't sufficient, we need to ensure we break
14586                      * out of translated code to check for pending interrupts.
14587                      */
14588                     gen_save_pc(ctx->base.pc_next + 4);
14589                     ctx->base.is_jmp = DISAS_EXIT;
14590                     break;
14591                 default:            /* Invalid */
14592                     MIPS_INVAL("mfmc0");
14593                     gen_reserved_instruction(ctx);
14594                     break;
14595                 }
14596             }
14597 #endif /* !CONFIG_USER_ONLY */
14598             break;
14599         case OPC_RDPGPR:
14600             check_insn(ctx, ISA_MIPS_R2);
14601             gen_load_srsgpr(rt, rd);
14602             break;
14603         case OPC_WRPGPR:
14604             check_insn(ctx, ISA_MIPS_R2);
14605             gen_store_srsgpr(rt, rd);
14606             break;
14607         default:
14608             MIPS_INVAL("cp0");
14609             gen_reserved_instruction(ctx);
14610             break;
14611         }
14612         break;
14613     case OPC_BOVC: /* OPC_BEQZALC, OPC_BEQC, OPC_ADDI */
14614         if (ctx->insn_flags & ISA_MIPS_R6) {
14615             /* OPC_BOVC, OPC_BEQZALC, OPC_BEQC */
14616             gen_compute_compact_branch(ctx, op, rs, rt, imm << 2);
14617         } else {
14618             /* OPC_ADDI */
14619             /* Arithmetic with immediate opcode */
14620             gen_arith_imm(ctx, op, rt, rs, imm);
14621         }
14622         break;
14623     case OPC_ADDIU:
14624          gen_arith_imm(ctx, op, rt, rs, imm);
14625          break;
14626     case OPC_SLTI: /* Set on less than with immediate opcode */
14627     case OPC_SLTIU:
14628          gen_slt_imm(ctx, op, rt, rs, imm);
14629          break;
14630     case OPC_ANDI: /* Arithmetic with immediate opcode */
14631     case OPC_LUI: /* OPC_AUI */
14632     case OPC_ORI:
14633     case OPC_XORI:
14634          gen_logic_imm(ctx, op, rt, rs, imm);
14635          break;
14636     case OPC_J: /* Jump */
14637     case OPC_JAL:
14638          offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
14639          gen_compute_branch(ctx, op, 4, rs, rt, offset, 4);
14640          break;
14641     /* Branch */
14642     case OPC_BLEZC: /* OPC_BGEZC, OPC_BGEC, OPC_BLEZL */
14643         if (ctx->insn_flags & ISA_MIPS_R6) {
14644             if (rt == 0) {
14645                 gen_reserved_instruction(ctx);
14646                 break;
14647             }
14648             /* OPC_BLEZC, OPC_BGEZC, OPC_BGEC */
14649             gen_compute_compact_branch(ctx, op, rs, rt, imm << 2);
14650         } else {
14651             /* OPC_BLEZL */
14652             gen_compute_branch(ctx, op, 4, rs, rt, imm << 2, 4);
14653         }
14654         break;
14655     case OPC_BGTZC: /* OPC_BLTZC, OPC_BLTC, OPC_BGTZL */
14656         if (ctx->insn_flags & ISA_MIPS_R6) {
14657             if (rt == 0) {
14658                 gen_reserved_instruction(ctx);
14659                 break;
14660             }
14661             /* OPC_BGTZC, OPC_BLTZC, OPC_BLTC */
14662             gen_compute_compact_branch(ctx, op, rs, rt, imm << 2);
14663         } else {
14664             /* OPC_BGTZL */
14665             gen_compute_branch(ctx, op, 4, rs, rt, imm << 2, 4);
14666         }
14667         break;
14668     case OPC_BLEZALC: /* OPC_BGEZALC, OPC_BGEUC, OPC_BLEZ */
14669         if (rt == 0) {
14670             /* OPC_BLEZ */
14671             gen_compute_branch(ctx, op, 4, rs, rt, imm << 2, 4);
14672         } else {
14673             check_insn(ctx, ISA_MIPS_R6);
14674             /* OPC_BLEZALC, OPC_BGEZALC, OPC_BGEUC */
14675             gen_compute_compact_branch(ctx, op, rs, rt, imm << 2);
14676         }
14677         break;
14678     case OPC_BGTZALC: /* OPC_BLTZALC, OPC_BLTUC, OPC_BGTZ */
14679         if (rt == 0) {
14680             /* OPC_BGTZ */
14681             gen_compute_branch(ctx, op, 4, rs, rt, imm << 2, 4);
14682         } else {
14683             check_insn(ctx, ISA_MIPS_R6);
14684             /* OPC_BGTZALC, OPC_BLTZALC, OPC_BLTUC */
14685             gen_compute_compact_branch(ctx, op, rs, rt, imm << 2);
14686         }
14687         break;
14688     case OPC_BEQL:
14689     case OPC_BNEL:
14690         check_insn(ctx, ISA_MIPS2);
14691          check_insn_opc_removed(ctx, ISA_MIPS_R6);
14692         /* Fallthrough */
14693     case OPC_BEQ:
14694     case OPC_BNE:
14695          gen_compute_branch(ctx, op, 4, rs, rt, imm << 2, 4);
14696          break;
14697     case OPC_LL: /* Load and stores */
14698         check_insn(ctx, ISA_MIPS2);
14699         if (ctx->insn_flags & INSN_R5900) {
14700             check_insn_opc_user_only(ctx, INSN_R5900);
14701         }
14702         /* Fallthrough */
14703     case OPC_LWL:
14704     case OPC_LWR:
14705     case OPC_LB:
14706     case OPC_LH:
14707     case OPC_LW:
14708     case OPC_LWPC:
14709     case OPC_LBU:
14710     case OPC_LHU:
14711          gen_ld(ctx, op, rt, rs, imm);
14712          break;
14713     case OPC_SWL:
14714     case OPC_SWR:
14715     case OPC_SB:
14716     case OPC_SH:
14717     case OPC_SW:
14718          gen_st(ctx, op, rt, rs, imm);
14719          break;
14720     case OPC_SC:
14721         check_insn(ctx, ISA_MIPS2);
14722         if (ctx->insn_flags & INSN_R5900) {
14723             check_insn_opc_user_only(ctx, INSN_R5900);
14724         }
14725         gen_st_cond(ctx, rt, rs, imm, mo_endian(ctx) | MO_SL, false);
14726         break;
14727     case OPC_CACHE:
14728         check_cp0_enabled(ctx);
14729         check_insn(ctx, ISA_MIPS3 | ISA_MIPS_R1);
14730         if (ctx->hflags & MIPS_HFLAG_ITC_CACHE) {
14731             gen_cache_operation(ctx, rt, rs, imm);
14732         }
14733         /* Treat as NOP. */
14734         break;
14735     case OPC_PREF:
14736         check_insn(ctx, ISA_MIPS4 | ISA_MIPS_R1 | INSN_R5900);
14737         /* Treat as NOP. */
14738         break;
14739 
14740     /* Floating point (COP1). */
14741     case OPC_LWC1:
14742     case OPC_LDC1:
14743     case OPC_SWC1:
14744     case OPC_SDC1:
14745         gen_cop1_ldst(ctx, op, rt, rs, imm);
14746         break;
14747 
14748     case OPC_CP1:
14749         op1 = MASK_CP1(ctx->opcode);
14750 
14751         switch (op1) {
14752         case OPC_MFHC1:
14753         case OPC_MTHC1:
14754             check_cp1_enabled(ctx);
14755             check_insn(ctx, ISA_MIPS_R2);
14756             /* fall through */
14757         case OPC_MFC1:
14758         case OPC_CFC1:
14759         case OPC_MTC1:
14760         case OPC_CTC1:
14761             check_cp1_enabled(ctx);
14762             gen_cp1(ctx, op1, rt, rd);
14763             break;
14764 #if defined(TARGET_MIPS64)
14765         case OPC_DMFC1:
14766         case OPC_DMTC1:
14767             check_cp1_enabled(ctx);
14768             check_insn(ctx, ISA_MIPS3);
14769             check_mips_64(ctx);
14770             gen_cp1(ctx, op1, rt, rd);
14771             break;
14772 #endif
14773         case OPC_BC1EQZ: /* OPC_BC1ANY2 */
14774             check_cp1_enabled(ctx);
14775             if (ctx->insn_flags & ISA_MIPS_R6) {
14776                 /* OPC_BC1EQZ */
14777                 gen_compute_branch1_r6(ctx, MASK_CP1(ctx->opcode),
14778                                        rt, imm << 2, 4);
14779             } else {
14780                 /* OPC_BC1ANY2 */
14781                 check_cop1x(ctx);
14782                 check_insn(ctx, ASE_MIPS3D);
14783                 gen_compute_branch1(ctx, MASK_BC1(ctx->opcode),
14784                                     (rt >> 2) & 0x7, imm << 2);
14785             }
14786             break;
14787         case OPC_BC1NEZ:
14788             check_cp1_enabled(ctx);
14789             check_insn(ctx, ISA_MIPS_R6);
14790             gen_compute_branch1_r6(ctx, MASK_CP1(ctx->opcode),
14791                                    rt, imm << 2, 4);
14792             break;
14793         case OPC_BC1ANY4:
14794             check_cp1_enabled(ctx);
14795             check_insn_opc_removed(ctx, ISA_MIPS_R6);
14796             check_cop1x(ctx);
14797             check_insn(ctx, ASE_MIPS3D);
14798             /* fall through */
14799         case OPC_BC1:
14800             check_cp1_enabled(ctx);
14801             check_insn_opc_removed(ctx, ISA_MIPS_R6);
14802             gen_compute_branch1(ctx, MASK_BC1(ctx->opcode),
14803                                 (rt >> 2) & 0x7, imm << 2);
14804             break;
14805         case OPC_PS_FMT:
14806             check_ps(ctx);
14807             /* fall through */
14808         case OPC_S_FMT:
14809         case OPC_D_FMT:
14810             check_cp1_enabled(ctx);
14811             gen_farith(ctx, ctx->opcode & FOP(0x3f, 0x1f), rt, rd, sa,
14812                        (imm >> 8) & 0x7);
14813             break;
14814         case OPC_W_FMT:
14815         case OPC_L_FMT:
14816         {
14817             int r6_op = ctx->opcode & FOP(0x3f, 0x1f);
14818             check_cp1_enabled(ctx);
14819             if (ctx->insn_flags & ISA_MIPS_R6) {
14820                 switch (r6_op) {
14821                 case R6_OPC_CMP_AF_S:
14822                 case R6_OPC_CMP_UN_S:
14823                 case R6_OPC_CMP_EQ_S:
14824                 case R6_OPC_CMP_UEQ_S:
14825                 case R6_OPC_CMP_LT_S:
14826                 case R6_OPC_CMP_ULT_S:
14827                 case R6_OPC_CMP_LE_S:
14828                 case R6_OPC_CMP_ULE_S:
14829                 case R6_OPC_CMP_SAF_S:
14830                 case R6_OPC_CMP_SUN_S:
14831                 case R6_OPC_CMP_SEQ_S:
14832                 case R6_OPC_CMP_SEUQ_S:
14833                 case R6_OPC_CMP_SLT_S:
14834                 case R6_OPC_CMP_SULT_S:
14835                 case R6_OPC_CMP_SLE_S:
14836                 case R6_OPC_CMP_SULE_S:
14837                 case R6_OPC_CMP_OR_S:
14838                 case R6_OPC_CMP_UNE_S:
14839                 case R6_OPC_CMP_NE_S:
14840                 case R6_OPC_CMP_SOR_S:
14841                 case R6_OPC_CMP_SUNE_S:
14842                 case R6_OPC_CMP_SNE_S:
14843                     gen_r6_cmp_s(ctx, ctx->opcode & 0x1f, rt, rd, sa);
14844                     break;
14845                 case R6_OPC_CMP_AF_D:
14846                 case R6_OPC_CMP_UN_D:
14847                 case R6_OPC_CMP_EQ_D:
14848                 case R6_OPC_CMP_UEQ_D:
14849                 case R6_OPC_CMP_LT_D:
14850                 case R6_OPC_CMP_ULT_D:
14851                 case R6_OPC_CMP_LE_D:
14852                 case R6_OPC_CMP_ULE_D:
14853                 case R6_OPC_CMP_SAF_D:
14854                 case R6_OPC_CMP_SUN_D:
14855                 case R6_OPC_CMP_SEQ_D:
14856                 case R6_OPC_CMP_SEUQ_D:
14857                 case R6_OPC_CMP_SLT_D:
14858                 case R6_OPC_CMP_SULT_D:
14859                 case R6_OPC_CMP_SLE_D:
14860                 case R6_OPC_CMP_SULE_D:
14861                 case R6_OPC_CMP_OR_D:
14862                 case R6_OPC_CMP_UNE_D:
14863                 case R6_OPC_CMP_NE_D:
14864                 case R6_OPC_CMP_SOR_D:
14865                 case R6_OPC_CMP_SUNE_D:
14866                 case R6_OPC_CMP_SNE_D:
14867                     gen_r6_cmp_d(ctx, ctx->opcode & 0x1f, rt, rd, sa);
14868                     break;
14869                 default:
14870                     gen_farith(ctx, ctx->opcode & FOP(0x3f, 0x1f),
14871                                rt, rd, sa, (imm >> 8) & 0x7);
14872 
14873                     break;
14874                 }
14875             } else {
14876                 gen_farith(ctx, ctx->opcode & FOP(0x3f, 0x1f), rt, rd, sa,
14877                            (imm >> 8) & 0x7);
14878             }
14879             break;
14880         }
14881         default:
14882             MIPS_INVAL("cp1");
14883             gen_reserved_instruction(ctx);
14884             break;
14885         }
14886         break;
14887 
14888     /* Compact branches [R6] and COP2 [non-R6] */
14889     case OPC_BC: /* OPC_LWC2 */
14890     case OPC_BALC: /* OPC_SWC2 */
14891         if (ctx->insn_flags & ISA_MIPS_R6) {
14892             /* OPC_BC, OPC_BALC */
14893             gen_compute_compact_branch(ctx, op, 0, 0,
14894                                        sextract32(ctx->opcode << 2, 0, 28));
14895         } else if (ctx->insn_flags & ASE_LEXT) {
14896             gen_loongson_lswc2(ctx, rt, rs, rd);
14897         } else {
14898             /* OPC_LWC2, OPC_SWC2 */
14899             /* COP2: Not implemented. */
14900             generate_exception_err(ctx, EXCP_CpU, 2);
14901         }
14902         break;
14903     case OPC_BEQZC: /* OPC_JIC, OPC_LDC2 */
14904     case OPC_BNEZC: /* OPC_JIALC, OPC_SDC2 */
14905         if (ctx->insn_flags & ISA_MIPS_R6) {
14906             if (rs != 0) {
14907                 /* OPC_BEQZC, OPC_BNEZC */
14908                 gen_compute_compact_branch(ctx, op, rs, 0,
14909                                            sextract32(ctx->opcode << 2, 0, 23));
14910             } else {
14911                 /* OPC_JIC, OPC_JIALC */
14912                 gen_compute_compact_branch(ctx, op, 0, rt, imm);
14913             }
14914         } else if (ctx->insn_flags & ASE_LEXT) {
14915             gen_loongson_lsdc2(ctx, rt, rs, rd);
14916         } else {
14917             /* OPC_LWC2, OPC_SWC2 */
14918             /* COP2: Not implemented. */
14919             generate_exception_err(ctx, EXCP_CpU, 2);
14920         }
14921         break;
14922     case OPC_CP2:
14923         check_insn(ctx, ASE_LMMI);
14924         /* Note that these instructions use different fields.  */
14925         gen_loongson_multimedia(ctx, sa, rd, rt);
14926         break;
14927 
14928     case OPC_CP3:
14929         if (ctx->CP0_Config1 & (1 << CP0C1_FP)) {
14930             check_cp1_enabled(ctx);
14931             op1 = MASK_CP3(ctx->opcode);
14932             switch (op1) {
14933             case OPC_LUXC1:
14934             case OPC_SUXC1:
14935                 check_insn(ctx, ISA_MIPS5 | ISA_MIPS_R2);
14936                 /* Fallthrough */
14937             case OPC_LWXC1:
14938             case OPC_LDXC1:
14939             case OPC_SWXC1:
14940             case OPC_SDXC1:
14941                 check_insn(ctx, ISA_MIPS4 | ISA_MIPS_R2);
14942                 gen_flt3_ldst(ctx, op1, sa, rd, rs, rt);
14943                 break;
14944             case OPC_PREFX:
14945                 check_insn(ctx, ISA_MIPS4 | ISA_MIPS_R2);
14946                 /* Treat as NOP. */
14947                 break;
14948             case OPC_ALNV_PS:
14949                 check_insn(ctx, ISA_MIPS5 | ISA_MIPS_R2);
14950                 /* Fallthrough */
14951             case OPC_MADD_S:
14952             case OPC_MADD_D:
14953             case OPC_MADD_PS:
14954             case OPC_MSUB_S:
14955             case OPC_MSUB_D:
14956             case OPC_MSUB_PS:
14957             case OPC_NMADD_S:
14958             case OPC_NMADD_D:
14959             case OPC_NMADD_PS:
14960             case OPC_NMSUB_S:
14961             case OPC_NMSUB_D:
14962             case OPC_NMSUB_PS:
14963                 check_insn(ctx, ISA_MIPS4 | ISA_MIPS_R2);
14964                 gen_flt3_arith(ctx, op1, sa, rs, rd, rt);
14965                 break;
14966             default:
14967                 MIPS_INVAL("cp3");
14968                 gen_reserved_instruction(ctx);
14969                 break;
14970             }
14971         } else {
14972             generate_exception_err(ctx, EXCP_CpU, 1);
14973         }
14974         break;
14975 
14976 #if defined(TARGET_MIPS64)
14977     /* MIPS64 opcodes */
14978     case OPC_LLD:
14979         if (ctx->insn_flags & INSN_R5900) {
14980             check_insn_opc_user_only(ctx, INSN_R5900);
14981         }
14982         /* fall through */
14983     case OPC_LDL:
14984     case OPC_LDR:
14985     case OPC_LWU:
14986     case OPC_LD:
14987         check_insn(ctx, ISA_MIPS3);
14988         check_mips_64(ctx);
14989         gen_ld(ctx, op, rt, rs, imm);
14990         break;
14991     case OPC_SDL:
14992     case OPC_SDR:
14993     case OPC_SD:
14994         check_insn(ctx, ISA_MIPS3);
14995         check_mips_64(ctx);
14996         gen_st(ctx, op, rt, rs, imm);
14997         break;
14998     case OPC_SCD:
14999         check_insn(ctx, ISA_MIPS3);
15000         if (ctx->insn_flags & INSN_R5900) {
15001             check_insn_opc_user_only(ctx, INSN_R5900);
15002         }
15003         check_mips_64(ctx);
15004         gen_st_cond(ctx, rt, rs, imm, mo_endian(ctx) | MO_UQ, false);
15005         break;
15006     case OPC_BNVC: /* OPC_BNEZALC, OPC_BNEC, OPC_DADDI */
15007         if (ctx->insn_flags & ISA_MIPS_R6) {
15008             /* OPC_BNVC, OPC_BNEZALC, OPC_BNEC */
15009             gen_compute_compact_branch(ctx, op, rs, rt, imm << 2);
15010         } else {
15011             /* OPC_DADDI */
15012             check_insn(ctx, ISA_MIPS3);
15013             check_mips_64(ctx);
15014             gen_arith_imm(ctx, op, rt, rs, imm);
15015         }
15016         break;
15017     case OPC_DADDIU:
15018         check_insn(ctx, ISA_MIPS3);
15019         check_mips_64(ctx);
15020         gen_arith_imm(ctx, op, rt, rs, imm);
15021         break;
15022 #else
15023     case OPC_BNVC: /* OPC_BNEZALC, OPC_BNEC */
15024         if (ctx->insn_flags & ISA_MIPS_R6) {
15025             gen_compute_compact_branch(ctx, op, rs, rt, imm << 2);
15026         } else {
15027             MIPS_INVAL("major opcode");
15028             gen_reserved_instruction(ctx);
15029         }
15030         break;
15031 #endif
15032     case OPC_DAUI: /* OPC_JALX */
15033         if (ctx->insn_flags & ISA_MIPS_R6) {
15034 #if defined(TARGET_MIPS64)
15035             /* OPC_DAUI */
15036             check_mips_64(ctx);
15037             if (rs == 0) {
15038                 generate_exception(ctx, EXCP_RI);
15039             } else if (rt != 0) {
15040                 TCGv t0 = tcg_temp_new();
15041                 gen_load_gpr(t0, rs);
15042                 tcg_gen_addi_tl(cpu_gpr[rt], t0, imm << 16);
15043             }
15044 #else
15045             gen_reserved_instruction(ctx);
15046             MIPS_INVAL("major opcode");
15047 #endif
15048         } else {
15049             /* OPC_JALX */
15050             check_insn(ctx, ASE_MIPS16 | ASE_MICROMIPS);
15051             offset = (int32_t)(ctx->opcode & 0x3FFFFFF) << 2;
15052             gen_compute_branch(ctx, op, 4, rs, rt, offset, 4);
15053         }
15054         break;
15055     case OPC_MDMX:
15056         /* MDMX: Not implemented. */
15057         break;
15058     case OPC_PCREL:
15059         check_insn(ctx, ISA_MIPS_R6);
15060         gen_pcrel(ctx, ctx->opcode, ctx->base.pc_next, rs);
15061         break;
15062     default:            /* Invalid */
15063         MIPS_INVAL("major opcode");
15064         return false;
15065     }
15066     return true;
15067 }
15068 
15069 static void decode_opc(CPUMIPSState *env, DisasContext *ctx)
15070 {
15071     /* make sure instructions are on a word boundary */
15072     if (ctx->base.pc_next & 0x3) {
15073         env->CP0_BadVAddr = ctx->base.pc_next;
15074         generate_exception_err(ctx, EXCP_AdEL, EXCP_INST_NOTAVAIL);
15075         return;
15076     }
15077 
15078     /* Handle blikely not taken case */
15079     if ((ctx->hflags & MIPS_HFLAG_BMASK_BASE) == MIPS_HFLAG_BL) {
15080         TCGLabel *l1 = gen_new_label();
15081 
15082         tcg_gen_brcondi_tl(TCG_COND_NE, bcond, 0, l1);
15083         tcg_gen_movi_i32(hflags, ctx->hflags & ~MIPS_HFLAG_BMASK);
15084         gen_goto_tb(ctx, 1, ctx->base.pc_next + 4);
15085         gen_set_label(l1);
15086     }
15087 
15088     /* Transition to the auto-generated decoder.  */
15089 
15090     /* Vendor specific extensions */
15091     if (cpu_supports_isa(env, INSN_R5900) && decode_ext_txx9(ctx, ctx->opcode)) {
15092         return;
15093     }
15094     if (cpu_supports_isa(env, INSN_VR54XX) && decode_ext_vr54xx(ctx, ctx->opcode)) {
15095         return;
15096     }
15097     if (TARGET_LONG_BITS == 64 && decode_ext_loongson(ctx, ctx->opcode)) {
15098         return;
15099     }
15100 #if defined(TARGET_MIPS64)
15101     if (ase_lcsr_available(env) && decode_ase_lcsr(ctx, ctx->opcode)) {
15102         return;
15103     }
15104     if (cpu_supports_isa(env, INSN_OCTEON) && decode_ext_octeon(ctx, ctx->opcode)) {
15105         return;
15106     }
15107 #endif
15108 
15109     /* ISA extensions */
15110     if (ase_msa_available(env) && decode_ase_msa(ctx, ctx->opcode)) {
15111         return;
15112     }
15113 
15114     /* ISA (from latest to oldest) */
15115     if (cpu_supports_isa(env, ISA_MIPS_R6) && decode_isa_rel6(ctx, ctx->opcode)) {
15116         return;
15117     }
15118 
15119     if (decode_opc_legacy(env, ctx)) {
15120         return;
15121     }
15122 
15123     gen_reserved_instruction(ctx);
15124 }
15125 
15126 static void mips_tr_init_disas_context(DisasContextBase *dcbase, CPUState *cs)
15127 {
15128     DisasContext *ctx = container_of(dcbase, DisasContext, base);
15129     CPUMIPSState *env = cpu_env(cs);
15130 
15131     ctx->page_start = ctx->base.pc_first & TARGET_PAGE_MASK;
15132     ctx->saved_pc = -1;
15133     ctx->insn_flags = env->insn_flags;
15134     ctx->CP0_Config0 = env->CP0_Config0;
15135     ctx->CP0_Config1 = env->CP0_Config1;
15136     ctx->CP0_Config2 = env->CP0_Config2;
15137     ctx->CP0_Config3 = env->CP0_Config3;
15138     ctx->CP0_Config5 = env->CP0_Config5;
15139     ctx->btarget = 0;
15140     ctx->kscrexist = (env->CP0_Config4 >> CP0C4_KScrExist) & 0xff;
15141     ctx->rxi = (env->CP0_Config3 >> CP0C3_RXI) & 1;
15142     ctx->ie = (env->CP0_Config4 >> CP0C4_IE) & 3;
15143     ctx->bi = (env->CP0_Config3 >> CP0C3_BI) & 1;
15144     ctx->bp = (env->CP0_Config3 >> CP0C3_BP) & 1;
15145     ctx->PAMask = env->PAMask;
15146     ctx->mvh = (env->CP0_Config5 >> CP0C5_MVH) & 1;
15147     ctx->eva = (env->CP0_Config5 >> CP0C5_EVA) & 1;
15148     ctx->sc = (env->CP0_Config3 >> CP0C3_SC) & 1;
15149     ctx->CP0_LLAddr_shift = env->CP0_LLAddr_shift;
15150     ctx->cmgcr = (env->CP0_Config3 >> CP0C3_CMGCR) & 1;
15151     /* Restore delay slot state from the tb context.  */
15152     ctx->hflags = (uint32_t)ctx->base.tb->flags; /* FIXME: maybe use 64 bits? */
15153     ctx->ulri = (env->CP0_Config3 >> CP0C3_ULRI) & 1;
15154     ctx->ps = ((env->active_fpu.fcr0 >> FCR0_PS) & 1) ||
15155              (env->insn_flags & (INSN_LOONGSON2E | INSN_LOONGSON2F));
15156     ctx->vp = (env->CP0_Config5 >> CP0C5_VP) & 1;
15157     ctx->mrp = (env->CP0_Config5 >> CP0C5_MRP) & 1;
15158     ctx->nan2008 = (env->active_fpu.fcr31 >> FCR31_NAN2008) & 1;
15159     ctx->abs2008 = (env->active_fpu.fcr31 >> FCR31_ABS2008) & 1;
15160     ctx->mi = (env->CP0_Config5 >> CP0C5_MI) & 1;
15161     ctx->gi = (env->CP0_Config5 >> CP0C5_GI) & 3;
15162     restore_cpu_state(env, ctx);
15163 #ifdef CONFIG_USER_ONLY
15164         ctx->mem_idx = MIPS_HFLAG_UM;
15165 #else
15166         ctx->mem_idx = hflags_mmu_index(ctx->hflags);
15167 #endif
15168     ctx->default_tcg_memop_mask = (!(ctx->insn_flags & ISA_NANOMIPS32) &&
15169                                   (ctx->insn_flags & (ISA_MIPS_R6 |
15170                                   INSN_LOONGSON3A))) ? MO_UNALN : MO_ALIGN;
15171 
15172     /*
15173      * Execute a branch and its delay slot as a single instruction.
15174      * This is what GDB expects and is consistent with what the
15175      * hardware does (e.g. if a delay slot instruction faults, the
15176      * reported PC is the PC of the branch).
15177      */
15178     if ((tb_cflags(ctx->base.tb) & CF_SINGLE_STEP) &&
15179         (ctx->hflags & MIPS_HFLAG_BMASK)) {
15180         ctx->base.max_insns = 2;
15181     }
15182 
15183     LOG_DISAS("\ntb %p idx %d hflags %04x\n", ctx->base.tb, ctx->mem_idx,
15184               ctx->hflags);
15185 }
15186 
15187 static void mips_tr_tb_start(DisasContextBase *dcbase, CPUState *cs)
15188 {
15189 }
15190 
15191 static void mips_tr_insn_start(DisasContextBase *dcbase, CPUState *cs)
15192 {
15193     DisasContext *ctx = container_of(dcbase, DisasContext, base);
15194 
15195     tcg_gen_insn_start(ctx->base.pc_next, ctx->hflags & MIPS_HFLAG_BMASK,
15196                        ctx->btarget);
15197 }
15198 
15199 static void mips_tr_translate_insn(DisasContextBase *dcbase, CPUState *cs)
15200 {
15201     CPUMIPSState *env = cpu_env(cs);
15202     DisasContext *ctx = container_of(dcbase, DisasContext, base);
15203     int insn_bytes;
15204     int is_slot;
15205 
15206     is_slot = ctx->hflags & MIPS_HFLAG_BMASK;
15207     if (ctx->insn_flags & ISA_NANOMIPS32) {
15208         ctx->opcode = translator_lduw(env, &ctx->base, ctx->base.pc_next);
15209         insn_bytes = decode_isa_nanomips(env, ctx);
15210     } else if (!(ctx->hflags & MIPS_HFLAG_M16)) {
15211         ctx->opcode = translator_ldl(env, &ctx->base, ctx->base.pc_next);
15212         insn_bytes = 4;
15213         decode_opc(env, ctx);
15214     } else if (ctx->insn_flags & ASE_MICROMIPS) {
15215         ctx->opcode = translator_lduw(env, &ctx->base, ctx->base.pc_next);
15216         insn_bytes = decode_isa_micromips(env, ctx);
15217     } else if (ctx->insn_flags & ASE_MIPS16) {
15218         ctx->opcode = translator_lduw(env, &ctx->base, ctx->base.pc_next);
15219         insn_bytes = decode_ase_mips16e(env, ctx);
15220     } else {
15221         gen_reserved_instruction(ctx);
15222         g_assert(ctx->base.is_jmp == DISAS_NORETURN);
15223         return;
15224     }
15225 
15226     if (ctx->hflags & MIPS_HFLAG_BMASK) {
15227         if (!(ctx->hflags & (MIPS_HFLAG_BDS16 | MIPS_HFLAG_BDS32 |
15228                              MIPS_HFLAG_FBNSLOT))) {
15229             /*
15230              * Force to generate branch as there is neither delay nor
15231              * forbidden slot.
15232              */
15233             is_slot = 1;
15234         }
15235         if ((ctx->hflags & MIPS_HFLAG_M16) &&
15236             (ctx->hflags & MIPS_HFLAG_FBNSLOT)) {
15237             /*
15238              * Force to generate branch as microMIPS R6 doesn't restrict
15239              * branches in the forbidden slot.
15240              */
15241             is_slot = 1;
15242         }
15243     }
15244     if (is_slot) {
15245         gen_branch(ctx, insn_bytes);
15246     }
15247     if (ctx->base.is_jmp == DISAS_SEMIHOST) {
15248         generate_exception_err(ctx, EXCP_SEMIHOST, insn_bytes);
15249     }
15250     ctx->base.pc_next += insn_bytes;
15251 
15252     if (ctx->base.is_jmp != DISAS_NEXT) {
15253         return;
15254     }
15255 
15256     /*
15257      * End the TB on (most) page crossings.
15258      * See mips_tr_init_disas_context about single-stepping a branch
15259      * together with its delay slot.
15260      */
15261     if (ctx->base.pc_next - ctx->page_start >= TARGET_PAGE_SIZE
15262         && !(tb_cflags(ctx->base.tb) & CF_SINGLE_STEP)) {
15263         ctx->base.is_jmp = DISAS_TOO_MANY;
15264     }
15265 }
15266 
15267 static void mips_tr_tb_stop(DisasContextBase *dcbase, CPUState *cs)
15268 {
15269     DisasContext *ctx = container_of(dcbase, DisasContext, base);
15270 
15271     switch (ctx->base.is_jmp) {
15272     case DISAS_STOP:
15273         gen_save_pc(ctx->base.pc_next);
15274         tcg_gen_lookup_and_goto_ptr();
15275         break;
15276     case DISAS_NEXT:
15277     case DISAS_TOO_MANY:
15278         save_cpu_state(ctx, 0);
15279         gen_goto_tb(ctx, 0, ctx->base.pc_next);
15280         break;
15281     case DISAS_EXIT:
15282         tcg_gen_exit_tb(NULL, 0);
15283         break;
15284     case DISAS_NORETURN:
15285         break;
15286     default:
15287         g_assert_not_reached();
15288     }
15289 }
15290 
15291 static const TranslatorOps mips_tr_ops = {
15292     .init_disas_context = mips_tr_init_disas_context,
15293     .tb_start           = mips_tr_tb_start,
15294     .insn_start         = mips_tr_insn_start,
15295     .translate_insn     = mips_tr_translate_insn,
15296     .tb_stop            = mips_tr_tb_stop,
15297 };
15298 
15299 void gen_intermediate_code(CPUState *cs, TranslationBlock *tb, int *max_insns,
15300                            vaddr pc, void *host_pc)
15301 {
15302     DisasContext ctx;
15303 
15304     translator_loop(cs, tb, max_insns, pc, host_pc, &mips_tr_ops, &ctx.base);
15305 }
15306 
15307 void mips_tcg_init(void)
15308 {
15309     cpu_gpr[0] = NULL;
15310     for (unsigned i = 1; i < 32; i++)
15311         cpu_gpr[i] = tcg_global_mem_new(tcg_env,
15312                                         offsetof(CPUMIPSState,
15313                                                  active_tc.gpr[i]),
15314                                         regnames[i]);
15315 #if defined(TARGET_MIPS64)
15316     cpu_gpr_hi[0] = NULL;
15317 
15318     for (unsigned i = 1; i < 32; i++) {
15319         g_autofree char *rname = g_strdup_printf("%s[hi]", regnames[i]);
15320 
15321         cpu_gpr_hi[i] = tcg_global_mem_new_i64(tcg_env,
15322                                                offsetof(CPUMIPSState,
15323                                                         active_tc.gpr_hi[i]),
15324                                                rname);
15325     }
15326 #endif /* !TARGET_MIPS64 */
15327     for (unsigned i = 0; i < 32; i++) {
15328         int off = offsetof(CPUMIPSState, active_fpu.fpr[i].wr.d[0]);
15329 
15330         fpu_f64[i] = tcg_global_mem_new_i64(tcg_env, off, fregnames[i]);
15331     }
15332     msa_translate_init();
15333     cpu_PC = tcg_global_mem_new(tcg_env,
15334                                 offsetof(CPUMIPSState, active_tc.PC), "PC");
15335     for (unsigned i = 0; i < MIPS_DSP_ACC; i++) {
15336         cpu_HI[i] = tcg_global_mem_new(tcg_env,
15337                                        offsetof(CPUMIPSState, active_tc.HI[i]),
15338                                        regnames_HI[i]);
15339         cpu_LO[i] = tcg_global_mem_new(tcg_env,
15340                                        offsetof(CPUMIPSState, active_tc.LO[i]),
15341                                        regnames_LO[i]);
15342     }
15343     cpu_dspctrl = tcg_global_mem_new(tcg_env,
15344                                      offsetof(CPUMIPSState,
15345                                               active_tc.DSPControl),
15346                                      "DSPControl");
15347     bcond = tcg_global_mem_new(tcg_env,
15348                                offsetof(CPUMIPSState, bcond), "bcond");
15349     btarget = tcg_global_mem_new(tcg_env,
15350                                  offsetof(CPUMIPSState, btarget), "btarget");
15351     hflags = tcg_global_mem_new_i32(tcg_env,
15352                                     offsetof(CPUMIPSState, hflags), "hflags");
15353 
15354     fpu_fcr0 = tcg_global_mem_new_i32(tcg_env,
15355                                       offsetof(CPUMIPSState, active_fpu.fcr0),
15356                                       "fcr0");
15357     fpu_fcr31 = tcg_global_mem_new_i32(tcg_env,
15358                                        offsetof(CPUMIPSState, active_fpu.fcr31),
15359                                        "fcr31");
15360     cpu_lladdr = tcg_global_mem_new(tcg_env, offsetof(CPUMIPSState, lladdr),
15361                                     "lladdr");
15362     cpu_llval = tcg_global_mem_new(tcg_env, offsetof(CPUMIPSState, llval),
15363                                    "llval");
15364 
15365     if (TARGET_LONG_BITS == 32) {
15366         mxu_translate_init();
15367     }
15368 }
15369 
15370 void mips_restore_state_to_opc(CPUState *cs,
15371                                const TranslationBlock *tb,
15372                                const uint64_t *data)
15373 {
15374     CPUMIPSState *env = cpu_env(cs);
15375 
15376     env->active_tc.PC = data[0];
15377     env->hflags &= ~MIPS_HFLAG_BMASK;
15378     env->hflags |= data[1];
15379     switch (env->hflags & MIPS_HFLAG_BMASK_BASE) {
15380     case MIPS_HFLAG_BR:
15381         break;
15382     case MIPS_HFLAG_BC:
15383     case MIPS_HFLAG_BL:
15384     case MIPS_HFLAG_B:
15385         env->btarget = data[2];
15386         break;
15387     }
15388 }
15389