SH4: Convert remaining non-fp ops to TCG
[qemu] / target-sh4 / translate.c
1 /*
2  *  SH4 translation
3  *
4  *  Copyright (c) 2005 Samuel Tardieu
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  */
20 #include <stdarg.h>
21 #include <stdlib.h>
22 #include <stdio.h>
23 #include <string.h>
24 #include <inttypes.h>
25 #include <assert.h>
26
27 #define DEBUG_DISAS
28 #define SH4_DEBUG_DISAS
29 //#define SH4_SINGLE_STEP
30
31 #include "cpu.h"
32 #include "exec-all.h"
33 #include "disas.h"
34 #include "helper.h"
35 #include "tcg-op.h"
36 #include "qemu-common.h"
37
38 typedef struct DisasContext {
39     struct TranslationBlock *tb;
40     target_ulong pc;
41     uint32_t sr;
42     uint32_t fpscr;
43     uint16_t opcode;
44     uint32_t flags;
45     int bstate;
46     int memidx;
47     uint32_t delayed_pc;
48     int singlestep_enabled;
49 } DisasContext;
50
51 enum {
52     BS_NONE     = 0, /* We go out of the TB without reaching a branch or an
53                       * exception condition
54                       */
55     BS_STOP     = 1, /* We want to stop translation for any reason */
56     BS_BRANCH   = 2, /* We reached a branch condition     */
57     BS_EXCP     = 3, /* We reached an exception condition */
58 };
59
60 /* global register indexes */
61 static TCGv cpu_env;
62 static TCGv cpu_gregs[24];
63 static TCGv cpu_pc, cpu_sr, cpu_ssr, cpu_spc, cpu_gbr;
64 static TCGv cpu_vbr, cpu_sgr, cpu_dbr, cpu_mach, cpu_macl;
65 static TCGv cpu_pr, cpu_fpscr, cpu_fpul, cpu_flags;
66
67 /* internal register indexes */
68 static TCGv cpu_flags, cpu_delayed_pc;
69
70 /* dyngen register indexes */
71 static TCGv cpu_T[2];
72
73 #include "gen-icount.h"
74
75 static void sh4_translate_init(void)
76 {
77     int i;
78     static int done_init = 0;
79     static const char * const gregnames[24] = {
80         "R0_BANK0", "R1_BANK0", "R2_BANK0", "R3_BANK0",
81         "R4_BANK0", "R5_BANK0", "R6_BANK0", "R7_BANK0",
82         "R8", "R9", "R10", "R11", "R12", "R13", "R14", "R15",
83         "R0_BANK1", "R1_BANK1", "R2_BANK1", "R3_BANK1",
84         "R4_BANK1", "R5_BANK1", "R6_BANK1", "R7_BANK1"
85     };
86
87     if (done_init)
88         return;
89
90     cpu_env = tcg_global_reg_new(TCG_TYPE_PTR, TCG_AREG0, "env");
91     cpu_T[0] = tcg_global_reg_new(TCG_TYPE_I32, TCG_AREG1, "T0");
92     cpu_T[1] = tcg_global_reg_new(TCG_TYPE_I32, TCG_AREG2, "T1");
93
94     for (i = 0; i < 24; i++)
95         cpu_gregs[i] = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
96                                           offsetof(CPUState, gregs[i]),
97                                           gregnames[i]);
98
99     cpu_pc = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
100                                 offsetof(CPUState, pc), "PC");
101     cpu_sr = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
102                                 offsetof(CPUState, sr), "SR");
103     cpu_ssr = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
104                                  offsetof(CPUState, ssr), "SSR");
105     cpu_spc = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
106                                  offsetof(CPUState, spc), "SPC");
107     cpu_gbr = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
108                                  offsetof(CPUState, gbr), "GBR");
109     cpu_vbr = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
110                                  offsetof(CPUState, vbr), "VBR");
111     cpu_sgr = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
112                                  offsetof(CPUState, sgr), "SGR");
113     cpu_dbr = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
114                                  offsetof(CPUState, dbr), "DBR");
115     cpu_mach = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
116                                   offsetof(CPUState, mach), "MACH");
117     cpu_macl = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
118                                   offsetof(CPUState, macl), "MACL");
119     cpu_pr = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
120                                 offsetof(CPUState, pr), "PR");
121     cpu_fpscr = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
122                                    offsetof(CPUState, fpscr), "FPSCR");
123     cpu_fpul = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
124                                   offsetof(CPUState, fpul), "FPUL");
125
126     cpu_flags = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
127                                    offsetof(CPUState, flags), "_flags_");
128     cpu_delayed_pc = tcg_global_mem_new(TCG_TYPE_I32, TCG_AREG0,
129                                         offsetof(CPUState, delayed_pc),
130                                         "_delayed_pc_");
131
132     /* register helpers */
133 #undef DEF_HELPER
134 #define DEF_HELPER(ret, name, params) tcg_register_helper(name, #name);
135 #include "helper.h"
136
137     done_init = 1;
138 }
139
140 #ifdef CONFIG_USER_ONLY
141
142 #define GEN_OP_LD(width, reg) \
143   void gen_op_ld##width##_T0_##reg (DisasContext *ctx) { \
144     gen_op_ld##width##_T0_##reg##_raw(); \
145   }
146 #define GEN_OP_ST(width, reg) \
147   void gen_op_st##width##_##reg##_T1 (DisasContext *ctx) { \
148     gen_op_st##width##_##reg##_T1_raw(); \
149   }
150
151 #else
152
153 #define GEN_OP_LD(width, reg) \
154   void gen_op_ld##width##_T0_##reg (DisasContext *ctx) { \
155     if (ctx->memidx) gen_op_ld##width##_T0_##reg##_kernel(); \
156     else gen_op_ld##width##_T0_##reg##_user();\
157   }
158 #define GEN_OP_ST(width, reg) \
159   void gen_op_st##width##_##reg##_T1 (DisasContext *ctx) { \
160     if (ctx->memidx) gen_op_st##width##_##reg##_T1_kernel(); \
161     else gen_op_st##width##_##reg##_T1_user();\
162   }
163
164 #endif
165
166 GEN_OP_LD(fl, FT0)
167 GEN_OP_ST(fl, FT0)
168 GEN_OP_LD(fq, DT0)
169 GEN_OP_ST(fq, DT0)
170
171 void cpu_dump_state(CPUState * env, FILE * f,
172                     int (*cpu_fprintf) (FILE * f, const char *fmt, ...),
173                     int flags)
174 {
175     int i;
176     cpu_fprintf(f, "pc=0x%08x sr=0x%08x pr=0x%08x fpscr=0x%08x\n",
177                 env->pc, env->sr, env->pr, env->fpscr);
178     cpu_fprintf(f, "spc=0x%08x ssr=0x%08x gbr=0x%08x vbr=0x%08x\n",
179                 env->spc, env->ssr, env->gbr, env->vbr);
180     cpu_fprintf(f, "sgr=0x%08x dbr=0x%08x delayed_pc=0x%08x fpul=0x%08x\n",
181                 env->sgr, env->dbr, env->delayed_pc, env->fpul);
182     for (i = 0; i < 24; i += 4) {
183         cpu_fprintf(f, "r%d=0x%08x r%d=0x%08x r%d=0x%08x r%d=0x%08x\n",
184                     i, env->gregs[i], i + 1, env->gregs[i + 1],
185                     i + 2, env->gregs[i + 2], i + 3, env->gregs[i + 3]);
186     }
187     if (env->flags & DELAY_SLOT) {
188         cpu_fprintf(f, "in delay slot (delayed_pc=0x%08x)\n",
189                     env->delayed_pc);
190     } else if (env->flags & DELAY_SLOT_CONDITIONAL) {
191         cpu_fprintf(f, "in conditional delay slot (delayed_pc=0x%08x)\n",
192                     env->delayed_pc);
193     }
194 }
195
196 void cpu_sh4_reset(CPUSH4State * env)
197 {
198 #if defined(CONFIG_USER_ONLY)
199     env->sr = SR_FD;            /* FD - kernel does lazy fpu context switch */
200 #else
201     env->sr = 0x700000F0;       /* MD, RB, BL, I3-I0 */
202 #endif
203     env->vbr = 0;
204     env->pc = 0xA0000000;
205 #if defined(CONFIG_USER_ONLY)
206     env->fpscr = FPSCR_PR; /* value for userspace according to the kernel */
207     set_float_rounding_mode(float_round_nearest_even, &env->fp_status); /* ?! */
208 #else
209     env->fpscr = 0x00040001; /* CPU reset value according to SH4 manual */
210     set_float_rounding_mode(float_round_to_zero, &env->fp_status);
211 #endif
212     env->mmucr = 0;
213 }
214
215 CPUSH4State *cpu_sh4_init(const char *cpu_model)
216 {
217     CPUSH4State *env;
218
219     env = qemu_mallocz(sizeof(CPUSH4State));
220     if (!env)
221         return NULL;
222     cpu_exec_init(env);
223     sh4_translate_init();
224     cpu_sh4_reset(env);
225     tlb_flush(env, 1);
226     return env;
227 }
228
229 static void gen_goto_tb(DisasContext * ctx, int n, target_ulong dest)
230 {
231     TranslationBlock *tb;
232     tb = ctx->tb;
233
234     if ((tb->pc & TARGET_PAGE_MASK) == (dest & TARGET_PAGE_MASK) &&
235         !ctx->singlestep_enabled) {
236         /* Use a direct jump if in same page and singlestep not enabled */
237         tcg_gen_goto_tb(n);
238         tcg_gen_movi_i32(cpu_pc, dest);
239         tcg_gen_exit_tb((long) tb + n);
240     } else {
241         tcg_gen_movi_i32(cpu_pc, dest);
242         if (ctx->singlestep_enabled)
243             tcg_gen_helper_0_0(helper_debug);
244         tcg_gen_exit_tb(0);
245     }
246 }
247
248 static void gen_jump(DisasContext * ctx)
249 {
250     if (ctx->delayed_pc == (uint32_t) - 1) {
251         /* Target is not statically known, it comes necessarily from a
252            delayed jump as immediate jump are conditinal jumps */
253         tcg_gen_mov_i32(cpu_pc, cpu_delayed_pc);
254         if (ctx->singlestep_enabled)
255             tcg_gen_helper_0_0(helper_debug);
256         tcg_gen_exit_tb(0);
257     } else {
258         gen_goto_tb(ctx, 0, ctx->delayed_pc);
259     }
260 }
261
262 static inline void gen_branch_slot(uint32_t delayed_pc, int t)
263 {
264     int label = gen_new_label();
265     tcg_gen_movi_i32(cpu_delayed_pc, delayed_pc);
266     tcg_gen_andi_i32(cpu_T[0], cpu_sr, SR_T);
267     tcg_gen_brcondi_i32(TCG_COND_NE, cpu_T[0], t ? SR_T : 0, label);
268     tcg_gen_ori_i32(cpu_flags, cpu_flags, DELAY_SLOT_TRUE);
269     gen_set_label(label);
270 }
271
272 /* Immediate conditional jump (bt or bf) */
273 static void gen_conditional_jump(DisasContext * ctx,
274                                  target_ulong ift, target_ulong ifnott)
275 {
276     int l1;
277
278     l1 = gen_new_label();
279     tcg_gen_andi_i32(cpu_T[0], cpu_sr, SR_T);
280     tcg_gen_brcondi_i32(TCG_COND_EQ, cpu_T[0], SR_T, l1);
281     gen_goto_tb(ctx, 0, ifnott);
282     gen_set_label(l1);
283     gen_goto_tb(ctx, 1, ift);
284 }
285
286 /* Delayed conditional jump (bt or bf) */
287 static void gen_delayed_conditional_jump(DisasContext * ctx)
288 {
289     int l1;
290
291     l1 = gen_new_label();
292     tcg_gen_andi_i32(cpu_T[0], cpu_flags, DELAY_SLOT_TRUE);
293     tcg_gen_brcondi_i32(TCG_COND_EQ, cpu_T[0], DELAY_SLOT_TRUE, l1);
294     gen_goto_tb(ctx, 1, ctx->pc + 2);
295     gen_set_label(l1);
296     tcg_gen_andi_i32(cpu_flags, cpu_flags, ~DELAY_SLOT_TRUE);
297     gen_jump(ctx);
298 }
299
300 static inline void gen_set_t(void)
301 {
302     tcg_gen_ori_i32(cpu_sr, cpu_sr, SR_T);
303 }
304
305 static inline void gen_clr_t(void)
306 {
307     tcg_gen_andi_i32(cpu_sr, cpu_sr, ~SR_T);
308 }
309
310 static inline void gen_cmp(int cond, TCGv t0, TCGv t1)
311 {
312     int label1 = gen_new_label();
313     int label2 = gen_new_label();
314     tcg_gen_brcond_i32(cond, t1, t0, label1);
315     gen_clr_t();
316     tcg_gen_br(label2);
317     gen_set_label(label1);
318     gen_set_t();
319     gen_set_label(label2);
320 }
321
322 static inline void gen_cmp_imm(int cond, TCGv t0, int32_t imm)
323 {
324     int label1 = gen_new_label();
325     int label2 = gen_new_label();
326     tcg_gen_brcondi_i32(cond, t0, imm, label1);
327     gen_clr_t();
328     tcg_gen_br(label2);
329     gen_set_label(label1);
330     gen_set_t();
331     gen_set_label(label2);
332 }
333
334 static inline void gen_store_flags(uint32_t flags)
335 {
336     tcg_gen_andi_i32(cpu_flags, cpu_flags, DELAY_SLOT_TRUE);
337     tcg_gen_ori_i32(cpu_flags, cpu_flags, flags);
338 }
339
340 static inline void gen_copy_bit_i32(TCGv t0, int p0, TCGv t1, int p1)
341 {
342     TCGv tmp = tcg_temp_new(TCG_TYPE_I32);
343
344     p0 &= 0x1f;
345     p1 &= 0x1f;
346
347     tcg_gen_andi_i32(tmp, t1, (1 << p1));
348     tcg_gen_andi_i32(t0, t0, ~(1 << p0));
349     if (p0 < p1)
350         tcg_gen_shri_i32(tmp, tmp, p1 - p0);
351     else if (p0 > p1)
352         tcg_gen_shli_i32(tmp, tmp, p0 - p1);
353     tcg_gen_or_i32(t0, t0, tmp);
354
355     tcg_temp_free(tmp);
356 }
357
358 #define B3_0 (ctx->opcode & 0xf)
359 #define B6_4 ((ctx->opcode >> 4) & 0x7)
360 #define B7_4 ((ctx->opcode >> 4) & 0xf)
361 #define B7_0 (ctx->opcode & 0xff)
362 #define B7_0s ((int32_t) (int8_t) (ctx->opcode & 0xff))
363 #define B11_0s (ctx->opcode & 0x800 ? 0xfffff000 | (ctx->opcode & 0xfff) : \
364   (ctx->opcode & 0xfff))
365 #define B11_8 ((ctx->opcode >> 8) & 0xf)
366 #define B15_12 ((ctx->opcode >> 12) & 0xf)
367
368 #define REG(x) ((x) < 8 && (ctx->sr & (SR_MD | SR_RB)) == (SR_MD | SR_RB) ? \
369                 (x) + 16 : (x))
370
371 #define ALTREG(x) ((x) < 8 && (ctx->sr & (SR_MD | SR_RB)) != (SR_MD | SR_RB) \
372                 ? (x) + 16 : (x))
373
374 #define FREG(x) (ctx->fpscr & FPSCR_FR ? (x) ^ 0x10 : (x))
375 #define XHACK(x) ((((x) & 1 ) << 4) | ((x) & 0xe))
376 #define XREG(x) (ctx->fpscr & FPSCR_FR ? XHACK(x) ^ 0x10 : XHACK(x))
377 #define DREG(x) FREG(x) /* Assumes lsb of (x) is always 0 */
378
379 #define CHECK_NOT_DELAY_SLOT \
380   if (ctx->flags & (DELAY_SLOT | DELAY_SLOT_CONDITIONAL)) \
381   {tcg_gen_helper_0_0(helper_raise_slot_illegal_instruction); ctx->bstate = BS_EXCP; \
382    return;}
383
384 void _decode_opc(DisasContext * ctx)
385 {
386 #if 0
387     fprintf(stderr, "Translating opcode 0x%04x\n", ctx->opcode);
388 #endif
389     switch (ctx->opcode) {
390     case 0x0019:                /* div0u */
391         tcg_gen_andi_i32(cpu_sr, cpu_sr, ~(SR_M | SR_Q | SR_T));
392         return;
393     case 0x000b:                /* rts */
394         CHECK_NOT_DELAY_SLOT
395         tcg_gen_mov_i32(cpu_delayed_pc, cpu_pr);
396         ctx->flags |= DELAY_SLOT;
397         ctx->delayed_pc = (uint32_t) - 1;
398         return;
399     case 0x0028:                /* clrmac */
400         tcg_gen_movi_i32(cpu_mach, 0);
401         tcg_gen_movi_i32(cpu_macl, 0);
402         return;
403     case 0x0048:                /* clrs */
404         tcg_gen_andi_i32(cpu_sr, cpu_sr, ~SR_S);
405         return;
406     case 0x0008:                /* clrt */
407         gen_clr_t();
408         return;
409     case 0x0038:                /* ldtlb */
410 #if defined(CONFIG_USER_ONLY)
411         assert(0);              /* XXXXX */
412 #else
413         tcg_gen_helper_0_0(helper_ldtlb);
414 #endif
415         return;
416     case 0x002b:                /* rte */
417         CHECK_NOT_DELAY_SLOT
418         tcg_gen_mov_i32(cpu_sr, cpu_ssr);
419         tcg_gen_mov_i32(cpu_delayed_pc, cpu_spc);
420         ctx->flags |= DELAY_SLOT;
421         ctx->delayed_pc = (uint32_t) - 1;
422         return;
423     case 0x0058:                /* sets */
424         tcg_gen_ori_i32(cpu_sr, cpu_sr, SR_S);
425         return;
426     case 0x0018:                /* sett */
427         gen_set_t();
428         return;
429     case 0xfbfd:                /* frchg */
430         tcg_gen_xori_i32(cpu_fpscr, cpu_fpscr, FPSCR_FR);
431         ctx->bstate = BS_STOP;
432         return;
433     case 0xf3fd:                /* fschg */
434         tcg_gen_xori_i32(cpu_fpscr, cpu_fpscr, FPSCR_SZ);
435         ctx->bstate = BS_STOP;
436         return;
437     case 0x0009:                /* nop */
438         return;
439     case 0x001b:                /* sleep */
440         if (ctx->memidx) {
441                 tcg_gen_helper_0_0(helper_sleep);
442         } else {
443                 tcg_gen_helper_0_0(helper_raise_illegal_instruction);
444                 ctx->bstate = BS_EXCP;
445         }
446         return;
447     }
448
449     switch (ctx->opcode & 0xf000) {
450     case 0x1000:                /* mov.l Rm,@(disp,Rn) */
451         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
452         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
453         tcg_gen_addi_i32(cpu_T[1], cpu_T[1], B3_0 * 4);
454         tcg_gen_qemu_st32(cpu_T[0], cpu_T[1], ctx->memidx);
455         return;
456     case 0x5000:                /* mov.l @(disp,Rm),Rn */
457         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
458         tcg_gen_addi_i32(cpu_T[0], cpu_T[0], B3_0 * 4);
459         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
460         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
461         return;
462     case 0xe000:                /* mov #imm,Rn */
463         tcg_gen_movi_i32(cpu_gregs[REG(B11_8)], B7_0s);
464         return;
465     case 0x9000:                /* mov.w @(disp,PC),Rn */
466         tcg_gen_movi_i32(cpu_T[0], ctx->pc + 4 + B7_0 * 2);
467         tcg_gen_qemu_ld16s(cpu_T[0], cpu_T[0], ctx->memidx);
468         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
469         return;
470     case 0xd000:                /* mov.l @(disp,PC),Rn */
471         tcg_gen_movi_i32(cpu_T[0], (ctx->pc + 4 + B7_0 * 4) & ~3);
472         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
473         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
474         return;
475     case 0x7000:                /* add #imm,Rn */
476         tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], B7_0s);
477         return;
478     case 0xa000:                /* bra disp */
479         CHECK_NOT_DELAY_SLOT
480         ctx->delayed_pc = ctx->pc + 4 + B11_0s * 2;
481         tcg_gen_movi_i32(cpu_delayed_pc, ctx->delayed_pc);
482         ctx->flags |= DELAY_SLOT;
483         return;
484     case 0xb000:                /* bsr disp */
485         CHECK_NOT_DELAY_SLOT
486         tcg_gen_movi_i32(cpu_pr, ctx->pc + 4);
487         ctx->delayed_pc = ctx->pc + 4 + B11_0s * 2;
488         tcg_gen_movi_i32(cpu_delayed_pc, ctx->delayed_pc);
489         ctx->flags |= DELAY_SLOT;
490         return;
491     }
492
493     switch (ctx->opcode & 0xf00f) {
494     case 0x6003:                /* mov Rm,Rn */
495         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
496         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
497         return;
498     case 0x2000:                /* mov.b Rm,@Rn */
499         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
500         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
501         tcg_gen_qemu_st8(cpu_T[0], cpu_T[1], ctx->memidx);
502         return;
503     case 0x2001:                /* mov.w Rm,@Rn */
504         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
505         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
506         tcg_gen_qemu_st16(cpu_T[0], cpu_T[1], ctx->memidx);
507         return;
508     case 0x2002:                /* mov.l Rm,@Rn */
509         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
510         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
511         tcg_gen_qemu_st32(cpu_T[0], cpu_T[1], ctx->memidx);
512         return;
513     case 0x6000:                /* mov.b @Rm,Rn */
514         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
515         tcg_gen_qemu_ld8s(cpu_T[0], cpu_T[0], ctx->memidx);
516         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
517         return;
518     case 0x6001:                /* mov.w @Rm,Rn */
519         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
520         tcg_gen_qemu_ld16s(cpu_T[0], cpu_T[0], ctx->memidx);
521         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
522         return;
523     case 0x6002:                /* mov.l @Rm,Rn */
524         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
525         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
526         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
527         return;
528     case 0x2004:                /* mov.b Rm,@-Rn */
529         tcg_gen_subi_i32(cpu_T[1], cpu_gregs[REG(B11_8)], 1);
530         tcg_gen_qemu_st8(cpu_gregs[REG(B7_4)], cpu_T[1], ctx->memidx);  /* might cause re-execution */
531         tcg_gen_subi_i32(cpu_gregs[REG(B11_8)],
532                          cpu_gregs[REG(B11_8)], 1);                     /* modify register status */
533         return;
534     case 0x2005:                /* mov.w Rm,@-Rn */
535         tcg_gen_subi_i32(cpu_T[1], cpu_gregs[REG(B11_8)], 2);
536         tcg_gen_qemu_st16(cpu_gregs[REG(B7_4)], cpu_T[1], ctx->memidx);
537         tcg_gen_subi_i32(cpu_gregs[REG(B11_8)],
538                          cpu_gregs[REG(B11_8)], 2);
539         return;
540     case 0x2006:                /* mov.l Rm,@-Rn */
541         tcg_gen_subi_i32(cpu_T[1], cpu_gregs[REG(B11_8)], 4);
542         tcg_gen_qemu_st32(cpu_gregs[REG(B7_4)], cpu_T[1], ctx->memidx);
543         tcg_gen_subi_i32(cpu_gregs[REG(B11_8)],
544                          cpu_gregs[REG(B11_8)], 4);
545         return;
546     case 0x6004:                /* mov.b @Rm+,Rn */
547         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
548         tcg_gen_qemu_ld8s(cpu_T[0], cpu_T[0], ctx->memidx);
549         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
550         if ( B11_8 != B7_4 )
551                 tcg_gen_addi_i32(cpu_gregs[REG(B7_4)],
552                                  cpu_gregs[REG(B7_4)], 1);
553         return;
554     case 0x6005:                /* mov.w @Rm+,Rn */
555         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
556         tcg_gen_qemu_ld16s(cpu_T[0], cpu_T[0], ctx->memidx);
557         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
558         if ( B11_8 != B7_4 )
559                 tcg_gen_addi_i32(cpu_gregs[REG(B7_4)],
560                                  cpu_gregs[REG(B7_4)], 2);
561         return;
562     case 0x6006:                /* mov.l @Rm+,Rn */
563         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
564         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
565         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
566         if ( B11_8 != B7_4 )
567                 tcg_gen_addi_i32(cpu_gregs[REG(B7_4)],
568                                  cpu_gregs[REG(B7_4)], 4);
569         return;
570     case 0x0004:                /* mov.b Rm,@(R0,Rn) */
571         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
572         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
573         tcg_gen_add_i32(cpu_T[1], cpu_T[1], cpu_gregs[REG(0)]);
574         tcg_gen_qemu_st8(cpu_T[0], cpu_T[1], ctx->memidx);
575         return;
576     case 0x0005:                /* mov.w Rm,@(R0,Rn) */
577         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
578         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
579         tcg_gen_add_i32(cpu_T[1], cpu_T[1], cpu_gregs[REG(0)]);
580         tcg_gen_qemu_st16(cpu_T[0], cpu_T[1], ctx->memidx);
581         return;
582     case 0x0006:                /* mov.l Rm,@(R0,Rn) */
583         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
584         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
585         tcg_gen_add_i32(cpu_T[1], cpu_T[1], cpu_gregs[REG(0)]);
586         tcg_gen_qemu_st32(cpu_T[0], cpu_T[1], ctx->memidx);
587         return;
588     case 0x000c:                /* mov.b @(R0,Rm),Rn */
589         tcg_gen_add_i32(cpu_T[0], cpu_gregs[REG(B7_4)], cpu_gregs[REG(0)]);
590         tcg_gen_qemu_ld8s(cpu_T[0], cpu_T[0], ctx->memidx);
591         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
592         return;
593     case 0x000d:                /* mov.w @(R0,Rm),Rn */
594         tcg_gen_add_i32(cpu_T[0], cpu_gregs[REG(B7_4)], cpu_gregs[REG(0)]);
595         tcg_gen_qemu_ld16s(cpu_T[0], cpu_T[0], ctx->memidx);
596         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
597         return;
598     case 0x000e:                /* mov.l @(R0,Rm),Rn */
599         tcg_gen_add_i32(cpu_T[0], cpu_gregs[REG(B7_4)], cpu_gregs[REG(0)]);
600         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
601         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
602         return;
603     case 0x6008:                /* swap.b Rm,Rn */
604         tcg_gen_andi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)], 0xffff0000);
605         tcg_gen_andi_i32(cpu_T[0], cpu_gregs[REG(B7_4)], 0xff);
606         tcg_gen_shli_i32(cpu_T[0], cpu_T[0], 8);
607         tcg_gen_or_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_T[0]);
608         tcg_gen_shri_i32(cpu_T[0], cpu_gregs[REG(B7_4)], 8);
609         tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0xff);
610         tcg_gen_or_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_T[0]);
611         return;
612     case 0x6009:                /* swap.w Rm,Rn */
613         tcg_gen_andi_i32(cpu_T[0], cpu_gregs[REG(B7_4)], 0xffff);
614         tcg_gen_shli_i32(cpu_T[0], cpu_T[0], 16);
615         tcg_gen_shri_i32(cpu_T[1], cpu_gregs[REG(B7_4)], 16);
616         tcg_gen_andi_i32(cpu_T[1], cpu_T[1], 0xffff);
617         tcg_gen_or_i32(cpu_gregs[REG(B11_8)], cpu_T[0], cpu_T[1]);
618         return;
619     case 0x200d:                /* xtrct Rm,Rn */
620         tcg_gen_andi_i32(cpu_T[0], cpu_gregs[REG(B7_4)], 0xffff);
621         tcg_gen_shli_i32(cpu_T[0], cpu_T[0], 16);
622         tcg_gen_shri_i32(cpu_T[1], cpu_gregs[REG(B11_8)], 16);
623         tcg_gen_andi_i32(cpu_T[1], cpu_T[1], 0xffff);
624         tcg_gen_or_i32(cpu_gregs[REG(B11_8)], cpu_T[0], cpu_T[1]);
625         return;
626     case 0x300c:                /* add Rm,Rn */
627         tcg_gen_add_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)]);
628         return;
629     case 0x300e:                /* addc Rm,Rn */
630         tcg_gen_helper_1_2(helper_addc, cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)], cpu_gregs[REG(B11_8)]);
631         return;
632     case 0x300f:                /* addv Rm,Rn */
633         tcg_gen_helper_1_2(helper_addv, cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)], cpu_gregs[REG(B11_8)]);
634         return;
635     case 0x2009:                /* and Rm,Rn */
636         tcg_gen_and_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)]);
637         return;
638     case 0x3000:                /* cmp/eq Rm,Rn */
639         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
640         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
641         gen_cmp(TCG_COND_EQ, cpu_T[0], cpu_T[1]);
642         return;
643     case 0x3003:                /* cmp/ge Rm,Rn */
644         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
645         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
646         gen_cmp(TCG_COND_GE, cpu_T[0], cpu_T[1]);
647         return;
648     case 0x3007:                /* cmp/gt Rm,Rn */
649         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
650         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
651         gen_cmp(TCG_COND_GT, cpu_T[0], cpu_T[1]);
652         return;
653     case 0x3006:                /* cmp/hi Rm,Rn */
654         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
655         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
656         gen_cmp(TCG_COND_GTU, cpu_T[0], cpu_T[1]);
657         return;
658     case 0x3002:                /* cmp/hs Rm,Rn */
659         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
660         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
661         gen_cmp(TCG_COND_GEU, cpu_T[0], cpu_T[1]);
662         return;
663     case 0x200c:                /* cmp/str Rm,Rn */
664         {
665             int label1 = gen_new_label();
666             int label2 = gen_new_label();
667             tcg_gen_xor_i32(cpu_T[0], cpu_gregs[REG(B7_4)], cpu_gregs[REG(B11_8)]);
668             tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0xff000000);
669             tcg_gen_brcondi_i32(TCG_COND_EQ, cpu_T[0], 0, label1);
670             tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0x00ff0000);
671             tcg_gen_brcondi_i32(TCG_COND_EQ, cpu_T[0], 0, label1);
672             tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0x0000ff00);
673             tcg_gen_brcondi_i32(TCG_COND_EQ, cpu_T[0], 0, label1);
674             tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0x000000ff);
675             tcg_gen_brcondi_i32(TCG_COND_EQ, cpu_T[0], 0, label1);
676             tcg_gen_andi_i32(cpu_sr, cpu_sr, ~SR_T);
677             tcg_gen_br(label2);
678             gen_set_label(label1);
679             tcg_gen_ori_i32(cpu_sr, cpu_sr, SR_T);
680             gen_set_label(label2);
681         }
682         return;
683     case 0x2007:                /* div0s Rm,Rn */
684         gen_copy_bit_i32(cpu_sr, 8, cpu_gregs[REG(B11_8)], 31); /* SR_Q */
685         gen_copy_bit_i32(cpu_sr, 9, cpu_gregs[REG(B7_4)], 31);  /* SR_M */
686         tcg_gen_xor_i32(cpu_T[0], cpu_gregs[REG(B7_4)], cpu_gregs[REG(B11_8)]);
687         gen_copy_bit_i32(cpu_sr, 0, cpu_T[0], 31);              /* SR_T */
688         return;
689     case 0x3004:                /* div1 Rm,Rn */
690         tcg_gen_helper_1_2(helper_div1, cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)], cpu_gregs[REG(B11_8)]);
691         return;
692     case 0x300d:                /* dmuls.l Rm,Rn */
693         {
694             TCGv tmp1 = tcg_temp_new(TCG_TYPE_I64);
695             TCGv tmp2 = tcg_temp_new(TCG_TYPE_I64);
696
697             tcg_gen_ext_i32_i64(tmp1, cpu_gregs[REG(B7_4)]);
698             tcg_gen_ext_i32_i64(tmp2, cpu_gregs[REG(B11_8)]);
699             tcg_gen_mul_i64(tmp1, tmp1, tmp2);
700             tcg_gen_trunc_i64_i32(cpu_macl, tmp1);
701             tcg_gen_shri_i64(tmp1, tmp1, 32);
702             tcg_gen_trunc_i64_i32(cpu_mach, tmp1);
703
704             tcg_temp_free(tmp1);
705             tcg_temp_free(tmp2);
706         }
707         return;
708     case 0x3005:                /* dmulu.l Rm,Rn */
709         {
710             TCGv tmp1 = tcg_temp_new(TCG_TYPE_I64);
711             TCGv tmp2 = tcg_temp_new(TCG_TYPE_I64);
712
713             tcg_gen_extu_i32_i64(tmp1, cpu_gregs[REG(B7_4)]);
714             tcg_gen_extu_i32_i64(tmp2, cpu_gregs[REG(B11_8)]);
715             tcg_gen_mul_i64(tmp1, tmp1, tmp2);
716             tcg_gen_trunc_i64_i32(cpu_macl, tmp1);
717             tcg_gen_shri_i64(tmp1, tmp1, 32);
718             tcg_gen_trunc_i64_i32(cpu_mach, tmp1);
719
720             tcg_temp_free(tmp1);
721             tcg_temp_free(tmp2);
722         }
723         return;
724     case 0x600e:                /* exts.b Rm,Rn */
725         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
726         tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0xff);
727         tcg_gen_ext8s_i32(cpu_T[0], cpu_T[0]);
728         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
729         return;
730     case 0x600f:                /* exts.w Rm,Rn */
731         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
732         tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0xffff);
733         tcg_gen_ext16s_i32(cpu_T[0], cpu_T[0]);
734         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
735         return;
736     case 0x600c:                /* extu.b Rm,Rn */
737         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
738         tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0xff);
739         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
740         return;
741     case 0x600d:                /* extu.w Rm,Rn */
742         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
743         tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0xffff);
744         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
745         return;
746     case 0x000f:                /* mac.l @Rm+,@Rn+ */
747         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
748         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
749         tcg_gen_mov_i32(cpu_T[1], cpu_T[0]);
750         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
751         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
752         tcg_gen_helper_0_2(helper_macl, cpu_T[0], cpu_T[1]);
753         tcg_gen_addi_i32(cpu_gregs[REG(B7_4)], cpu_gregs[REG(B7_4)], 4);
754         tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
755         return;
756     case 0x400f:                /* mac.w @Rm+,@Rn+ */
757         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
758         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
759         tcg_gen_mov_i32(cpu_T[1], cpu_T[0]);
760         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
761         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
762         tcg_gen_helper_0_2(helper_macw, cpu_T[0], cpu_T[1]);
763         tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 2);
764         tcg_gen_addi_i32(cpu_gregs[REG(B7_4)], cpu_gregs[REG(B7_4)], 2);
765         return;
766     case 0x0007:                /* mul.l Rm,Rn */
767         tcg_gen_mul_i32(cpu_macl, cpu_gregs[REG(B7_4)], cpu_gregs[REG(B11_8)]);
768         return;
769     case 0x200f:                /* muls.w Rm,Rn */
770         tcg_gen_ext16s_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
771         tcg_gen_ext16s_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
772         tcg_gen_mul_i32(cpu_macl, cpu_T[0], cpu_T[1]);
773         return;
774     case 0x200e:                /* mulu.w Rm,Rn */
775         tcg_gen_ext16u_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
776         tcg_gen_ext16u_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
777         tcg_gen_mul_i32(cpu_macl, cpu_T[0], cpu_T[1]);
778         return;
779     case 0x600b:                /* neg Rm,Rn */
780         tcg_gen_neg_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)]);
781         return;
782     case 0x600a:                /* negc Rm,Rn */
783         tcg_gen_helper_1_1(helper_negc, cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)]);
784         return;
785     case 0x6007:                /* not Rm,Rn */
786         tcg_gen_not_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)]);
787         return;
788     case 0x200b:                /* or Rm,Rn */
789         tcg_gen_or_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)]);
790         return;
791     case 0x400c:                /* shad Rm,Rn */
792         {
793             int label1 = gen_new_label();
794             int label2 = gen_new_label();
795             int label3 = gen_new_label();
796             int label4 = gen_new_label();
797             tcg_gen_brcondi_i32(TCG_COND_LT, cpu_gregs[REG(B7_4)], 0, label1);
798             /* Rm positive, shift to the left */
799             tcg_gen_andi_i32(cpu_T[0], cpu_gregs[REG(B7_4)], 0x1f);
800             tcg_gen_shl_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_T[0]);
801             tcg_gen_br(label4);
802             /* Rm negative, shift to the right */
803             gen_set_label(label1);
804             tcg_gen_andi_i32(cpu_T[0], cpu_gregs[REG(B7_4)], 0x1f);
805             tcg_gen_brcondi_i32(TCG_COND_EQ, cpu_T[0], 0, label2);
806             tcg_gen_not_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
807             tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0x1f);
808             tcg_gen_addi_i32(cpu_T[0], cpu_T[0], 1);
809             tcg_gen_sar_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_T[0]);
810             tcg_gen_br(label4);
811             /* Rm = -32 */
812             gen_set_label(label2);
813             tcg_gen_brcondi_i32(TCG_COND_LT, cpu_gregs[REG(B11_8)], 0, label3);
814             tcg_gen_movi_i32(cpu_gregs[REG(B11_8)], 0);
815             tcg_gen_br(label4);
816             gen_set_label(label3);
817             tcg_gen_movi_i32(cpu_gregs[REG(B11_8)], 0xffffffff);
818             gen_set_label(label4);
819         }
820         return;
821     case 0x400d:                /* shld Rm,Rn */
822         {
823             int label1 = gen_new_label();
824             int label2 = gen_new_label();
825             int label3 = gen_new_label();
826             tcg_gen_brcondi_i32(TCG_COND_LT, cpu_gregs[REG(B7_4)], 0, label1);
827             /* Rm positive, shift to the left */
828             tcg_gen_andi_i32(cpu_T[0], cpu_gregs[REG(B7_4)], 0x1f);
829             tcg_gen_shl_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_T[0]);
830             tcg_gen_br(label3);
831             /* Rm negative, shift to the right */
832             gen_set_label(label1);
833             tcg_gen_andi_i32(cpu_T[0], cpu_gregs[REG(B7_4)], 0x1f);
834             tcg_gen_brcondi_i32(TCG_COND_EQ, cpu_T[0], 0, label2);
835             tcg_gen_not_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
836             tcg_gen_andi_i32(cpu_T[0], cpu_T[0], 0x1f);
837             tcg_gen_addi_i32(cpu_T[0], cpu_T[0], 1);
838             tcg_gen_shr_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_T[0]);
839             tcg_gen_br(label3);
840             /* Rm = -32 */
841             gen_set_label(label2);
842             tcg_gen_movi_i32(cpu_gregs[REG(B11_8)], 0);
843             gen_set_label(label3);
844         }
845         return;
846     case 0x3008:                /* sub Rm,Rn */
847         tcg_gen_sub_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)]);
848         return;
849     case 0x300a:                /* subc Rm,Rn */
850         tcg_gen_helper_1_2(helper_subc, cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)], cpu_gregs[REG(B11_8)]);
851         return;
852     case 0x300b:                /* subv Rm,Rn */
853         tcg_gen_helper_1_2(helper_subv, cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)], cpu_gregs[REG(B11_8)]);
854         return;
855     case 0x2008:                /* tst Rm,Rn */
856         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
857         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
858         tcg_gen_and_i32(cpu_T[0], cpu_T[0], cpu_T[1]);
859         gen_cmp_imm(TCG_COND_EQ, cpu_T[0], 0);
860         return;
861     case 0x200a:                /* xor Rm,Rn */
862         tcg_gen_xor_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], cpu_gregs[REG(B7_4)]);
863         return;
864     case 0xf00c: /* fmov {F,D,X}Rm,{F,D,X}Rn - FPSCR: Nothing */
865         if (ctx->fpscr & FPSCR_SZ) {
866             gen_op_fmov_drN_DT0(XREG(B7_4));
867             gen_op_fmov_DT0_drN(XREG(B11_8));
868         } else {
869             gen_op_fmov_frN_FT0(FREG(B7_4));
870             gen_op_fmov_FT0_frN(FREG(B11_8));
871         }
872         return;
873     case 0xf00a: /* fmov {F,D,X}Rm,@Rn - FPSCR: Nothing */
874         if (ctx->fpscr & FPSCR_SZ) {
875             gen_op_fmov_drN_DT0(XREG(B7_4));
876             tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
877             gen_op_stfq_DT0_T1(ctx);
878         } else {
879             gen_op_fmov_frN_FT0(FREG(B7_4));
880             tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
881             gen_op_stfl_FT0_T1(ctx);
882         }
883         return;
884     case 0xf008: /* fmov @Rm,{F,D,X}Rn - FPSCR: Nothing */
885         if (ctx->fpscr & FPSCR_SZ) {
886             tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
887             gen_op_ldfq_T0_DT0(ctx);
888             gen_op_fmov_DT0_drN(XREG(B11_8));
889         } else {
890             tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
891             gen_op_ldfl_T0_FT0(ctx);
892             gen_op_fmov_FT0_frN(FREG(B11_8));
893         }
894         return;
895     case 0xf009: /* fmov @Rm+,{F,D,X}Rn - FPSCR: Nothing */
896         if (ctx->fpscr & FPSCR_SZ) {
897             tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
898             gen_op_ldfq_T0_DT0(ctx);
899             gen_op_fmov_DT0_drN(XREG(B11_8));
900             tcg_gen_addi_i32(cpu_gregs[REG(B7_4)],
901                              cpu_gregs[REG(B7_4)], 8);
902         } else {
903             tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
904             gen_op_ldfl_T0_FT0(ctx);
905             gen_op_fmov_FT0_frN(FREG(B11_8));
906             tcg_gen_addi_i32(cpu_gregs[REG(B7_4)],
907                              cpu_gregs[REG(B7_4)], 4);
908         }
909         return;
910     case 0xf00b: /* fmov {F,D,X}Rm,@-Rn - FPSCR: Nothing */
911         if (ctx->fpscr & FPSCR_SZ) {
912             tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 8);
913             gen_op_fmov_drN_DT0(XREG(B7_4));
914             tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
915             tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 8);
916             gen_op_stfq_DT0_T1(ctx);
917             tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 8);
918         } else {
919             tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
920             gen_op_fmov_frN_FT0(FREG(B7_4));
921             tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
922             tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
923             gen_op_stfl_FT0_T1(ctx);
924             tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
925         }
926         return;
927     case 0xf006: /* fmov @(R0,Rm),{F,D,X}Rm - FPSCR: Nothing */
928         tcg_gen_add_i32(cpu_T[0], cpu_gregs[REG(B7_4)], cpu_gregs[REG(0)]);
929         if (ctx->fpscr & FPSCR_SZ) {
930             gen_op_ldfq_T0_DT0(ctx);
931             gen_op_fmov_DT0_drN(XREG(B11_8));
932         } else {
933             gen_op_ldfl_T0_FT0(ctx);
934             gen_op_fmov_FT0_frN(FREG(B11_8));
935         }
936         return;
937     case 0xf007: /* fmov {F,D,X}Rn,@(R0,Rn) - FPSCR: Nothing */
938         if (ctx->fpscr & FPSCR_SZ) {
939             gen_op_fmov_drN_DT0(XREG(B7_4));
940             tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
941             tcg_gen_add_i32(cpu_T[1], cpu_T[1], cpu_gregs[REG(0)]);
942             gen_op_stfq_DT0_T1(ctx);
943         } else {
944             gen_op_fmov_frN_FT0(FREG(B7_4));
945             tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
946             tcg_gen_add_i32(cpu_T[1], cpu_T[1], cpu_gregs[REG(0)]);
947             gen_op_stfl_FT0_T1(ctx);
948         }
949         return;
950     case 0xf000: /* fadd Rm,Rn - FPSCR: R[PR,Enable.O/U/I]/W[Cause,Flag] */
951     case 0xf001: /* fsub Rm,Rn - FPSCR: R[PR,Enable.O/U/I]/W[Cause,Flag] */
952     case 0xf002: /* fmul Rm,Rn - FPSCR: R[PR,Enable.O/U/I]/W[Cause,Flag] */
953     case 0xf003: /* fdiv Rm,Rn - FPSCR: R[PR,Enable.O/U/I]/W[Cause,Flag] */
954     case 0xf004: /* fcmp/eq Rm,Rn - FPSCR: R[PR,Enable.V]/W[Cause,Flag] */
955     case 0xf005: /* fcmp/gt Rm,Rn - FPSCR: R[PR,Enable.V]/W[Cause,Flag] */
956         if (ctx->fpscr & FPSCR_PR) {
957             if (ctx->opcode & 0x0110)
958                 break; /* illegal instruction */
959             gen_op_fmov_drN_DT1(DREG(B7_4));
960             gen_op_fmov_drN_DT0(DREG(B11_8));
961         }
962         else {
963             gen_op_fmov_frN_FT1(FREG(B7_4));
964             gen_op_fmov_frN_FT0(FREG(B11_8));
965         }
966
967         switch (ctx->opcode & 0xf00f) {
968         case 0xf000:            /* fadd Rm,Rn */
969             ctx->fpscr & FPSCR_PR ? gen_op_fadd_DT() : gen_op_fadd_FT();
970             break;
971         case 0xf001:            /* fsub Rm,Rn */
972             ctx->fpscr & FPSCR_PR ? gen_op_fsub_DT() : gen_op_fsub_FT();
973             break;
974         case 0xf002:            /* fmul Rm,Rn */
975             ctx->fpscr & FPSCR_PR ? gen_op_fmul_DT() : gen_op_fmul_FT();
976             break;
977         case 0xf003:            /* fdiv Rm,Rn */
978             ctx->fpscr & FPSCR_PR ? gen_op_fdiv_DT() : gen_op_fdiv_FT();
979             break;
980         case 0xf004:            /* fcmp/eq Rm,Rn */
981             ctx->fpscr & FPSCR_PR ? gen_op_fcmp_eq_DT() : gen_op_fcmp_eq_FT();
982             return;
983         case 0xf005:            /* fcmp/gt Rm,Rn */
984             ctx->fpscr & FPSCR_PR ? gen_op_fcmp_gt_DT() : gen_op_fcmp_gt_FT();
985             return;
986         }
987
988         if (ctx->fpscr & FPSCR_PR) {
989             gen_op_fmov_DT0_drN(DREG(B11_8));
990         }
991         else {
992             gen_op_fmov_FT0_frN(FREG(B11_8));
993         }
994         return;
995     }
996
997     switch (ctx->opcode & 0xff00) {
998     case 0xc900:                /* and #imm,R0 */
999         tcg_gen_andi_i32(cpu_gregs[REG(0)], cpu_gregs[REG(0)], B7_0);
1000         return;
1001     case 0xcd00:                /* and.b #imm,@(R0,GBR) */
1002         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1003         tcg_gen_add_i32(cpu_T[0], cpu_T[0], cpu_gbr);
1004         tcg_gen_mov_i32(cpu_T[1], cpu_T[0]);
1005         tcg_gen_qemu_ld8u(cpu_T[0], cpu_T[0], ctx->memidx);
1006         tcg_gen_andi_i32(cpu_T[0], cpu_T[0], B7_0);
1007         tcg_gen_qemu_st8(cpu_T[0], cpu_T[1], ctx->memidx);
1008         return;
1009     case 0x8b00:                /* bf label */
1010         CHECK_NOT_DELAY_SLOT
1011             gen_conditional_jump(ctx, ctx->pc + 2,
1012                                  ctx->pc + 4 + B7_0s * 2);
1013         ctx->bstate = BS_BRANCH;
1014         return;
1015     case 0x8f00:                /* bf/s label */
1016         CHECK_NOT_DELAY_SLOT
1017         gen_branch_slot(ctx->delayed_pc = ctx->pc + 4 + B7_0s * 2, 0);
1018         ctx->flags |= DELAY_SLOT_CONDITIONAL;
1019         return;
1020     case 0x8900:                /* bt label */
1021         CHECK_NOT_DELAY_SLOT
1022             gen_conditional_jump(ctx, ctx->pc + 4 + B7_0s * 2,
1023                                  ctx->pc + 2);
1024         ctx->bstate = BS_BRANCH;
1025         return;
1026     case 0x8d00:                /* bt/s label */
1027         CHECK_NOT_DELAY_SLOT
1028         gen_branch_slot(ctx->delayed_pc = ctx->pc + 4 + B7_0s * 2, 1);
1029         ctx->flags |= DELAY_SLOT_CONDITIONAL;
1030         return;
1031     case 0x8800:                /* cmp/eq #imm,R0 */
1032         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1033         gen_cmp_imm(TCG_COND_EQ, cpu_T[0], B7_0s);
1034         return;
1035     case 0xc400:                /* mov.b @(disp,GBR),R0 */
1036         tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0);
1037         tcg_gen_qemu_ld8s(cpu_T[0], cpu_T[0], ctx->memidx);
1038         tcg_gen_mov_i32(cpu_gregs[REG(0)], cpu_T[0]);
1039         return;
1040     case 0xc500:                /* mov.w @(disp,GBR),R0 */
1041         tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0 * 2);
1042         tcg_gen_qemu_ld16s(cpu_T[0], cpu_T[0], ctx->memidx);
1043         tcg_gen_mov_i32(cpu_gregs[REG(0)], cpu_T[0]);
1044         return;
1045     case 0xc600:                /* mov.l @(disp,GBR),R0 */
1046         tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0 * 4);
1047         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
1048         tcg_gen_mov_i32(cpu_gregs[REG(0)], cpu_T[0]);
1049         return;
1050     case 0xc000:                /* mov.b R0,@(disp,GBR) */
1051         tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0);
1052         tcg_gen_mov_i32(cpu_T[1], cpu_T[0]);
1053         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1054         tcg_gen_qemu_st8(cpu_T[0], cpu_T[1], ctx->memidx);
1055         return;
1056     case 0xc100:                /* mov.w R0,@(disp,GBR) */
1057         tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0 * 2);
1058         tcg_gen_mov_i32(cpu_T[1], cpu_T[0]);
1059         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1060         tcg_gen_qemu_st16(cpu_T[0], cpu_T[1], ctx->memidx);
1061         return;
1062     case 0xc200:                /* mov.l R0,@(disp,GBR) */
1063         tcg_gen_addi_i32(cpu_T[0], cpu_gbr, B7_0 * 4);
1064         tcg_gen_mov_i32(cpu_T[1], cpu_T[0]);
1065         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1066         tcg_gen_qemu_st32(cpu_T[0], cpu_T[1], ctx->memidx);
1067         return;
1068     case 0x8000:                /* mov.b R0,@(disp,Rn) */
1069         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1070         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B7_4)]);
1071         tcg_gen_addi_i32(cpu_T[1], cpu_T[1], B3_0);
1072         tcg_gen_qemu_st8(cpu_T[0], cpu_T[1], ctx->memidx);
1073         return;
1074     case 0x8100:                /* mov.w R0,@(disp,Rn) */
1075         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1076         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B7_4)]);
1077         tcg_gen_addi_i32(cpu_T[1], cpu_T[1], B3_0 * 2);
1078         tcg_gen_qemu_st16(cpu_T[0], cpu_T[1], ctx->memidx);
1079         return;
1080     case 0x8400:                /* mov.b @(disp,Rn),R0 */
1081         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
1082         tcg_gen_addi_i32(cpu_T[0], cpu_T[0], B3_0);
1083         tcg_gen_qemu_ld8s(cpu_T[0], cpu_T[0], ctx->memidx);
1084         tcg_gen_mov_i32(cpu_gregs[REG(0)], cpu_T[0]);
1085         return;
1086     case 0x8500:                /* mov.w @(disp,Rn),R0 */
1087         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B7_4)]);
1088         tcg_gen_addi_i32(cpu_T[0], cpu_T[0], B3_0 * 2);
1089         tcg_gen_qemu_ld16s(cpu_T[0], cpu_T[0], ctx->memidx);
1090         tcg_gen_mov_i32(cpu_gregs[REG(0)], cpu_T[0]);
1091         return;
1092     case 0xc700:                /* mova @(disp,PC),R0 */
1093         tcg_gen_movi_i32(cpu_gregs[REG(0)],
1094                          ((ctx->pc & 0xfffffffc) + 4 + B7_0 * 4) & ~3);
1095         return;
1096     case 0xcb00:                /* or #imm,R0 */
1097         tcg_gen_ori_i32(cpu_gregs[REG(0)], cpu_gregs[REG(0)], B7_0);
1098         return;
1099     case 0xcf00:                /* or.b #imm,@(R0,GBR) */
1100         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1101         tcg_gen_add_i32(cpu_T[0], cpu_T[0], cpu_gbr);
1102         tcg_gen_mov_i32(cpu_T[0], cpu_T[1]);
1103         tcg_gen_qemu_ld8u(cpu_T[0], cpu_T[0], ctx->memidx);
1104         tcg_gen_ori_i32(cpu_T[0], cpu_T[0], B7_0);
1105         tcg_gen_qemu_st8(cpu_T[0], cpu_T[1], ctx->memidx);
1106         return;
1107     case 0xc300:                /* trapa #imm */
1108         CHECK_NOT_DELAY_SLOT
1109         tcg_gen_movi_i32(cpu_pc, ctx->pc);
1110         tcg_gen_movi_i32(cpu_T[0], B7_0);
1111         tcg_gen_helper_0_1(helper_trapa, cpu_T[0]);
1112         ctx->bstate = BS_BRANCH;
1113         return;
1114     case 0xc800:                /* tst #imm,R0 */
1115         tcg_gen_andi_i32(cpu_T[0], cpu_gregs[REG(0)], B7_0);
1116         gen_cmp_imm(TCG_COND_EQ, cpu_T[0], 0);
1117         return;
1118     case 0xcc00:                /* tst.b #imm,@(R0,GBR) */
1119         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1120         tcg_gen_add_i32(cpu_T[0], cpu_T[0], cpu_gbr);
1121         tcg_gen_qemu_ld8u(cpu_T[0], cpu_T[0], ctx->memidx);
1122         tcg_gen_andi_i32(cpu_T[0], cpu_T[0], B7_0);
1123         gen_cmp_imm(TCG_COND_EQ, cpu_T[0], 0);
1124         return;
1125     case 0xca00:                /* xor #imm,R0 */
1126         tcg_gen_xori_i32(cpu_gregs[REG(0)], cpu_gregs[REG(0)], B7_0);
1127         return;
1128     case 0xce00:                /* xor.b #imm,@(R0,GBR) */
1129         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1130         tcg_gen_add_i32(cpu_T[0], cpu_T[0], cpu_gbr);
1131         tcg_gen_mov_i32(cpu_T[1], cpu_T[0]);
1132         tcg_gen_qemu_ld8u(cpu_T[0], cpu_T[0], ctx->memidx);
1133         tcg_gen_xori_i32(cpu_T[0], cpu_T[0], B7_0);
1134         tcg_gen_qemu_st8(cpu_T[0], cpu_T[1], ctx->memidx);
1135         return;
1136     }
1137
1138     switch (ctx->opcode & 0xf08f) {
1139     case 0x408e:                /* ldc Rm,Rn_BANK */
1140         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1141         tcg_gen_mov_i32(cpu_gregs[ALTREG(B6_4)], cpu_T[0]);
1142         return;
1143     case 0x4087:                /* ldc.l @Rm+,Rn_BANK */
1144         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1145         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
1146         tcg_gen_mov_i32(cpu_gregs[ALTREG(B6_4)], cpu_T[0]);
1147         tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
1148         return;
1149     case 0x0082:                /* stc Rm_BANK,Rn */
1150         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[ALTREG(B6_4)]);
1151         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
1152         return;
1153     case 0x4083:                /* stc.l Rm_BANK,@-Rn */
1154         tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
1155         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
1156         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[ALTREG(B6_4)]);
1157         tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
1158         tcg_gen_qemu_st32(cpu_T[0], cpu_T[1], ctx->memidx);
1159         tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
1160         return;
1161     }
1162
1163     switch (ctx->opcode & 0xf0ff) {
1164     case 0x0023:                /* braf Rn */
1165         CHECK_NOT_DELAY_SLOT tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1166         tcg_gen_addi_i32(cpu_delayed_pc, cpu_T[0], ctx->pc + 4);
1167         ctx->flags |= DELAY_SLOT;
1168         ctx->delayed_pc = (uint32_t) - 1;
1169         return;
1170     case 0x0003:                /* bsrf Rn */
1171         CHECK_NOT_DELAY_SLOT tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1172         tcg_gen_movi_i32(cpu_pr, ctx->pc + 4);
1173         tcg_gen_add_i32(cpu_delayed_pc, cpu_T[0], cpu_pr);
1174         ctx->flags |= DELAY_SLOT;
1175         ctx->delayed_pc = (uint32_t) - 1;
1176         return;
1177     case 0x4015:                /* cmp/pl Rn */
1178         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1179         gen_cmp_imm(TCG_COND_GT, cpu_T[0], 0);
1180         return;
1181     case 0x4011:                /* cmp/pz Rn */
1182         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1183         gen_cmp_imm(TCG_COND_GE, cpu_T[0], 0);
1184         return;
1185     case 0x4010:                /* dt Rn */
1186         tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 1);
1187         gen_cmp_imm(TCG_COND_EQ, cpu_gregs[REG(B11_8)], 0);
1188         return;
1189     case 0x402b:                /* jmp @Rn */
1190         CHECK_NOT_DELAY_SLOT tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1191         tcg_gen_mov_i32(cpu_delayed_pc, cpu_T[0]);
1192         ctx->flags |= DELAY_SLOT;
1193         ctx->delayed_pc = (uint32_t) - 1;
1194         return;
1195     case 0x400b:                /* jsr @Rn */
1196         CHECK_NOT_DELAY_SLOT tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1197         tcg_gen_movi_i32(cpu_pr, ctx->pc + 4);
1198         tcg_gen_mov_i32(cpu_delayed_pc, cpu_T[0]);
1199         ctx->flags |= DELAY_SLOT;
1200         ctx->delayed_pc = (uint32_t) - 1;
1201         return;
1202     case 0x400e:                /* lds Rm,SR */
1203         tcg_gen_andi_i32(cpu_sr, cpu_gregs[REG(B11_8)], 0x700083f3);
1204         ctx->bstate = BS_STOP;
1205         return;
1206     case 0x4007:                /* lds.l @Rm+,SR */
1207         tcg_gen_qemu_ld32s(cpu_T[0], cpu_gregs[REG(B11_8)], ctx->memidx);
1208         tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
1209         tcg_gen_andi_i32(cpu_sr, cpu_T[0], 0x700083f3);
1210         ctx->bstate = BS_STOP;
1211         return;
1212     case 0x0002:                /* sts SR,Rn */
1213         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_sr);
1214         return;
1215     case 0x4003:                /* sts SR,@-Rn */
1216         tcg_gen_subi_i32(cpu_T[0], cpu_gregs[REG(B11_8)], 4);
1217         tcg_gen_qemu_st32(cpu_sr, cpu_T[0], ctx->memidx);
1218         tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
1219         return;
1220 #define LDST(reg,ldnum,ldpnum,stnum,stpnum)                     \
1221   case ldnum:                                                   \
1222     tcg_gen_mov_i32 (cpu_##reg, cpu_gregs[REG(B11_8)]);         \
1223     return;                                                     \
1224   case ldpnum:                                                  \
1225     tcg_gen_qemu_ld32s (cpu_##reg, cpu_gregs[REG(B11_8)], ctx->memidx); \
1226     tcg_gen_addi_i32(cpu_gregs[REG(B11_8)],                     \
1227                      cpu_gregs[REG(B11_8)], 4);                 \
1228     return;                                                     \
1229   case stnum:                                                   \
1230     tcg_gen_mov_i32 (cpu_gregs[REG(B11_8)], cpu_##reg);         \
1231     return;                                                     \
1232   case stpnum:                                                  \
1233     tcg_gen_subi_i32(cpu_T[1], cpu_gregs[REG(B11_8)], 4);       \
1234     tcg_gen_qemu_st32 (cpu_##reg, cpu_T[1], ctx->memidx);       \
1235     tcg_gen_subi_i32(cpu_gregs[REG(B11_8)],                     \
1236                      cpu_gregs[REG(B11_8)], 4);                 \
1237     return;
1238         LDST(gbr,  0x401e, 0x4017, 0x0012, 0x4013)
1239         LDST(vbr,  0x402e, 0x4027, 0x0022, 0x4023)
1240         LDST(ssr,  0x403e, 0x4037, 0x0032, 0x4033)
1241         LDST(spc,  0x404e, 0x4047, 0x0042, 0x4043)
1242         LDST(dbr,  0x40fa, 0x40f6, 0x00fa, 0x40f2)
1243         LDST(mach, 0x400a, 0x4006, 0x000a, 0x4002)
1244         LDST(macl, 0x401a, 0x4016, 0x001a, 0x4012)
1245         LDST(pr,   0x402a, 0x4026, 0x002a, 0x4022)
1246         LDST(fpul, 0x405a, 0x4056, 0x005a, 0x4052)
1247     case 0x406a:                /* lds Rm,FPSCR */
1248         tcg_gen_helper_0_1(helper_ld_fpscr, cpu_gregs[REG(B11_8)]);
1249         ctx->bstate = BS_STOP;
1250         return;
1251     case 0x4066:                /* lds.l @Rm+,FPSCR */
1252         tcg_gen_qemu_ld32s(cpu_T[0], cpu_gregs[REG(B11_8)], ctx->memidx);
1253         tcg_gen_addi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
1254         tcg_gen_helper_0_1(helper_ld_fpscr, cpu_T[0]);
1255         ctx->bstate = BS_STOP;
1256         return;
1257     case 0x006a:                /* sts FPSCR,Rn */
1258         tcg_gen_andi_i32(cpu_T[0], cpu_fpscr, 0x003fffff);
1259         tcg_gen_mov_i32(cpu_gregs[REG(B11_8)], cpu_T[0]);
1260         return;
1261     case 0x4062:                /* sts FPSCR,@-Rn */
1262         tcg_gen_andi_i32(cpu_T[0], cpu_fpscr, 0x003fffff);
1263         tcg_gen_subi_i32(cpu_T[1], cpu_gregs[REG(B11_8)], 4);
1264         tcg_gen_qemu_st32(cpu_T[0], cpu_T[1], ctx->memidx);
1265         tcg_gen_subi_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 4);
1266         return;
1267     case 0x00c3:                /* movca.l R0,@Rm */
1268         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(0)]);
1269         tcg_gen_mov_i32(cpu_T[1], cpu_gregs[REG(B11_8)]);
1270         tcg_gen_qemu_st32(cpu_T[0], cpu_T[1], ctx->memidx);
1271         return;
1272     case 0x0029:                /* movt Rn */
1273         tcg_gen_andi_i32(cpu_gregs[REG(B11_8)], cpu_sr, SR_T);
1274         return;
1275     case 0x0093:                /* ocbi @Rn */
1276         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1277         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
1278         return;
1279     case 0x00a3:                /* ocbp @Rn */
1280         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1281         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
1282         return;
1283     case 0x00b3:                /* ocbwb @Rn */
1284         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1285         tcg_gen_qemu_ld32s(cpu_T[0], cpu_T[0], ctx->memidx);
1286         return;
1287     case 0x0083:                /* pref @Rn */
1288         return;
1289     case 0x4024:                /* rotcl Rn */
1290         tcg_gen_mov_i32(cpu_T[0], cpu_sr);
1291         gen_copy_bit_i32(cpu_sr, 0, cpu_gregs[REG(B11_8)], 31);
1292         tcg_gen_shli_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 1);
1293         gen_copy_bit_i32(cpu_gregs[REG(B11_8)], 0, cpu_T[0], 0);
1294         return;
1295     case 0x4025:                /* rotcr Rn */
1296         tcg_gen_mov_i32(cpu_T[0], cpu_sr);
1297         gen_copy_bit_i32(cpu_sr, 0, cpu_gregs[REG(B11_8)], 0);
1298         tcg_gen_shri_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 1);
1299         gen_copy_bit_i32(cpu_gregs[REG(B11_8)], 31, cpu_T[0], 0);
1300         return;
1301     case 0x4004:                /* rotl Rn */
1302         gen_copy_bit_i32(cpu_sr, 0, cpu_gregs[REG(B11_8)], 31);
1303         tcg_gen_shli_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 1);
1304         gen_copy_bit_i32(cpu_gregs[REG(B11_8)], 0, cpu_sr, 0);
1305         return;
1306     case 0x4005:                /* rotr Rn */
1307         gen_copy_bit_i32(cpu_sr, 0, cpu_gregs[REG(B11_8)], 0);
1308         tcg_gen_shri_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 1);
1309         gen_copy_bit_i32(cpu_gregs[REG(B11_8)], 31, cpu_sr, 0);
1310         return;
1311     case 0x4000:                /* shll Rn */
1312     case 0x4020:                /* shal Rn */
1313         gen_copy_bit_i32(cpu_sr, 0, cpu_gregs[REG(B11_8)], 31);
1314         tcg_gen_shli_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 1);
1315         return;
1316     case 0x4021:                /* shar Rn */
1317         gen_copy_bit_i32(cpu_sr, 0, cpu_gregs[REG(B11_8)], 0);
1318         tcg_gen_sari_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 1);
1319         return;
1320     case 0x4001:                /* shlr Rn */
1321         gen_copy_bit_i32(cpu_sr, 0, cpu_gregs[REG(B11_8)], 0);
1322         tcg_gen_shri_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 1);
1323         return;
1324     case 0x4008:                /* shll2 Rn */
1325         tcg_gen_shli_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 2);
1326         return;
1327     case 0x4018:                /* shll8 Rn */
1328         tcg_gen_shli_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 8);
1329         return;
1330     case 0x4028:                /* shll16 Rn */
1331         tcg_gen_shli_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 16);
1332         return;
1333     case 0x4009:                /* shlr2 Rn */
1334         tcg_gen_shri_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 2);
1335         return;
1336     case 0x4019:                /* shlr8 Rn */
1337         tcg_gen_shri_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 8);
1338         return;
1339     case 0x4029:                /* shlr16 Rn */
1340         tcg_gen_shri_i32(cpu_gregs[REG(B11_8)], cpu_gregs[REG(B11_8)], 16);
1341         return;
1342     case 0x401b:                /* tas.b @Rn */
1343         tcg_gen_mov_i32(cpu_T[0], cpu_gregs[REG(B11_8)]);
1344         tcg_gen_mov_i32(cpu_T[1], cpu_T[0]);
1345         tcg_gen_qemu_ld8u(cpu_T[0], cpu_T[0], ctx->memidx);
1346         gen_cmp_imm(TCG_COND_EQ, cpu_T[0], 0);
1347         tcg_gen_ori_i32(cpu_T[0], cpu_T[0], 0x80);
1348         tcg_gen_qemu_st8(cpu_T[0], cpu_T[1], ctx->memidx);
1349         return;
1350     case 0xf00d: /* fsts FPUL,FRn - FPSCR: Nothing */
1351         gen_op_movl_fpul_FT0();
1352         gen_op_fmov_FT0_frN(FREG(B11_8));
1353         return;
1354     case 0xf01d: /* flds FRm,FPUL - FPSCR: Nothing */
1355         gen_op_fmov_frN_FT0(FREG(B11_8));
1356         gen_op_movl_FT0_fpul();
1357         return;
1358     case 0xf02d: /* float FPUL,FRn/DRn - FPSCR: R[PR,Enable.I]/W[Cause,Flag] */
1359         if (ctx->fpscr & FPSCR_PR) {
1360             if (ctx->opcode & 0x0100)
1361                 break; /* illegal instruction */
1362             gen_op_float_DT();
1363             gen_op_fmov_DT0_drN(DREG(B11_8));
1364         }
1365         else {
1366             gen_op_float_FT();
1367             gen_op_fmov_FT0_frN(FREG(B11_8));
1368         }
1369         return;
1370     case 0xf03d: /* ftrc FRm/DRm,FPUL - FPSCR: R[PR,Enable.V]/W[Cause,Flag] */
1371         if (ctx->fpscr & FPSCR_PR) {
1372             if (ctx->opcode & 0x0100)
1373                 break; /* illegal instruction */
1374             gen_op_fmov_drN_DT0(DREG(B11_8));
1375             gen_op_ftrc_DT();
1376         }
1377         else {
1378             gen_op_fmov_frN_FT0(FREG(B11_8));
1379             gen_op_ftrc_FT();
1380         }
1381         return;
1382     case 0xf04d: /* fneg FRn/DRn - FPSCR: Nothing */
1383         gen_op_fneg_frN(FREG(B11_8));
1384         return;
1385     case 0xf05d: /* fabs FRn/DRn */
1386         if (ctx->fpscr & FPSCR_PR) {
1387             if (ctx->opcode & 0x0100)
1388                 break; /* illegal instruction */
1389             gen_op_fmov_drN_DT0(DREG(B11_8));
1390             gen_op_fabs_DT();
1391             gen_op_fmov_DT0_drN(DREG(B11_8));
1392         } else {
1393             gen_op_fmov_frN_FT0(FREG(B11_8));
1394             gen_op_fabs_FT();
1395             gen_op_fmov_FT0_frN(FREG(B11_8));
1396         }
1397         return;
1398     case 0xf06d: /* fsqrt FRn */
1399         if (ctx->fpscr & FPSCR_PR) {
1400             if (ctx->opcode & 0x0100)
1401                 break; /* illegal instruction */
1402             gen_op_fmov_drN_DT0(FREG(B11_8));
1403             gen_op_fsqrt_DT();
1404             gen_op_fmov_DT0_drN(FREG(B11_8));
1405         } else {
1406             gen_op_fmov_frN_FT0(FREG(B11_8));
1407             gen_op_fsqrt_FT();
1408             gen_op_fmov_FT0_frN(FREG(B11_8));
1409         }
1410         return;
1411     case 0xf07d: /* fsrra FRn */
1412         break;
1413     case 0xf08d: /* fldi0 FRn - FPSCR: R[PR] */
1414         if (!(ctx->fpscr & FPSCR_PR)) {
1415             tcg_gen_movi_i32(cpu_T[0], 0);
1416             gen_op_fmov_T0_frN(FREG(B11_8));
1417             return;
1418         }
1419         break;
1420     case 0xf09d: /* fldi1 FRn - FPSCR: R[PR] */
1421         if (!(ctx->fpscr & FPSCR_PR)) {
1422             tcg_gen_movi_i32(cpu_T[0], 0x3f800000);
1423             gen_op_fmov_T0_frN(FREG(B11_8));
1424             return;
1425         }
1426         break;
1427     case 0xf0ad: /* fcnvsd FPUL,DRn */
1428         gen_op_movl_fpul_FT0();
1429         gen_op_fcnvsd_FT_DT();
1430         gen_op_fmov_DT0_drN(DREG(B11_8));
1431         return;
1432     case 0xf0bd: /* fcnvds DRn,FPUL */
1433         gen_op_fmov_drN_DT0(DREG(B11_8));
1434         gen_op_fcnvds_DT_FT();
1435         gen_op_movl_FT0_fpul();
1436         return;
1437     }
1438
1439     fprintf(stderr, "unknown instruction 0x%04x at pc 0x%08x\n",
1440             ctx->opcode, ctx->pc);
1441     tcg_gen_helper_0_0(helper_raise_illegal_instruction);
1442     ctx->bstate = BS_EXCP;
1443 }
1444
1445 void decode_opc(DisasContext * ctx)
1446 {
1447     uint32_t old_flags = ctx->flags;
1448
1449     _decode_opc(ctx);
1450
1451     if (old_flags & (DELAY_SLOT | DELAY_SLOT_CONDITIONAL)) {
1452         if (ctx->flags & DELAY_SLOT_CLEARME) {
1453             gen_store_flags(0);
1454         } else {
1455             /* go out of the delay slot */
1456             uint32_t new_flags = ctx->flags;
1457             new_flags &= ~(DELAY_SLOT | DELAY_SLOT_CONDITIONAL);
1458             gen_store_flags(new_flags);
1459         }
1460         ctx->flags = 0;
1461         ctx->bstate = BS_BRANCH;
1462         if (old_flags & DELAY_SLOT_CONDITIONAL) {
1463             gen_delayed_conditional_jump(ctx);
1464         } else if (old_flags & DELAY_SLOT) {
1465             gen_jump(ctx);
1466         }
1467
1468     }
1469
1470     /* go into a delay slot */
1471     if (ctx->flags & (DELAY_SLOT | DELAY_SLOT_CONDITIONAL))
1472         gen_store_flags(ctx->flags);
1473 }
1474
1475 static inline void
1476 gen_intermediate_code_internal(CPUState * env, TranslationBlock * tb,
1477                                int search_pc)
1478 {
1479     DisasContext ctx;
1480     target_ulong pc_start;
1481     static uint16_t *gen_opc_end;
1482     int i, ii;
1483     int num_insns;
1484     int max_insns;
1485
1486     pc_start = tb->pc;
1487     gen_opc_end = gen_opc_buf + OPC_MAX_SIZE;
1488     ctx.pc = pc_start;
1489     ctx.flags = (uint32_t)tb->flags;
1490     ctx.bstate = BS_NONE;
1491     ctx.sr = env->sr;
1492     ctx.fpscr = env->fpscr;
1493     ctx.memidx = (env->sr & SR_MD) ? 1 : 0;
1494     /* We don't know if the delayed pc came from a dynamic or static branch,
1495        so assume it is a dynamic branch.  */
1496     ctx.delayed_pc = -1; /* use delayed pc from env pointer */
1497     ctx.tb = tb;
1498     ctx.singlestep_enabled = env->singlestep_enabled;
1499
1500 #ifdef DEBUG_DISAS
1501     if (loglevel & CPU_LOG_TB_CPU) {
1502         fprintf(logfile,
1503                 "------------------------------------------------\n");
1504         cpu_dump_state(env, logfile, fprintf, 0);
1505     }
1506 #endif
1507
1508     ii = -1;
1509     num_insns = 0;
1510     max_insns = tb->cflags & CF_COUNT_MASK;
1511     if (max_insns == 0)
1512         max_insns = CF_COUNT_MASK;
1513     gen_icount_start();
1514     while (ctx.bstate == BS_NONE && gen_opc_ptr < gen_opc_end) {
1515         if (env->nb_breakpoints > 0) {
1516             for (i = 0; i < env->nb_breakpoints; i++) {
1517                 if (ctx.pc == env->breakpoints[i]) {
1518                     /* We have hit a breakpoint - make sure PC is up-to-date */
1519                     tcg_gen_movi_i32(cpu_pc, ctx.pc);
1520                     tcg_gen_helper_0_0(helper_debug);
1521                     ctx.bstate = BS_EXCP;
1522                     break;
1523                 }
1524             }
1525         }
1526         if (search_pc) {
1527             i = gen_opc_ptr - gen_opc_buf;
1528             if (ii < i) {
1529                 ii++;
1530                 while (ii < i)
1531                     gen_opc_instr_start[ii++] = 0;
1532             }
1533             gen_opc_pc[ii] = ctx.pc;
1534             gen_opc_hflags[ii] = ctx.flags;
1535             gen_opc_instr_start[ii] = 1;
1536             gen_opc_icount[ii] = num_insns;
1537         }
1538         if (num_insns + 1 == max_insns && (tb->cflags & CF_LAST_IO))
1539             gen_io_start();
1540 #if 0
1541         fprintf(stderr, "Loading opcode at address 0x%08x\n", ctx.pc);
1542         fflush(stderr);
1543 #endif
1544         ctx.opcode = lduw_code(ctx.pc);
1545         decode_opc(&ctx);
1546         num_insns++;
1547         ctx.pc += 2;
1548         if ((ctx.pc & (TARGET_PAGE_SIZE - 1)) == 0)
1549             break;
1550         if (env->singlestep_enabled)
1551             break;
1552         if (num_insns >= max_insns)
1553             break;
1554 #ifdef SH4_SINGLE_STEP
1555         break;
1556 #endif
1557     }
1558     if (tb->cflags & CF_LAST_IO)
1559         gen_io_end();
1560     if (env->singlestep_enabled) {
1561         tcg_gen_helper_0_0(helper_debug);
1562     } else {
1563         switch (ctx.bstate) {
1564         case BS_STOP:
1565             /* gen_op_interrupt_restart(); */
1566             /* fall through */
1567         case BS_NONE:
1568             if (ctx.flags) {
1569                 gen_store_flags(ctx.flags | DELAY_SLOT_CLEARME);
1570             }
1571             gen_goto_tb(&ctx, 0, ctx.pc);
1572             break;
1573         case BS_EXCP:
1574             /* gen_op_interrupt_restart(); */
1575             tcg_gen_exit_tb(0);
1576             break;
1577         case BS_BRANCH:
1578         default:
1579             break;
1580         }
1581     }
1582
1583     gen_icount_end(tb, num_insns);
1584     *gen_opc_ptr = INDEX_op_end;
1585     if (search_pc) {
1586         i = gen_opc_ptr - gen_opc_buf;
1587         ii++;
1588         while (ii <= i)
1589             gen_opc_instr_start[ii++] = 0;
1590     } else {
1591         tb->size = ctx.pc - pc_start;
1592         tb->icount = num_insns;
1593     }
1594
1595 #ifdef DEBUG_DISAS
1596 #ifdef SH4_DEBUG_DISAS
1597     if (loglevel & CPU_LOG_TB_IN_ASM)
1598         fprintf(logfile, "\n");
1599 #endif
1600     if (loglevel & CPU_LOG_TB_IN_ASM) {
1601         fprintf(logfile, "IN:\n");      /* , lookup_symbol(pc_start)); */
1602         target_disas(logfile, pc_start, ctx.pc - pc_start, 0);
1603         fprintf(logfile, "\n");
1604     }
1605 #endif
1606 }
1607
1608 void gen_intermediate_code(CPUState * env, struct TranslationBlock *tb)
1609 {
1610     gen_intermediate_code_internal(env, tb, 0);
1611 }
1612
1613 void gen_intermediate_code_pc(CPUState * env, struct TranslationBlock *tb)
1614 {
1615     gen_intermediate_code_internal(env, tb, 1);
1616 }
1617
1618 void gen_pc_load(CPUState *env, TranslationBlock *tb,
1619                 unsigned long searched_pc, int pc_pos, void *puc)
1620 {
1621     env->pc = gen_opc_pc[pc_pos];
1622     env->flags = gen_opc_hflags[pc_pos];
1623 }