xref: /openbmc/qemu/target/cris/translate.c (revision abaf3e5b)
1 /*
2  *  CRIS emulation for qemu: main translation routines.
3  *
4  *  Copyright (c) 2008 AXIS Communications AB
5  *  Written by Edgar E. Iglesias.
6  *
7  * This library is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2.1 of the License, or (at your option) any later version.
11  *
12  * This library is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public
18  * License along with this library; if not, see <http://www.gnu.org/licenses/>.
19  */
20 
21 /*
22  * FIXME:
23  * The condition code translation is in need of attention.
24  */
25 
26 #include "qemu/osdep.h"
27 #include "cpu.h"
28 #include "disas/disas.h"
29 #include "exec/exec-all.h"
30 #include "tcg/tcg-op.h"
31 #include "exec/helper-proto.h"
32 #include "mmu.h"
33 #include "exec/cpu_ldst.h"
34 #include "exec/translator.h"
35 #include "crisv32-decode.h"
36 #include "qemu/qemu-print.h"
37 #include "exec/helper-gen.h"
38 #include "exec/log.h"
39 
40 #define HELPER_H "helper.h"
41 #include "exec/helper-info.c.inc"
42 #undef  HELPER_H
43 
44 
45 #define DISAS_CRIS 0
46 #if DISAS_CRIS
47 #  define LOG_DIS(...) qemu_log_mask(CPU_LOG_TB_IN_ASM, ## __VA_ARGS__)
48 #else
49 #  define LOG_DIS(...) do { } while (0)
50 #endif
51 
52 #define D(x)
53 #define BUG() (gen_BUG(dc, __FILE__, __LINE__))
54 #define BUG_ON(x) ({if (x) BUG();})
55 
56 /*
57  * Target-specific is_jmp field values
58  */
59 /* Only pc was modified dynamically */
60 #define DISAS_JUMP          DISAS_TARGET_0
61 /* Cpu state was modified dynamically, including pc */
62 #define DISAS_UPDATE        DISAS_TARGET_1
63 /* Cpu state was modified dynamically, excluding pc -- use npc */
64 #define DISAS_UPDATE_NEXT   DISAS_TARGET_2
65 /* PC update for delayed branch, see cpustate_changed otherwise */
66 #define DISAS_DBRANCH       DISAS_TARGET_3
67 
68 /* Used by the decoder.  */
69 #define EXTRACT_FIELD(src, start, end) \
70             (((src) >> start) & ((1 << (end - start + 1)) - 1))
71 
72 #define CC_MASK_NZ 0xc
73 #define CC_MASK_NZV 0xe
74 #define CC_MASK_NZVC 0xf
75 #define CC_MASK_RNZV 0x10e
76 
77 static TCGv cpu_R[16];
78 static TCGv cpu_PR[16];
79 static TCGv cc_x;
80 static TCGv cc_src;
81 static TCGv cc_dest;
82 static TCGv cc_result;
83 static TCGv cc_op;
84 static TCGv cc_size;
85 static TCGv cc_mask;
86 
87 static TCGv env_btaken;
88 static TCGv env_btarget;
89 static TCGv env_pc;
90 
91 /* This is the state at translation time.  */
92 typedef struct DisasContext {
93     DisasContextBase base;
94 
95     CRISCPU *cpu;
96     target_ulong pc, ppc;
97 
98     /* Decoder.  */
99         unsigned int (*decoder)(CPUCRISState *env, struct DisasContext *dc);
100     uint32_t ir;
101     uint32_t opcode;
102     unsigned int op1;
103     unsigned int op2;
104     unsigned int zsize, zzsize;
105     unsigned int mode;
106     unsigned int postinc;
107 
108     unsigned int size;
109     unsigned int src;
110     unsigned int dst;
111     unsigned int cond;
112 
113     int update_cc;
114     int cc_op;
115     int cc_size;
116     uint32_t cc_mask;
117 
118     int cc_size_uptodate; /* -1 invalid or last written value.  */
119 
120     int cc_x_uptodate;  /* 1 - ccs, 2 - known | X_FLAG. 0 not up-to-date.  */
121     int flags_uptodate; /* Whether or not $ccs is up-to-date.  */
122     int flags_x;
123 
124     int clear_x; /* Clear x after this insn?  */
125     int clear_prefix; /* Clear prefix after this insn?  */
126     int clear_locked_irq; /* Clear the irq lockout.  */
127     int cpustate_changed;
128     unsigned int tb_flags; /* tb dependent flags.  */
129 
130 #define JMP_NOJMP     0
131 #define JMP_DIRECT    1
132 #define JMP_DIRECT_CC 2
133 #define JMP_INDIRECT  3
134     int jmp; /* 0=nojmp, 1=direct, 2=indirect.  */
135     uint32_t jmp_pc;
136 
137     int delayed_branch;
138 } DisasContext;
139 
140 static void gen_BUG(DisasContext *dc, const char *file, int line)
141 {
142     cpu_abort(CPU(dc->cpu), "%s:%d pc=%x\n", file, line, dc->pc);
143 }
144 
145 static const char * const regnames_v32[] =
146 {
147     "$r0", "$r1", "$r2", "$r3",
148     "$r4", "$r5", "$r6", "$r7",
149     "$r8", "$r9", "$r10", "$r11",
150     "$r12", "$r13", "$sp", "$acr",
151 };
152 
153 static const char * const pregnames_v32[] =
154 {
155     "$bz", "$vr", "$pid", "$srs",
156     "$wz", "$exs", "$eda", "$mof",
157     "$dz", "$ebp", "$erp", "$srp",
158     "$nrp", "$ccs", "$usp", "$spc",
159 };
160 
161 /* We need this table to handle preg-moves with implicit width.  */
162 static const int preg_sizes[] = {
163     1, /* bz.  */
164     1, /* vr.  */
165     4, /* pid.  */
166     1, /* srs.  */
167     2, /* wz.  */
168     4, 4, 4,
169     4, 4, 4, 4,
170     4, 4, 4, 4,
171 };
172 
173 #define t_gen_mov_TN_env(tn, member) \
174     tcg_gen_ld_tl(tn, cpu_env, offsetof(CPUCRISState, member))
175 #define t_gen_mov_env_TN(member, tn) \
176     tcg_gen_st_tl(tn, cpu_env, offsetof(CPUCRISState, member))
177 #define t_gen_movi_env_TN(member, c) \
178     t_gen_mov_env_TN(member, tcg_constant_tl(c))
179 
180 static inline void t_gen_mov_TN_preg(TCGv tn, int r)
181 {
182     assert(r >= 0 && r <= 15);
183     if (r == PR_BZ || r == PR_WZ || r == PR_DZ) {
184         tcg_gen_movi_tl(tn, 0);
185     } else if (r == PR_VR) {
186         tcg_gen_movi_tl(tn, 32);
187     } else {
188         tcg_gen_mov_tl(tn, cpu_PR[r]);
189     }
190 }
191 static inline void t_gen_mov_preg_TN(DisasContext *dc, int r, TCGv tn)
192 {
193     assert(r >= 0 && r <= 15);
194     if (r == PR_BZ || r == PR_WZ || r == PR_DZ) {
195         return;
196     } else if (r == PR_SRS) {
197         tcg_gen_andi_tl(cpu_PR[r], tn, 3);
198     } else {
199         if (r == PR_PID) {
200             gen_helper_tlb_flush_pid(cpu_env, tn);
201         }
202         if (dc->tb_flags & S_FLAG && r == PR_SPC) {
203             gen_helper_spc_write(cpu_env, tn);
204         } else if (r == PR_CCS) {
205             dc->cpustate_changed = 1;
206         }
207         tcg_gen_mov_tl(cpu_PR[r], tn);
208     }
209 }
210 
211 /* Sign extend at translation time.  */
212 static int sign_extend(unsigned int val, unsigned int width)
213 {
214     int sval;
215 
216     /* LSL.  */
217     val <<= 31 - width;
218     sval = val;
219     /* ASR.  */
220     sval >>= 31 - width;
221     return sval;
222 }
223 
224 static int cris_fetch(CPUCRISState *env, DisasContext *dc, uint32_t addr,
225               unsigned int size, unsigned int sign)
226 {
227     int r;
228 
229     switch (size) {
230     case 4:
231     {
232         r = cpu_ldl_code(env, addr);
233         break;
234     }
235     case 2:
236     {
237         if (sign) {
238             r = cpu_ldsw_code(env, addr);
239         } else {
240             r = cpu_lduw_code(env, addr);
241         }
242         break;
243     }
244     case 1:
245     {
246         if (sign) {
247             r = cpu_ldsb_code(env, addr);
248         } else {
249             r = cpu_ldub_code(env, addr);
250         }
251         break;
252     }
253     default:
254         cpu_abort(CPU(dc->cpu), "Invalid fetch size %d\n", size);
255         break;
256     }
257     return r;
258 }
259 
260 static void cris_lock_irq(DisasContext *dc)
261 {
262     dc->clear_locked_irq = 0;
263     t_gen_movi_env_TN(locked_irq, 1);
264 }
265 
266 static inline void t_gen_raise_exception(uint32_t index)
267 {
268     gen_helper_raise_exception(cpu_env, tcg_constant_i32(index));
269 }
270 
271 static void t_gen_lsl(TCGv d, TCGv a, TCGv b)
272 {
273     TCGv t0, t_31;
274 
275     t0 = tcg_temp_new();
276     t_31 = tcg_constant_tl(31);
277     tcg_gen_shl_tl(d, a, b);
278 
279     tcg_gen_sub_tl(t0, t_31, b);
280     tcg_gen_sar_tl(t0, t0, t_31);
281     tcg_gen_and_tl(t0, t0, d);
282     tcg_gen_xor_tl(d, d, t0);
283 }
284 
285 static void t_gen_lsr(TCGv d, TCGv a, TCGv b)
286 {
287     TCGv t0, t_31;
288 
289     t0 = tcg_temp_new();
290     t_31 = tcg_temp_new();
291     tcg_gen_shr_tl(d, a, b);
292 
293     tcg_gen_movi_tl(t_31, 31);
294     tcg_gen_sub_tl(t0, t_31, b);
295     tcg_gen_sar_tl(t0, t0, t_31);
296     tcg_gen_and_tl(t0, t0, d);
297     tcg_gen_xor_tl(d, d, t0);
298 }
299 
300 static void t_gen_asr(TCGv d, TCGv a, TCGv b)
301 {
302     TCGv t0, t_31;
303 
304     t0 = tcg_temp_new();
305     t_31 = tcg_temp_new();
306     tcg_gen_sar_tl(d, a, b);
307 
308     tcg_gen_movi_tl(t_31, 31);
309     tcg_gen_sub_tl(t0, t_31, b);
310     tcg_gen_sar_tl(t0, t0, t_31);
311     tcg_gen_or_tl(d, d, t0);
312 }
313 
314 static void t_gen_cris_dstep(TCGv d, TCGv a, TCGv b)
315 {
316     TCGv t = tcg_temp_new();
317 
318     /*
319      * d <<= 1
320      * if (d >= s)
321      *    d -= s;
322      */
323     tcg_gen_shli_tl(d, a, 1);
324     tcg_gen_sub_tl(t, d, b);
325     tcg_gen_movcond_tl(TCG_COND_GEU, d, d, b, t, d);
326 }
327 
328 static void t_gen_cris_mstep(TCGv d, TCGv a, TCGv b, TCGv ccs)
329 {
330     TCGv t;
331 
332     /*
333      * d <<= 1
334      * if (n)
335      *    d += s;
336      */
337     t = tcg_temp_new();
338     tcg_gen_shli_tl(d, a, 1);
339     tcg_gen_shli_tl(t, ccs, 31 - 3);
340     tcg_gen_sari_tl(t, t, 31);
341     tcg_gen_and_tl(t, t, b);
342     tcg_gen_add_tl(d, d, t);
343 }
344 
345 /* Extended arithmetic on CRIS.  */
346 static inline void t_gen_add_flag(TCGv d, int flag)
347 {
348     TCGv c;
349 
350     c = tcg_temp_new();
351     t_gen_mov_TN_preg(c, PR_CCS);
352     /* Propagate carry into d.  */
353     tcg_gen_andi_tl(c, c, 1 << flag);
354     if (flag) {
355         tcg_gen_shri_tl(c, c, flag);
356     }
357     tcg_gen_add_tl(d, d, c);
358 }
359 
360 static inline void t_gen_addx_carry(DisasContext *dc, TCGv d)
361 {
362     if (dc->flags_x) {
363         TCGv c = tcg_temp_new();
364 
365         t_gen_mov_TN_preg(c, PR_CCS);
366         /* C flag is already at bit 0.  */
367         tcg_gen_andi_tl(c, c, C_FLAG);
368         tcg_gen_add_tl(d, d, c);
369     }
370 }
371 
372 static inline void t_gen_subx_carry(DisasContext *dc, TCGv d)
373 {
374     if (dc->flags_x) {
375         TCGv c = tcg_temp_new();
376 
377         t_gen_mov_TN_preg(c, PR_CCS);
378         /* C flag is already at bit 0.  */
379         tcg_gen_andi_tl(c, c, C_FLAG);
380         tcg_gen_sub_tl(d, d, c);
381     }
382 }
383 
384 /* Swap the two bytes within each half word of the s operand.
385    T0 = ((T0 << 8) & 0xff00ff00) | ((T0 >> 8) & 0x00ff00ff)  */
386 static inline void t_gen_swapb(TCGv d, TCGv s)
387 {
388     TCGv t, org_s;
389 
390     t = tcg_temp_new();
391     org_s = tcg_temp_new();
392 
393     /* d and s may refer to the same object.  */
394     tcg_gen_mov_tl(org_s, s);
395     tcg_gen_shli_tl(t, org_s, 8);
396     tcg_gen_andi_tl(d, t, 0xff00ff00);
397     tcg_gen_shri_tl(t, org_s, 8);
398     tcg_gen_andi_tl(t, t, 0x00ff00ff);
399     tcg_gen_or_tl(d, d, t);
400 }
401 
402 /* Swap the halfwords of the s operand.  */
403 static inline void t_gen_swapw(TCGv d, TCGv s)
404 {
405     TCGv t;
406     /* d and s refer the same object.  */
407     t = tcg_temp_new();
408     tcg_gen_mov_tl(t, s);
409     tcg_gen_shli_tl(d, t, 16);
410     tcg_gen_shri_tl(t, t, 16);
411     tcg_gen_or_tl(d, d, t);
412 }
413 
414 /*
415  * Reverse the bits within each byte.
416  *
417  *  T0 = ((T0 << 7) & 0x80808080)
418  *     | ((T0 << 5) & 0x40404040)
419  *     | ((T0 << 3) & 0x20202020)
420  *     | ((T0 << 1) & 0x10101010)
421  *     | ((T0 >> 1) & 0x08080808)
422  *     | ((T0 >> 3) & 0x04040404)
423  *     | ((T0 >> 5) & 0x02020202)
424  *     | ((T0 >> 7) & 0x01010101);
425  */
426 static void t_gen_swapr(TCGv d, TCGv s)
427 {
428     static const struct {
429         int shift; /* LSL when positive, LSR when negative.  */
430         uint32_t mask;
431     } bitrev[] = {
432         {7, 0x80808080},
433         {5, 0x40404040},
434         {3, 0x20202020},
435         {1, 0x10101010},
436         {-1, 0x08080808},
437         {-3, 0x04040404},
438         {-5, 0x02020202},
439         {-7, 0x01010101}
440     };
441     int i;
442     TCGv t, org_s;
443 
444     /* d and s refer the same object.  */
445     t = tcg_temp_new();
446     org_s = tcg_temp_new();
447     tcg_gen_mov_tl(org_s, s);
448 
449     tcg_gen_shli_tl(t, org_s,  bitrev[0].shift);
450     tcg_gen_andi_tl(d, t,  bitrev[0].mask);
451     for (i = 1; i < ARRAY_SIZE(bitrev); i++) {
452         if (bitrev[i].shift >= 0) {
453             tcg_gen_shli_tl(t, org_s,  bitrev[i].shift);
454         } else {
455             tcg_gen_shri_tl(t, org_s,  -bitrev[i].shift);
456         }
457         tcg_gen_andi_tl(t, t,  bitrev[i].mask);
458         tcg_gen_or_tl(d, d, t);
459     }
460 }
461 
462 static bool use_goto_tb(DisasContext *dc, target_ulong dest)
463 {
464     return translator_use_goto_tb(&dc->base, dest);
465 }
466 
467 static void gen_goto_tb(DisasContext *dc, int n, target_ulong dest)
468 {
469     if (use_goto_tb(dc, dest)) {
470         tcg_gen_goto_tb(n);
471         tcg_gen_movi_tl(env_pc, dest);
472         tcg_gen_exit_tb(dc->base.tb, n);
473     } else {
474         tcg_gen_movi_tl(env_pc, dest);
475         tcg_gen_lookup_and_goto_ptr();
476     }
477 }
478 
479 static inline void cris_clear_x_flag(DisasContext *dc)
480 {
481     if (dc->flags_x) {
482         dc->flags_uptodate = 0;
483     }
484     dc->flags_x = 0;
485 }
486 
487 static void cris_flush_cc_state(DisasContext *dc)
488 {
489     if (dc->cc_size_uptodate != dc->cc_size) {
490         tcg_gen_movi_tl(cc_size, dc->cc_size);
491         dc->cc_size_uptodate = dc->cc_size;
492     }
493     tcg_gen_movi_tl(cc_op, dc->cc_op);
494     tcg_gen_movi_tl(cc_mask, dc->cc_mask);
495 }
496 
497 static void cris_evaluate_flags(DisasContext *dc)
498 {
499     if (dc->flags_uptodate) {
500         return;
501     }
502 
503     cris_flush_cc_state(dc);
504 
505     switch (dc->cc_op) {
506     case CC_OP_MCP:
507         gen_helper_evaluate_flags_mcp(cpu_PR[PR_CCS], cpu_env,
508                 cpu_PR[PR_CCS], cc_src,
509                 cc_dest, cc_result);
510         break;
511     case CC_OP_MULS:
512         gen_helper_evaluate_flags_muls(cpu_PR[PR_CCS], cpu_env,
513                 cpu_PR[PR_CCS], cc_result,
514                 cpu_PR[PR_MOF]);
515         break;
516     case CC_OP_MULU:
517         gen_helper_evaluate_flags_mulu(cpu_PR[PR_CCS], cpu_env,
518                 cpu_PR[PR_CCS], cc_result,
519                 cpu_PR[PR_MOF]);
520         break;
521     case CC_OP_MOVE:
522     case CC_OP_AND:
523     case CC_OP_OR:
524     case CC_OP_XOR:
525     case CC_OP_ASR:
526     case CC_OP_LSR:
527     case CC_OP_LSL:
528         switch (dc->cc_size) {
529         case 4:
530             gen_helper_evaluate_flags_move_4(cpu_PR[PR_CCS],
531                     cpu_env, cpu_PR[PR_CCS], cc_result);
532             break;
533         case 2:
534             gen_helper_evaluate_flags_move_2(cpu_PR[PR_CCS],
535                     cpu_env, cpu_PR[PR_CCS], cc_result);
536             break;
537         default:
538             gen_helper_evaluate_flags(cpu_env);
539             break;
540         }
541         break;
542     case CC_OP_FLAGS:
543         /* live.  */
544         break;
545     case CC_OP_SUB:
546     case CC_OP_CMP:
547         if (dc->cc_size == 4) {
548             gen_helper_evaluate_flags_sub_4(cpu_PR[PR_CCS], cpu_env,
549                     cpu_PR[PR_CCS], cc_src, cc_dest, cc_result);
550         } else {
551             gen_helper_evaluate_flags(cpu_env);
552         }
553 
554         break;
555     default:
556         switch (dc->cc_size) {
557         case 4:
558             gen_helper_evaluate_flags_alu_4(cpu_PR[PR_CCS], cpu_env,
559                     cpu_PR[PR_CCS], cc_src, cc_dest, cc_result);
560             break;
561         default:
562             gen_helper_evaluate_flags(cpu_env);
563             break;
564         }
565         break;
566     }
567 
568     if (dc->flags_x) {
569         tcg_gen_ori_tl(cpu_PR[PR_CCS], cpu_PR[PR_CCS], X_FLAG);
570     } else if (dc->cc_op == CC_OP_FLAGS) {
571         tcg_gen_andi_tl(cpu_PR[PR_CCS], cpu_PR[PR_CCS], ~X_FLAG);
572     }
573     dc->flags_uptodate = 1;
574 }
575 
576 static void cris_cc_mask(DisasContext *dc, unsigned int mask)
577 {
578     uint32_t ovl;
579 
580     if (!mask) {
581         dc->update_cc = 0;
582         return;
583     }
584 
585     /* Check if we need to evaluate the condition codes due to
586        CC overlaying.  */
587     ovl = (dc->cc_mask ^ mask) & ~mask;
588     if (ovl) {
589         /* TODO: optimize this case. It trigs all the time.  */
590         cris_evaluate_flags(dc);
591     }
592     dc->cc_mask = mask;
593     dc->update_cc = 1;
594 }
595 
596 static void cris_update_cc_op(DisasContext *dc, int op, int size)
597 {
598     dc->cc_op = op;
599     dc->cc_size = size;
600     dc->flags_uptodate = 0;
601 }
602 
603 static inline void cris_update_cc_x(DisasContext *dc)
604 {
605     /* Save the x flag state at the time of the cc snapshot.  */
606     if (dc->cc_x_uptodate == (2 | dc->flags_x)) {
607         return;
608     }
609     tcg_gen_movi_tl(cc_x, dc->flags_x);
610     dc->cc_x_uptodate = 2 | dc->flags_x;
611 }
612 
613 /* Update cc prior to executing ALU op. Needs source operands untouched.  */
614 static void cris_pre_alu_update_cc(DisasContext *dc, int op,
615                    TCGv dst, TCGv src, int size)
616 {
617     if (dc->update_cc) {
618         cris_update_cc_op(dc, op, size);
619         tcg_gen_mov_tl(cc_src, src);
620 
621         if (op != CC_OP_MOVE
622             && op != CC_OP_AND
623             && op != CC_OP_OR
624             && op != CC_OP_XOR
625             && op != CC_OP_ASR
626             && op != CC_OP_LSR
627             && op != CC_OP_LSL) {
628             tcg_gen_mov_tl(cc_dest, dst);
629         }
630 
631         cris_update_cc_x(dc);
632     }
633 }
634 
635 /* Update cc after executing ALU op. needs the result.  */
636 static inline void cris_update_result(DisasContext *dc, TCGv res)
637 {
638     if (dc->update_cc) {
639         tcg_gen_mov_tl(cc_result, res);
640     }
641 }
642 
643 /* Returns one if the write back stage should execute.  */
644 static void cris_alu_op_exec(DisasContext *dc, int op,
645                    TCGv dst, TCGv a, TCGv b, int size)
646 {
647     /* Emit the ALU insns.  */
648     switch (op) {
649     case CC_OP_ADD:
650         tcg_gen_add_tl(dst, a, b);
651         /* Extended arithmetic.  */
652         t_gen_addx_carry(dc, dst);
653         break;
654     case CC_OP_ADDC:
655         tcg_gen_add_tl(dst, a, b);
656         t_gen_add_flag(dst, 0); /* C_FLAG.  */
657         break;
658     case CC_OP_MCP:
659         tcg_gen_add_tl(dst, a, b);
660         t_gen_add_flag(dst, 8); /* R_FLAG.  */
661         break;
662     case CC_OP_SUB:
663         tcg_gen_sub_tl(dst, a, b);
664         /* Extended arithmetic.  */
665         t_gen_subx_carry(dc, dst);
666         break;
667     case CC_OP_MOVE:
668         tcg_gen_mov_tl(dst, b);
669         break;
670     case CC_OP_OR:
671         tcg_gen_or_tl(dst, a, b);
672         break;
673     case CC_OP_AND:
674         tcg_gen_and_tl(dst, a, b);
675         break;
676     case CC_OP_XOR:
677         tcg_gen_xor_tl(dst, a, b);
678         break;
679     case CC_OP_LSL:
680         t_gen_lsl(dst, a, b);
681         break;
682     case CC_OP_LSR:
683         t_gen_lsr(dst, a, b);
684         break;
685     case CC_OP_ASR:
686         t_gen_asr(dst, a, b);
687         break;
688     case CC_OP_NEG:
689         tcg_gen_neg_tl(dst, b);
690         /* Extended arithmetic.  */
691         t_gen_subx_carry(dc, dst);
692         break;
693     case CC_OP_LZ:
694         tcg_gen_clzi_tl(dst, b, TARGET_LONG_BITS);
695         break;
696     case CC_OP_MULS:
697         tcg_gen_muls2_tl(dst, cpu_PR[PR_MOF], a, b);
698         break;
699     case CC_OP_MULU:
700         tcg_gen_mulu2_tl(dst, cpu_PR[PR_MOF], a, b);
701         break;
702     case CC_OP_DSTEP:
703         t_gen_cris_dstep(dst, a, b);
704         break;
705     case CC_OP_MSTEP:
706         t_gen_cris_mstep(dst, a, b, cpu_PR[PR_CCS]);
707         break;
708     case CC_OP_BOUND:
709         tcg_gen_movcond_tl(TCG_COND_LEU, dst, a, b, a, b);
710         break;
711     case CC_OP_CMP:
712         tcg_gen_sub_tl(dst, a, b);
713         /* Extended arithmetic.  */
714         t_gen_subx_carry(dc, dst);
715         break;
716     default:
717         qemu_log_mask(LOG_GUEST_ERROR, "illegal ALU op.\n");
718         BUG();
719         break;
720     }
721 
722     if (size == 1) {
723         tcg_gen_andi_tl(dst, dst, 0xff);
724     } else if (size == 2) {
725         tcg_gen_andi_tl(dst, dst, 0xffff);
726     }
727 }
728 
729 static void cris_alu(DisasContext *dc, int op,
730                    TCGv d, TCGv op_a, TCGv op_b, int size)
731 {
732     TCGv tmp;
733     int writeback;
734 
735     writeback = 1;
736 
737     if (op == CC_OP_CMP) {
738         tmp = tcg_temp_new();
739         writeback = 0;
740     } else if (size == 4) {
741         tmp = d;
742         writeback = 0;
743     } else {
744         tmp = tcg_temp_new();
745     }
746 
747 
748     cris_pre_alu_update_cc(dc, op, op_a, op_b, size);
749     cris_alu_op_exec(dc, op, tmp, op_a, op_b, size);
750     cris_update_result(dc, tmp);
751 
752     /* Writeback.  */
753     if (writeback) {
754         if (size == 1) {
755             tcg_gen_andi_tl(d, d, ~0xff);
756         } else {
757             tcg_gen_andi_tl(d, d, ~0xffff);
758         }
759         tcg_gen_or_tl(d, d, tmp);
760     }
761 }
762 
763 static int arith_cc(DisasContext *dc)
764 {
765     if (dc->update_cc) {
766         switch (dc->cc_op) {
767         case CC_OP_ADDC: return 1;
768         case CC_OP_ADD: return 1;
769         case CC_OP_SUB: return 1;
770         case CC_OP_DSTEP: return 1;
771         case CC_OP_LSL: return 1;
772         case CC_OP_LSR: return 1;
773         case CC_OP_ASR: return 1;
774         case CC_OP_CMP: return 1;
775         case CC_OP_NEG: return 1;
776         case CC_OP_OR: return 1;
777         case CC_OP_AND: return 1;
778         case CC_OP_XOR: return 1;
779         case CC_OP_MULU: return 1;
780         case CC_OP_MULS: return 1;
781         default:
782             return 0;
783         }
784     }
785     return 0;
786 }
787 
788 static void gen_tst_cc (DisasContext *dc, TCGv cc, int cond)
789 {
790     int arith_opt, move_opt;
791 
792     /* TODO: optimize more condition codes.  */
793 
794     /*
795      * If the flags are live, we've gotta look into the bits of CCS.
796      * Otherwise, if we just did an arithmetic operation we try to
797      * evaluate the condition code faster.
798      *
799      * When this function is done, T0 should be non-zero if the condition
800      * code is true.
801      */
802     arith_opt = arith_cc(dc) && !dc->flags_uptodate;
803     move_opt = (dc->cc_op == CC_OP_MOVE);
804     switch (cond) {
805     case CC_EQ:
806         if ((arith_opt || move_opt)
807                 && dc->cc_x_uptodate != (2 | X_FLAG)) {
808             tcg_gen_setcondi_tl(TCG_COND_EQ, cc, cc_result, 0);
809         } else {
810             cris_evaluate_flags(dc);
811             tcg_gen_andi_tl(cc,
812                     cpu_PR[PR_CCS], Z_FLAG);
813         }
814         break;
815     case CC_NE:
816         if ((arith_opt || move_opt)
817                 && dc->cc_x_uptodate != (2 | X_FLAG)) {
818             tcg_gen_mov_tl(cc, cc_result);
819         } else {
820             cris_evaluate_flags(dc);
821             tcg_gen_xori_tl(cc, cpu_PR[PR_CCS],
822                     Z_FLAG);
823             tcg_gen_andi_tl(cc, cc, Z_FLAG);
824         }
825         break;
826     case CC_CS:
827         cris_evaluate_flags(dc);
828         tcg_gen_andi_tl(cc, cpu_PR[PR_CCS], C_FLAG);
829         break;
830     case CC_CC:
831         cris_evaluate_flags(dc);
832         tcg_gen_xori_tl(cc, cpu_PR[PR_CCS], C_FLAG);
833         tcg_gen_andi_tl(cc, cc, C_FLAG);
834         break;
835     case CC_VS:
836         cris_evaluate_flags(dc);
837         tcg_gen_andi_tl(cc, cpu_PR[PR_CCS], V_FLAG);
838         break;
839     case CC_VC:
840         cris_evaluate_flags(dc);
841         tcg_gen_xori_tl(cc, cpu_PR[PR_CCS],
842                 V_FLAG);
843         tcg_gen_andi_tl(cc, cc, V_FLAG);
844         break;
845     case CC_PL:
846         if (arith_opt || move_opt) {
847             int bits = 31;
848 
849             if (dc->cc_size == 1) {
850                 bits = 7;
851             } else if (dc->cc_size == 2) {
852                 bits = 15;
853             }
854 
855             tcg_gen_shri_tl(cc, cc_result, bits);
856             tcg_gen_xori_tl(cc, cc, 1);
857         } else {
858             cris_evaluate_flags(dc);
859             tcg_gen_xori_tl(cc, cpu_PR[PR_CCS],
860                     N_FLAG);
861             tcg_gen_andi_tl(cc, cc, N_FLAG);
862         }
863         break;
864     case CC_MI:
865         if (arith_opt || move_opt) {
866             int bits = 31;
867 
868             if (dc->cc_size == 1) {
869                 bits = 7;
870             } else if (dc->cc_size == 2) {
871                 bits = 15;
872             }
873 
874             tcg_gen_shri_tl(cc, cc_result, bits);
875             tcg_gen_andi_tl(cc, cc, 1);
876         } else {
877             cris_evaluate_flags(dc);
878             tcg_gen_andi_tl(cc, cpu_PR[PR_CCS],
879                     N_FLAG);
880         }
881         break;
882     case CC_LS:
883         cris_evaluate_flags(dc);
884         tcg_gen_andi_tl(cc, cpu_PR[PR_CCS],
885                 C_FLAG | Z_FLAG);
886         break;
887     case CC_HI:
888         cris_evaluate_flags(dc);
889         {
890             TCGv tmp;
891 
892             tmp = tcg_temp_new();
893             tcg_gen_xori_tl(tmp, cpu_PR[PR_CCS],
894                     C_FLAG | Z_FLAG);
895             /* Overlay the C flag on top of the Z.  */
896             tcg_gen_shli_tl(cc, tmp, 2);
897             tcg_gen_and_tl(cc, tmp, cc);
898             tcg_gen_andi_tl(cc, cc, Z_FLAG);
899         }
900         break;
901     case CC_GE:
902         cris_evaluate_flags(dc);
903         /* Overlay the V flag on top of the N.  */
904         tcg_gen_shli_tl(cc, cpu_PR[PR_CCS], 2);
905         tcg_gen_xor_tl(cc,
906                 cpu_PR[PR_CCS], cc);
907         tcg_gen_andi_tl(cc, cc, N_FLAG);
908         tcg_gen_xori_tl(cc, cc, N_FLAG);
909         break;
910     case CC_LT:
911         cris_evaluate_flags(dc);
912         /* Overlay the V flag on top of the N.  */
913         tcg_gen_shli_tl(cc, cpu_PR[PR_CCS], 2);
914         tcg_gen_xor_tl(cc,
915                 cpu_PR[PR_CCS], cc);
916         tcg_gen_andi_tl(cc, cc, N_FLAG);
917         break;
918     case CC_GT:
919         cris_evaluate_flags(dc);
920         {
921             TCGv n, z;
922 
923             n = tcg_temp_new();
924             z = tcg_temp_new();
925 
926             /* To avoid a shift we overlay everything on
927                    the V flag.  */
928             tcg_gen_shri_tl(n, cpu_PR[PR_CCS], 2);
929             tcg_gen_shri_tl(z, cpu_PR[PR_CCS], 1);
930             /* invert Z.  */
931             tcg_gen_xori_tl(z, z, 2);
932 
933             tcg_gen_xor_tl(n, n, cpu_PR[PR_CCS]);
934             tcg_gen_xori_tl(n, n, 2);
935             tcg_gen_and_tl(cc, z, n);
936             tcg_gen_andi_tl(cc, cc, 2);
937         }
938         break;
939     case CC_LE:
940         cris_evaluate_flags(dc);
941         {
942             TCGv n, z;
943 
944             n = tcg_temp_new();
945             z = tcg_temp_new();
946 
947             /* To avoid a shift we overlay everything on
948                    the V flag.  */
949             tcg_gen_shri_tl(n, cpu_PR[PR_CCS], 2);
950             tcg_gen_shri_tl(z, cpu_PR[PR_CCS], 1);
951 
952             tcg_gen_xor_tl(n, n, cpu_PR[PR_CCS]);
953             tcg_gen_or_tl(cc, z, n);
954             tcg_gen_andi_tl(cc, cc, 2);
955         }
956         break;
957     case CC_P:
958         cris_evaluate_flags(dc);
959         tcg_gen_andi_tl(cc, cpu_PR[PR_CCS], P_FLAG);
960         break;
961     case CC_A:
962         tcg_gen_movi_tl(cc, 1);
963         break;
964     default:
965         BUG();
966         break;
967     };
968 }
969 
970 static void cris_store_direct_jmp(DisasContext *dc)
971 {
972     /* Store the direct jmp state into the cpu-state.  */
973     if (dc->jmp == JMP_DIRECT || dc->jmp == JMP_DIRECT_CC) {
974         if (dc->jmp == JMP_DIRECT) {
975             tcg_gen_movi_tl(env_btaken, 1);
976         }
977         tcg_gen_movi_tl(env_btarget, dc->jmp_pc);
978         dc->jmp = JMP_INDIRECT;
979     }
980 }
981 
982 static void cris_prepare_cc_branch (DisasContext *dc,
983                     int offset, int cond)
984 {
985     /* This helps us re-schedule the micro-code to insns in delay-slots
986        before the actual jump.  */
987     dc->delayed_branch = 2;
988     dc->jmp = JMP_DIRECT_CC;
989     dc->jmp_pc = dc->pc + offset;
990 
991     gen_tst_cc(dc, env_btaken, cond);
992     tcg_gen_movi_tl(env_btarget, dc->jmp_pc);
993 }
994 
995 
996 /* jumps, when the dest is in a live reg for example. Direct should be set
997    when the dest addr is constant to allow tb chaining.  */
998 static inline void cris_prepare_jmp (DisasContext *dc, unsigned int type)
999 {
1000     /* This helps us re-schedule the micro-code to insns in delay-slots
1001        before the actual jump.  */
1002     dc->delayed_branch = 2;
1003     dc->jmp = type;
1004     if (type == JMP_INDIRECT) {
1005         tcg_gen_movi_tl(env_btaken, 1);
1006     }
1007 }
1008 
1009 static void gen_load64(DisasContext *dc, TCGv_i64 dst, TCGv addr)
1010 {
1011     int mem_index = cpu_mmu_index(&dc->cpu->env, false);
1012 
1013     /* If we get a fault on a delayslot we must keep the jmp state in
1014        the cpu-state to be able to re-execute the jmp.  */
1015     if (dc->delayed_branch == 1) {
1016         cris_store_direct_jmp(dc);
1017     }
1018 
1019     tcg_gen_qemu_ld_i64(dst, addr, mem_index, MO_TEUQ);
1020 }
1021 
1022 static void gen_load(DisasContext *dc, TCGv dst, TCGv addr,
1023              unsigned int size, int sign)
1024 {
1025     int mem_index = cpu_mmu_index(&dc->cpu->env, false);
1026 
1027     /* If we get a fault on a delayslot we must keep the jmp state in
1028        the cpu-state to be able to re-execute the jmp.  */
1029     if (dc->delayed_branch == 1) {
1030         cris_store_direct_jmp(dc);
1031     }
1032 
1033     tcg_gen_qemu_ld_tl(dst, addr, mem_index,
1034                        MO_TE + ctz32(size) + (sign ? MO_SIGN : 0));
1035 }
1036 
1037 static void gen_store (DisasContext *dc, TCGv addr, TCGv val,
1038                unsigned int size)
1039 {
1040     int mem_index = cpu_mmu_index(&dc->cpu->env, false);
1041 
1042     /* If we get a fault on a delayslot we must keep the jmp state in
1043        the cpu-state to be able to re-execute the jmp.  */
1044     if (dc->delayed_branch == 1) {
1045         cris_store_direct_jmp(dc);
1046     }
1047 
1048 
1049     /* Conditional writes. We only support the kind were X and P are known
1050        at translation time.  */
1051     if (dc->flags_x && (dc->tb_flags & P_FLAG)) {
1052         dc->postinc = 0;
1053         cris_evaluate_flags(dc);
1054         tcg_gen_ori_tl(cpu_PR[PR_CCS], cpu_PR[PR_CCS], C_FLAG);
1055         return;
1056     }
1057 
1058     tcg_gen_qemu_st_tl(val, addr, mem_index, MO_TE + ctz32(size));
1059 
1060     if (dc->flags_x) {
1061         cris_evaluate_flags(dc);
1062         tcg_gen_andi_tl(cpu_PR[PR_CCS], cpu_PR[PR_CCS], ~C_FLAG);
1063     }
1064 }
1065 
1066 static inline void t_gen_sext(TCGv d, TCGv s, int size)
1067 {
1068     if (size == 1) {
1069         tcg_gen_ext8s_i32(d, s);
1070     } else if (size == 2) {
1071         tcg_gen_ext16s_i32(d, s);
1072     } else {
1073         tcg_gen_mov_tl(d, s);
1074     }
1075 }
1076 
1077 static inline void t_gen_zext(TCGv d, TCGv s, int size)
1078 {
1079     if (size == 1) {
1080         tcg_gen_ext8u_i32(d, s);
1081     } else if (size == 2) {
1082         tcg_gen_ext16u_i32(d, s);
1083     } else {
1084         tcg_gen_mov_tl(d, s);
1085     }
1086 }
1087 
1088 #if DISAS_CRIS
1089 static char memsize_char(int size)
1090 {
1091     switch (size) {
1092     case 1: return 'b';
1093     case 2: return 'w';
1094     case 4: return 'd';
1095     default:
1096         return 'x';
1097     }
1098 }
1099 #endif
1100 
1101 static inline unsigned int memsize_z(DisasContext *dc)
1102 {
1103     return dc->zsize + 1;
1104 }
1105 
1106 static inline unsigned int memsize_zz(DisasContext *dc)
1107 {
1108     switch (dc->zzsize) {
1109     case 0: return 1;
1110     case 1: return 2;
1111     default:
1112         return 4;
1113     }
1114 }
1115 
1116 static inline void do_postinc (DisasContext *dc, int size)
1117 {
1118     if (dc->postinc) {
1119         tcg_gen_addi_tl(cpu_R[dc->op1], cpu_R[dc->op1], size);
1120     }
1121 }
1122 
1123 static inline void dec_prep_move_r(DisasContext *dc, int rs, int rd,
1124                    int size, int s_ext, TCGv dst)
1125 {
1126     if (s_ext) {
1127         t_gen_sext(dst, cpu_R[rs], size);
1128     } else {
1129         t_gen_zext(dst, cpu_R[rs], size);
1130     }
1131 }
1132 
1133 /* Prepare T0 and T1 for a register alu operation.
1134    s_ext decides if the operand1 should be sign-extended or zero-extended when
1135    needed.  */
1136 static void dec_prep_alu_r(DisasContext *dc, int rs, int rd,
1137               int size, int s_ext, TCGv dst, TCGv src)
1138 {
1139     dec_prep_move_r(dc, rs, rd, size, s_ext, src);
1140 
1141     if (s_ext) {
1142         t_gen_sext(dst, cpu_R[rd], size);
1143     } else {
1144         t_gen_zext(dst, cpu_R[rd], size);
1145     }
1146 }
1147 
1148 static int dec_prep_move_m(CPUCRISState *env, DisasContext *dc,
1149                            int s_ext, int memsize, TCGv dst)
1150 {
1151     unsigned int rs;
1152     uint32_t imm;
1153     int is_imm;
1154     int insn_len = 2;
1155 
1156     rs = dc->op1;
1157     is_imm = rs == 15 && dc->postinc;
1158 
1159     /* Load [$rs] onto T1.  */
1160     if (is_imm) {
1161         insn_len = 2 + memsize;
1162         if (memsize == 1) {
1163             insn_len++;
1164         }
1165 
1166         imm = cris_fetch(env, dc, dc->pc + 2, memsize, s_ext);
1167         tcg_gen_movi_tl(dst, imm);
1168         dc->postinc = 0;
1169     } else {
1170         cris_flush_cc_state(dc);
1171         gen_load(dc, dst, cpu_R[rs], memsize, 0);
1172         if (s_ext) {
1173             t_gen_sext(dst, dst, memsize);
1174         } else {
1175             t_gen_zext(dst, dst, memsize);
1176         }
1177     }
1178     return insn_len;
1179 }
1180 
1181 /* Prepare T0 and T1 for a memory + alu operation.
1182    s_ext decides if the operand1 should be sign-extended or zero-extended when
1183    needed.  */
1184 static int dec_prep_alu_m(CPUCRISState *env, DisasContext *dc,
1185                           int s_ext, int memsize, TCGv dst, TCGv src)
1186 {
1187     int insn_len;
1188 
1189     insn_len = dec_prep_move_m(env, dc, s_ext, memsize, src);
1190     tcg_gen_mov_tl(dst, cpu_R[dc->op2]);
1191     return insn_len;
1192 }
1193 
1194 #if DISAS_CRIS
1195 static const char *cc_name(int cc)
1196 {
1197     static const char * const cc_names[16] = {
1198         "cc", "cs", "ne", "eq", "vc", "vs", "pl", "mi",
1199         "ls", "hi", "ge", "lt", "gt", "le", "a", "p"
1200     };
1201     assert(cc < 16);
1202     return cc_names[cc];
1203 }
1204 #endif
1205 
1206 /* Start of insn decoders.  */
1207 
1208 static int dec_bccq(CPUCRISState *env, DisasContext *dc)
1209 {
1210     int32_t offset;
1211     int sign;
1212     uint32_t cond = dc->op2;
1213 
1214     offset = EXTRACT_FIELD(dc->ir, 1, 7);
1215     sign = EXTRACT_FIELD(dc->ir, 0, 0);
1216 
1217     offset *= 2;
1218     offset |= sign << 8;
1219     offset = sign_extend(offset, 8);
1220 
1221     LOG_DIS("b%s %x\n", cc_name(cond), dc->pc + offset);
1222 
1223     /* op2 holds the condition-code.  */
1224     cris_cc_mask(dc, 0);
1225     cris_prepare_cc_branch(dc, offset, cond);
1226     return 2;
1227 }
1228 static int dec_addoq(CPUCRISState *env, DisasContext *dc)
1229 {
1230     int32_t imm;
1231 
1232     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 7);
1233     imm = sign_extend(dc->op1, 7);
1234 
1235     LOG_DIS("addoq %d, $r%u\n", imm, dc->op2);
1236     cris_cc_mask(dc, 0);
1237     /* Fetch register operand,  */
1238     tcg_gen_addi_tl(cpu_R[R_ACR], cpu_R[dc->op2], imm);
1239 
1240     return 2;
1241 }
1242 static int dec_addq(CPUCRISState *env, DisasContext *dc)
1243 {
1244     TCGv c;
1245     LOG_DIS("addq %u, $r%u\n", dc->op1, dc->op2);
1246 
1247     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 5);
1248 
1249     cris_cc_mask(dc, CC_MASK_NZVC);
1250 
1251     c = tcg_constant_tl(dc->op1);
1252     cris_alu(dc, CC_OP_ADD,
1253             cpu_R[dc->op2], cpu_R[dc->op2], c, 4);
1254     return 2;
1255 }
1256 static int dec_moveq(CPUCRISState *env, DisasContext *dc)
1257 {
1258     uint32_t imm;
1259 
1260     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 5);
1261     imm = sign_extend(dc->op1, 5);
1262     LOG_DIS("moveq %d, $r%u\n", imm, dc->op2);
1263 
1264     tcg_gen_movi_tl(cpu_R[dc->op2], imm);
1265     return 2;
1266 }
1267 static int dec_subq(CPUCRISState *env, DisasContext *dc)
1268 {
1269     TCGv c;
1270     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 5);
1271 
1272     LOG_DIS("subq %u, $r%u\n", dc->op1, dc->op2);
1273 
1274     cris_cc_mask(dc, CC_MASK_NZVC);
1275     c = tcg_constant_tl(dc->op1);
1276     cris_alu(dc, CC_OP_SUB,
1277             cpu_R[dc->op2], cpu_R[dc->op2], c, 4);
1278     return 2;
1279 }
1280 static int dec_cmpq(CPUCRISState *env, DisasContext *dc)
1281 {
1282     uint32_t imm;
1283     TCGv c;
1284     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 5);
1285     imm = sign_extend(dc->op1, 5);
1286 
1287     LOG_DIS("cmpq %d, $r%d\n", imm, dc->op2);
1288     cris_cc_mask(dc, CC_MASK_NZVC);
1289 
1290     c = tcg_constant_tl(imm);
1291     cris_alu(dc, CC_OP_CMP,
1292             cpu_R[dc->op2], cpu_R[dc->op2], c, 4);
1293     return 2;
1294 }
1295 static int dec_andq(CPUCRISState *env, DisasContext *dc)
1296 {
1297     uint32_t imm;
1298     TCGv c;
1299     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 5);
1300     imm = sign_extend(dc->op1, 5);
1301 
1302     LOG_DIS("andq %d, $r%d\n", imm, dc->op2);
1303     cris_cc_mask(dc, CC_MASK_NZ);
1304 
1305     c = tcg_constant_tl(imm);
1306     cris_alu(dc, CC_OP_AND,
1307             cpu_R[dc->op2], cpu_R[dc->op2], c, 4);
1308     return 2;
1309 }
1310 static int dec_orq(CPUCRISState *env, DisasContext *dc)
1311 {
1312     uint32_t imm;
1313     TCGv c;
1314     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 5);
1315     imm = sign_extend(dc->op1, 5);
1316     LOG_DIS("orq %d, $r%d\n", imm, dc->op2);
1317     cris_cc_mask(dc, CC_MASK_NZ);
1318 
1319     c = tcg_constant_tl(imm);
1320     cris_alu(dc, CC_OP_OR,
1321             cpu_R[dc->op2], cpu_R[dc->op2], c, 4);
1322     return 2;
1323 }
1324 static int dec_btstq(CPUCRISState *env, DisasContext *dc)
1325 {
1326     TCGv c;
1327     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 4);
1328     LOG_DIS("btstq %u, $r%d\n", dc->op1, dc->op2);
1329 
1330     cris_cc_mask(dc, CC_MASK_NZ);
1331     c = tcg_constant_tl(dc->op1);
1332     cris_evaluate_flags(dc);
1333     gen_helper_btst(cpu_PR[PR_CCS], cpu_env, cpu_R[dc->op2],
1334             c, cpu_PR[PR_CCS]);
1335     cris_alu(dc, CC_OP_MOVE,
1336          cpu_R[dc->op2], cpu_R[dc->op2], cpu_R[dc->op2], 4);
1337     cris_update_cc_op(dc, CC_OP_FLAGS, 4);
1338     dc->flags_uptodate = 1;
1339     return 2;
1340 }
1341 static int dec_asrq(CPUCRISState *env, DisasContext *dc)
1342 {
1343     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 4);
1344     LOG_DIS("asrq %u, $r%d\n", dc->op1, dc->op2);
1345     cris_cc_mask(dc, CC_MASK_NZ);
1346 
1347     tcg_gen_sari_tl(cpu_R[dc->op2], cpu_R[dc->op2], dc->op1);
1348     cris_alu(dc, CC_OP_MOVE,
1349             cpu_R[dc->op2],
1350             cpu_R[dc->op2], cpu_R[dc->op2], 4);
1351     return 2;
1352 }
1353 static int dec_lslq(CPUCRISState *env, DisasContext *dc)
1354 {
1355     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 4);
1356     LOG_DIS("lslq %u, $r%d\n", dc->op1, dc->op2);
1357 
1358     cris_cc_mask(dc, CC_MASK_NZ);
1359 
1360     tcg_gen_shli_tl(cpu_R[dc->op2], cpu_R[dc->op2], dc->op1);
1361 
1362     cris_alu(dc, CC_OP_MOVE,
1363             cpu_R[dc->op2],
1364             cpu_R[dc->op2], cpu_R[dc->op2], 4);
1365     return 2;
1366 }
1367 static int dec_lsrq(CPUCRISState *env, DisasContext *dc)
1368 {
1369     dc->op1 = EXTRACT_FIELD(dc->ir, 0, 4);
1370     LOG_DIS("lsrq %u, $r%d\n", dc->op1, dc->op2);
1371 
1372     cris_cc_mask(dc, CC_MASK_NZ);
1373 
1374     tcg_gen_shri_tl(cpu_R[dc->op2], cpu_R[dc->op2], dc->op1);
1375     cris_alu(dc, CC_OP_MOVE,
1376             cpu_R[dc->op2],
1377             cpu_R[dc->op2], cpu_R[dc->op2], 4);
1378     return 2;
1379 }
1380 
1381 static int dec_move_r(CPUCRISState *env, DisasContext *dc)
1382 {
1383     int size = memsize_zz(dc);
1384 
1385     LOG_DIS("move.%c $r%u, $r%u\n",
1386             memsize_char(size), dc->op1, dc->op2);
1387 
1388     cris_cc_mask(dc, CC_MASK_NZ);
1389     if (size == 4) {
1390         dec_prep_move_r(dc, dc->op1, dc->op2, size, 0, cpu_R[dc->op2]);
1391         cris_cc_mask(dc, CC_MASK_NZ);
1392         cris_update_cc_op(dc, CC_OP_MOVE, 4);
1393         cris_update_cc_x(dc);
1394         cris_update_result(dc, cpu_R[dc->op2]);
1395     } else {
1396         TCGv t0;
1397 
1398         t0 = tcg_temp_new();
1399         dec_prep_move_r(dc, dc->op1, dc->op2, size, 0, t0);
1400         cris_alu(dc, CC_OP_MOVE,
1401              cpu_R[dc->op2],
1402              cpu_R[dc->op2], t0, size);
1403     }
1404     return 2;
1405 }
1406 
1407 static int dec_scc_r(CPUCRISState *env, DisasContext *dc)
1408 {
1409     int cond = dc->op2;
1410 
1411     LOG_DIS("s%s $r%u\n",
1412             cc_name(cond), dc->op1);
1413 
1414     gen_tst_cc(dc, cpu_R[dc->op1], cond);
1415     tcg_gen_setcondi_tl(TCG_COND_NE, cpu_R[dc->op1], cpu_R[dc->op1], 0);
1416 
1417     cris_cc_mask(dc, 0);
1418     return 2;
1419 }
1420 
1421 static inline void cris_alu_alloc_temps(DisasContext *dc, int size, TCGv *t)
1422 {
1423     if (size == 4) {
1424         t[0] = cpu_R[dc->op2];
1425         t[1] = cpu_R[dc->op1];
1426     } else {
1427         t[0] = tcg_temp_new();
1428         t[1] = tcg_temp_new();
1429     }
1430 }
1431 
1432 static int dec_and_r(CPUCRISState *env, DisasContext *dc)
1433 {
1434     TCGv t[2];
1435     int size = memsize_zz(dc);
1436 
1437     LOG_DIS("and.%c $r%u, $r%u\n",
1438             memsize_char(size), dc->op1, dc->op2);
1439 
1440     cris_cc_mask(dc, CC_MASK_NZ);
1441 
1442     cris_alu_alloc_temps(dc, size, t);
1443     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 0, t[0], t[1]);
1444     cris_alu(dc, CC_OP_AND, cpu_R[dc->op2], t[0], t[1], size);
1445     return 2;
1446 }
1447 
1448 static int dec_lz_r(CPUCRISState *env, DisasContext *dc)
1449 {
1450     TCGv t0;
1451     LOG_DIS("lz $r%u, $r%u\n",
1452             dc->op1, dc->op2);
1453     cris_cc_mask(dc, CC_MASK_NZ);
1454     t0 = tcg_temp_new();
1455     dec_prep_alu_r(dc, dc->op1, dc->op2, 4, 0, cpu_R[dc->op2], t0);
1456     cris_alu(dc, CC_OP_LZ, cpu_R[dc->op2], cpu_R[dc->op2], t0, 4);
1457     return 2;
1458 }
1459 
1460 static int dec_lsl_r(CPUCRISState *env, DisasContext *dc)
1461 {
1462     TCGv t[2];
1463     int size = memsize_zz(dc);
1464 
1465     LOG_DIS("lsl.%c $r%u, $r%u\n",
1466             memsize_char(size), dc->op1, dc->op2);
1467 
1468     cris_cc_mask(dc, CC_MASK_NZ);
1469     cris_alu_alloc_temps(dc, size, t);
1470     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 0, t[0], t[1]);
1471     tcg_gen_andi_tl(t[1], t[1], 63);
1472     cris_alu(dc, CC_OP_LSL, cpu_R[dc->op2], t[0], t[1], size);
1473     return 2;
1474 }
1475 
1476 static int dec_lsr_r(CPUCRISState *env, DisasContext *dc)
1477 {
1478     TCGv t[2];
1479     int size = memsize_zz(dc);
1480 
1481     LOG_DIS("lsr.%c $r%u, $r%u\n",
1482             memsize_char(size), dc->op1, dc->op2);
1483 
1484     cris_cc_mask(dc, CC_MASK_NZ);
1485     cris_alu_alloc_temps(dc, size, t);
1486     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 0, t[0], t[1]);
1487     tcg_gen_andi_tl(t[1], t[1], 63);
1488     cris_alu(dc, CC_OP_LSR, cpu_R[dc->op2], t[0], t[1], size);
1489     return 2;
1490 }
1491 
1492 static int dec_asr_r(CPUCRISState *env, DisasContext *dc)
1493 {
1494     TCGv t[2];
1495     int size = memsize_zz(dc);
1496 
1497     LOG_DIS("asr.%c $r%u, $r%u\n",
1498             memsize_char(size), dc->op1, dc->op2);
1499 
1500     cris_cc_mask(dc, CC_MASK_NZ);
1501     cris_alu_alloc_temps(dc, size, t);
1502     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 1, t[0], t[1]);
1503     tcg_gen_andi_tl(t[1], t[1], 63);
1504     cris_alu(dc, CC_OP_ASR, cpu_R[dc->op2], t[0], t[1], size);
1505     return 2;
1506 }
1507 
1508 static int dec_muls_r(CPUCRISState *env, DisasContext *dc)
1509 {
1510     TCGv t[2];
1511     int size = memsize_zz(dc);
1512 
1513     LOG_DIS("muls.%c $r%u, $r%u\n",
1514             memsize_char(size), dc->op1, dc->op2);
1515     cris_cc_mask(dc, CC_MASK_NZV);
1516     cris_alu_alloc_temps(dc, size, t);
1517     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 1, t[0], t[1]);
1518 
1519     cris_alu(dc, CC_OP_MULS, cpu_R[dc->op2], t[0], t[1], 4);
1520     return 2;
1521 }
1522 
1523 static int dec_mulu_r(CPUCRISState *env, DisasContext *dc)
1524 {
1525     TCGv t[2];
1526     int size = memsize_zz(dc);
1527 
1528     LOG_DIS("mulu.%c $r%u, $r%u\n",
1529             memsize_char(size), dc->op1, dc->op2);
1530     cris_cc_mask(dc, CC_MASK_NZV);
1531     cris_alu_alloc_temps(dc, size, t);
1532     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 0, t[0], t[1]);
1533 
1534     cris_alu(dc, CC_OP_MULU, cpu_R[dc->op2], t[0], t[1], 4);
1535     return 2;
1536 }
1537 
1538 
1539 static int dec_dstep_r(CPUCRISState *env, DisasContext *dc)
1540 {
1541     LOG_DIS("dstep $r%u, $r%u\n", dc->op1, dc->op2);
1542     cris_cc_mask(dc, CC_MASK_NZ);
1543     cris_alu(dc, CC_OP_DSTEP,
1544             cpu_R[dc->op2], cpu_R[dc->op2], cpu_R[dc->op1], 4);
1545     return 2;
1546 }
1547 
1548 static int dec_xor_r(CPUCRISState *env, DisasContext *dc)
1549 {
1550     TCGv t[2];
1551     int size = memsize_zz(dc);
1552     LOG_DIS("xor.%c $r%u, $r%u\n",
1553             memsize_char(size), dc->op1, dc->op2);
1554     BUG_ON(size != 4); /* xor is dword.  */
1555     cris_cc_mask(dc, CC_MASK_NZ);
1556     cris_alu_alloc_temps(dc, size, t);
1557     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 0, t[0], t[1]);
1558 
1559     cris_alu(dc, CC_OP_XOR, cpu_R[dc->op2], t[0], t[1], 4);
1560     return 2;
1561 }
1562 
1563 static int dec_bound_r(CPUCRISState *env, DisasContext *dc)
1564 {
1565     TCGv l0;
1566     int size = memsize_zz(dc);
1567     LOG_DIS("bound.%c $r%u, $r%u\n",
1568             memsize_char(size), dc->op1, dc->op2);
1569     cris_cc_mask(dc, CC_MASK_NZ);
1570     l0 = tcg_temp_new();
1571     dec_prep_move_r(dc, dc->op1, dc->op2, size, 0, l0);
1572     cris_alu(dc, CC_OP_BOUND, cpu_R[dc->op2], cpu_R[dc->op2], l0, 4);
1573     return 2;
1574 }
1575 
1576 static int dec_cmp_r(CPUCRISState *env, DisasContext *dc)
1577 {
1578     TCGv t[2];
1579     int size = memsize_zz(dc);
1580     LOG_DIS("cmp.%c $r%u, $r%u\n",
1581             memsize_char(size), dc->op1, dc->op2);
1582     cris_cc_mask(dc, CC_MASK_NZVC);
1583     cris_alu_alloc_temps(dc, size, t);
1584     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 0, t[0], t[1]);
1585 
1586     cris_alu(dc, CC_OP_CMP, cpu_R[dc->op2], t[0], t[1], size);
1587     return 2;
1588 }
1589 
1590 static int dec_abs_r(CPUCRISState *env, DisasContext *dc)
1591 {
1592     LOG_DIS("abs $r%u, $r%u\n",
1593             dc->op1, dc->op2);
1594     cris_cc_mask(dc, CC_MASK_NZ);
1595 
1596     tcg_gen_abs_tl(cpu_R[dc->op2], cpu_R[dc->op1]);
1597     cris_alu(dc, CC_OP_MOVE,
1598             cpu_R[dc->op2], cpu_R[dc->op2], cpu_R[dc->op2], 4);
1599     return 2;
1600 }
1601 
1602 static int dec_add_r(CPUCRISState *env, DisasContext *dc)
1603 {
1604     TCGv t[2];
1605     int size = memsize_zz(dc);
1606     LOG_DIS("add.%c $r%u, $r%u\n",
1607             memsize_char(size), dc->op1, dc->op2);
1608     cris_cc_mask(dc, CC_MASK_NZVC);
1609     cris_alu_alloc_temps(dc, size, t);
1610     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 0, t[0], t[1]);
1611 
1612     cris_alu(dc, CC_OP_ADD, cpu_R[dc->op2], t[0], t[1], size);
1613     return 2;
1614 }
1615 
1616 static int dec_addc_r(CPUCRISState *env, DisasContext *dc)
1617 {
1618     LOG_DIS("addc $r%u, $r%u\n",
1619             dc->op1, dc->op2);
1620     cris_evaluate_flags(dc);
1621 
1622     /* Set for this insn.  */
1623     dc->flags_x = X_FLAG;
1624 
1625     cris_cc_mask(dc, CC_MASK_NZVC);
1626     cris_alu(dc, CC_OP_ADDC,
1627          cpu_R[dc->op2], cpu_R[dc->op2], cpu_R[dc->op1], 4);
1628     return 2;
1629 }
1630 
1631 static int dec_mcp_r(CPUCRISState *env, DisasContext *dc)
1632 {
1633     LOG_DIS("mcp $p%u, $r%u\n",
1634              dc->op2, dc->op1);
1635     cris_evaluate_flags(dc);
1636     cris_cc_mask(dc, CC_MASK_RNZV);
1637     cris_alu(dc, CC_OP_MCP,
1638             cpu_R[dc->op1], cpu_R[dc->op1], cpu_PR[dc->op2], 4);
1639     return 2;
1640 }
1641 
1642 #if DISAS_CRIS
1643 static char * swapmode_name(int mode, char *modename) {
1644     int i = 0;
1645     if (mode & 8) {
1646         modename[i++] = 'n';
1647     }
1648     if (mode & 4) {
1649         modename[i++] = 'w';
1650     }
1651     if (mode & 2) {
1652         modename[i++] = 'b';
1653     }
1654     if (mode & 1) {
1655         modename[i++] = 'r';
1656     }
1657     modename[i++] = 0;
1658     return modename;
1659 }
1660 #endif
1661 
1662 static int dec_swap_r(CPUCRISState *env, DisasContext *dc)
1663 {
1664     TCGv t0;
1665 #if DISAS_CRIS
1666     char modename[4];
1667 #endif
1668     LOG_DIS("swap%s $r%u\n",
1669              swapmode_name(dc->op2, modename), dc->op1);
1670 
1671     cris_cc_mask(dc, CC_MASK_NZ);
1672     t0 = tcg_temp_new();
1673     tcg_gen_mov_tl(t0, cpu_R[dc->op1]);
1674     if (dc->op2 & 8) {
1675         tcg_gen_not_tl(t0, t0);
1676     }
1677     if (dc->op2 & 4) {
1678         t_gen_swapw(t0, t0);
1679     }
1680     if (dc->op2 & 2) {
1681         t_gen_swapb(t0, t0);
1682     }
1683     if (dc->op2 & 1) {
1684         t_gen_swapr(t0, t0);
1685     }
1686     cris_alu(dc, CC_OP_MOVE, cpu_R[dc->op1], cpu_R[dc->op1], t0, 4);
1687     return 2;
1688 }
1689 
1690 static int dec_or_r(CPUCRISState *env, DisasContext *dc)
1691 {
1692     TCGv t[2];
1693     int size = memsize_zz(dc);
1694     LOG_DIS("or.%c $r%u, $r%u\n",
1695             memsize_char(size), dc->op1, dc->op2);
1696     cris_cc_mask(dc, CC_MASK_NZ);
1697     cris_alu_alloc_temps(dc, size, t);
1698     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 0, t[0], t[1]);
1699     cris_alu(dc, CC_OP_OR, cpu_R[dc->op2], t[0], t[1], size);
1700     return 2;
1701 }
1702 
1703 static int dec_addi_r(CPUCRISState *env, DisasContext *dc)
1704 {
1705     TCGv t0;
1706     LOG_DIS("addi.%c $r%u, $r%u\n",
1707             memsize_char(memsize_zz(dc)), dc->op2, dc->op1);
1708     cris_cc_mask(dc, 0);
1709     t0 = tcg_temp_new();
1710     tcg_gen_shli_tl(t0, cpu_R[dc->op2], dc->zzsize);
1711     tcg_gen_add_tl(cpu_R[dc->op1], cpu_R[dc->op1], t0);
1712     return 2;
1713 }
1714 
1715 static int dec_addi_acr(CPUCRISState *env, DisasContext *dc)
1716 {
1717     TCGv t0;
1718     LOG_DIS("addi.%c $r%u, $r%u, $acr\n",
1719           memsize_char(memsize_zz(dc)), dc->op2, dc->op1);
1720     cris_cc_mask(dc, 0);
1721     t0 = tcg_temp_new();
1722     tcg_gen_shli_tl(t0, cpu_R[dc->op2], dc->zzsize);
1723     tcg_gen_add_tl(cpu_R[R_ACR], cpu_R[dc->op1], t0);
1724     return 2;
1725 }
1726 
1727 static int dec_neg_r(CPUCRISState *env, DisasContext *dc)
1728 {
1729     TCGv t[2];
1730     int size = memsize_zz(dc);
1731     LOG_DIS("neg.%c $r%u, $r%u\n",
1732             memsize_char(size), dc->op1, dc->op2);
1733     cris_cc_mask(dc, CC_MASK_NZVC);
1734     cris_alu_alloc_temps(dc, size, t);
1735     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 0, t[0], t[1]);
1736 
1737     cris_alu(dc, CC_OP_NEG, cpu_R[dc->op2], t[0], t[1], size);
1738     return 2;
1739 }
1740 
1741 static int dec_btst_r(CPUCRISState *env, DisasContext *dc)
1742 {
1743     LOG_DIS("btst $r%u, $r%u\n",
1744             dc->op1, dc->op2);
1745     cris_cc_mask(dc, CC_MASK_NZ);
1746     cris_evaluate_flags(dc);
1747         gen_helper_btst(cpu_PR[PR_CCS], cpu_env, cpu_R[dc->op2],
1748             cpu_R[dc->op1], cpu_PR[PR_CCS]);
1749     cris_alu(dc, CC_OP_MOVE, cpu_R[dc->op2],
1750          cpu_R[dc->op2], cpu_R[dc->op2], 4);
1751     cris_update_cc_op(dc, CC_OP_FLAGS, 4);
1752     dc->flags_uptodate = 1;
1753     return 2;
1754 }
1755 
1756 static int dec_sub_r(CPUCRISState *env, DisasContext *dc)
1757 {
1758     TCGv t[2];
1759     int size = memsize_zz(dc);
1760     LOG_DIS("sub.%c $r%u, $r%u\n",
1761             memsize_char(size), dc->op1, dc->op2);
1762     cris_cc_mask(dc, CC_MASK_NZVC);
1763     cris_alu_alloc_temps(dc, size, t);
1764     dec_prep_alu_r(dc, dc->op1, dc->op2, size, 0, t[0], t[1]);
1765     cris_alu(dc, CC_OP_SUB, cpu_R[dc->op2], t[0], t[1], size);
1766     return 2;
1767 }
1768 
1769 /* Zero extension. From size to dword.  */
1770 static int dec_movu_r(CPUCRISState *env, DisasContext *dc)
1771 {
1772     TCGv t0;
1773     int size = memsize_z(dc);
1774     LOG_DIS("movu.%c $r%u, $r%u\n",
1775             memsize_char(size),
1776             dc->op1, dc->op2);
1777 
1778     cris_cc_mask(dc, CC_MASK_NZ);
1779     t0 = tcg_temp_new();
1780     dec_prep_move_r(dc, dc->op1, dc->op2, size, 0, t0);
1781     cris_alu(dc, CC_OP_MOVE, cpu_R[dc->op2], cpu_R[dc->op2], t0, 4);
1782     return 2;
1783 }
1784 
1785 /* Sign extension. From size to dword.  */
1786 static int dec_movs_r(CPUCRISState *env, DisasContext *dc)
1787 {
1788     TCGv t0;
1789     int size = memsize_z(dc);
1790     LOG_DIS("movs.%c $r%u, $r%u\n",
1791             memsize_char(size),
1792             dc->op1, dc->op2);
1793 
1794     cris_cc_mask(dc, CC_MASK_NZ);
1795     t0 = tcg_temp_new();
1796     /* Size can only be qi or hi.  */
1797     t_gen_sext(t0, cpu_R[dc->op1], size);
1798     cris_alu(dc, CC_OP_MOVE,
1799             cpu_R[dc->op2], cpu_R[dc->op1], t0, 4);
1800     return 2;
1801 }
1802 
1803 /* zero extension. From size to dword.  */
1804 static int dec_addu_r(CPUCRISState *env, DisasContext *dc)
1805 {
1806     TCGv t0;
1807     int size = memsize_z(dc);
1808     LOG_DIS("addu.%c $r%u, $r%u\n",
1809             memsize_char(size),
1810             dc->op1, dc->op2);
1811 
1812     cris_cc_mask(dc, CC_MASK_NZVC);
1813     t0 = tcg_temp_new();
1814     /* Size can only be qi or hi.  */
1815     t_gen_zext(t0, cpu_R[dc->op1], size);
1816     cris_alu(dc, CC_OP_ADD, cpu_R[dc->op2], cpu_R[dc->op2], t0, 4);
1817     return 2;
1818 }
1819 
1820 /* Sign extension. From size to dword.  */
1821 static int dec_adds_r(CPUCRISState *env, DisasContext *dc)
1822 {
1823     TCGv t0;
1824     int size = memsize_z(dc);
1825     LOG_DIS("adds.%c $r%u, $r%u\n",
1826             memsize_char(size),
1827             dc->op1, dc->op2);
1828 
1829     cris_cc_mask(dc, CC_MASK_NZVC);
1830     t0 = tcg_temp_new();
1831     /* Size can only be qi or hi.  */
1832     t_gen_sext(t0, cpu_R[dc->op1], size);
1833     cris_alu(dc, CC_OP_ADD,
1834             cpu_R[dc->op2], cpu_R[dc->op2], t0, 4);
1835     return 2;
1836 }
1837 
1838 /* Zero extension. From size to dword.  */
1839 static int dec_subu_r(CPUCRISState *env, DisasContext *dc)
1840 {
1841     TCGv t0;
1842     int size = memsize_z(dc);
1843     LOG_DIS("subu.%c $r%u, $r%u\n",
1844             memsize_char(size),
1845             dc->op1, dc->op2);
1846 
1847     cris_cc_mask(dc, CC_MASK_NZVC);
1848     t0 = tcg_temp_new();
1849     /* Size can only be qi or hi.  */
1850     t_gen_zext(t0, cpu_R[dc->op1], size);
1851     cris_alu(dc, CC_OP_SUB,
1852             cpu_R[dc->op2], cpu_R[dc->op2], t0, 4);
1853     return 2;
1854 }
1855 
1856 /* Sign extension. From size to dword.  */
1857 static int dec_subs_r(CPUCRISState *env, DisasContext *dc)
1858 {
1859     TCGv t0;
1860     int size = memsize_z(dc);
1861     LOG_DIS("subs.%c $r%u, $r%u\n",
1862             memsize_char(size),
1863             dc->op1, dc->op2);
1864 
1865     cris_cc_mask(dc, CC_MASK_NZVC);
1866     t0 = tcg_temp_new();
1867     /* Size can only be qi or hi.  */
1868     t_gen_sext(t0, cpu_R[dc->op1], size);
1869     cris_alu(dc, CC_OP_SUB,
1870             cpu_R[dc->op2], cpu_R[dc->op2], t0, 4);
1871     return 2;
1872 }
1873 
1874 static int dec_setclrf(CPUCRISState *env, DisasContext *dc)
1875 {
1876     uint32_t flags;
1877     int set = (~dc->opcode >> 2) & 1;
1878 
1879 
1880     flags = (EXTRACT_FIELD(dc->ir, 12, 15) << 4)
1881         | EXTRACT_FIELD(dc->ir, 0, 3);
1882     if (set && flags == 0) {
1883         LOG_DIS("nop\n");
1884         return 2;
1885     } else if (!set && (flags & 0x20)) {
1886         LOG_DIS("di\n");
1887     } else {
1888         LOG_DIS("%sf %x\n", set ? "set" : "clr", flags);
1889     }
1890 
1891     /* User space is not allowed to touch these. Silently ignore.  */
1892     if (dc->tb_flags & U_FLAG) {
1893         flags &= ~(S_FLAG | I_FLAG | U_FLAG);
1894     }
1895 
1896     if (flags & X_FLAG) {
1897         if (set) {
1898             dc->flags_x = X_FLAG;
1899         } else {
1900             dc->flags_x = 0;
1901         }
1902     }
1903 
1904     /* Break the TB if any of the SPI flag changes.  */
1905     if (flags & (P_FLAG | S_FLAG)) {
1906         tcg_gen_movi_tl(env_pc, dc->pc + 2);
1907         dc->base.is_jmp = DISAS_UPDATE;
1908         dc->cpustate_changed = 1;
1909     }
1910 
1911     /* For the I flag, only act on posedge.  */
1912     if ((flags & I_FLAG)) {
1913         tcg_gen_movi_tl(env_pc, dc->pc + 2);
1914         dc->base.is_jmp = DISAS_UPDATE;
1915         dc->cpustate_changed = 1;
1916     }
1917 
1918 
1919     /* Simply decode the flags.  */
1920     cris_evaluate_flags(dc);
1921     cris_update_cc_op(dc, CC_OP_FLAGS, 4);
1922     cris_update_cc_x(dc);
1923     tcg_gen_movi_tl(cc_op, dc->cc_op);
1924 
1925     if (set) {
1926         if (!(dc->tb_flags & U_FLAG) && (flags & U_FLAG)) {
1927             /* Enter user mode.  */
1928             t_gen_mov_env_TN(ksp, cpu_R[R_SP]);
1929             tcg_gen_mov_tl(cpu_R[R_SP], cpu_PR[PR_USP]);
1930             dc->cpustate_changed = 1;
1931         }
1932         tcg_gen_ori_tl(cpu_PR[PR_CCS], cpu_PR[PR_CCS], flags);
1933     } else {
1934         tcg_gen_andi_tl(cpu_PR[PR_CCS], cpu_PR[PR_CCS], ~flags);
1935     }
1936 
1937     dc->flags_uptodate = 1;
1938     dc->clear_x = 0;
1939     return 2;
1940 }
1941 
1942 static int dec_move_rs(CPUCRISState *env, DisasContext *dc)
1943 {
1944     TCGv c2, c1;
1945     LOG_DIS("move $r%u, $s%u\n", dc->op1, dc->op2);
1946     c1 = tcg_constant_tl(dc->op1);
1947     c2 = tcg_constant_tl(dc->op2);
1948     cris_cc_mask(dc, 0);
1949     gen_helper_movl_sreg_reg(cpu_env, c2, c1);
1950     return 2;
1951 }
1952 static int dec_move_sr(CPUCRISState *env, DisasContext *dc)
1953 {
1954     TCGv c2, c1;
1955     LOG_DIS("move $s%u, $r%u\n", dc->op2, dc->op1);
1956     c1 = tcg_constant_tl(dc->op1);
1957     c2 = tcg_constant_tl(dc->op2);
1958     cris_cc_mask(dc, 0);
1959     gen_helper_movl_reg_sreg(cpu_env, c1, c2);
1960     return 2;
1961 }
1962 
1963 static int dec_move_rp(CPUCRISState *env, DisasContext *dc)
1964 {
1965     TCGv t[2];
1966     LOG_DIS("move $r%u, $p%u\n", dc->op1, dc->op2);
1967     cris_cc_mask(dc, 0);
1968 
1969     t[0] = tcg_temp_new();
1970     if (dc->op2 == PR_CCS) {
1971         cris_evaluate_flags(dc);
1972         tcg_gen_mov_tl(t[0], cpu_R[dc->op1]);
1973         if (dc->tb_flags & U_FLAG) {
1974             t[1] = tcg_temp_new();
1975             /* User space is not allowed to touch all flags.  */
1976             tcg_gen_andi_tl(t[0], t[0], 0x39f);
1977             tcg_gen_andi_tl(t[1], cpu_PR[PR_CCS], ~0x39f);
1978             tcg_gen_or_tl(t[0], t[1], t[0]);
1979         }
1980     } else {
1981         tcg_gen_mov_tl(t[0], cpu_R[dc->op1]);
1982     }
1983 
1984     t_gen_mov_preg_TN(dc, dc->op2, t[0]);
1985     if (dc->op2 == PR_CCS) {
1986         cris_update_cc_op(dc, CC_OP_FLAGS, 4);
1987         dc->flags_uptodate = 1;
1988     }
1989     return 2;
1990 }
1991 static int dec_move_pr(CPUCRISState *env, DisasContext *dc)
1992 {
1993     TCGv t0;
1994     LOG_DIS("move $p%u, $r%u\n", dc->op2, dc->op1);
1995     cris_cc_mask(dc, 0);
1996 
1997     if (dc->op2 == PR_CCS) {
1998         cris_evaluate_flags(dc);
1999     }
2000 
2001     if (dc->op2 == PR_DZ) {
2002         tcg_gen_movi_tl(cpu_R[dc->op1], 0);
2003     } else {
2004         t0 = tcg_temp_new();
2005         t_gen_mov_TN_preg(t0, dc->op2);
2006         cris_alu(dc, CC_OP_MOVE,
2007                 cpu_R[dc->op1], cpu_R[dc->op1], t0,
2008                 preg_sizes[dc->op2]);
2009     }
2010     return 2;
2011 }
2012 
2013 static int dec_move_mr(CPUCRISState *env, DisasContext *dc)
2014 {
2015     int memsize = memsize_zz(dc);
2016     int insn_len;
2017     LOG_DIS("move.%c [$r%u%s, $r%u\n",
2018             memsize_char(memsize),
2019             dc->op1, dc->postinc ? "+]" : "]",
2020                     dc->op2);
2021 
2022     if (memsize == 4) {
2023         insn_len = dec_prep_move_m(env, dc, 0, 4, cpu_R[dc->op2]);
2024         cris_cc_mask(dc, CC_MASK_NZ);
2025         cris_update_cc_op(dc, CC_OP_MOVE, 4);
2026         cris_update_cc_x(dc);
2027         cris_update_result(dc, cpu_R[dc->op2]);
2028     } else {
2029         TCGv t0;
2030 
2031         t0 = tcg_temp_new();
2032         insn_len = dec_prep_move_m(env, dc, 0, memsize, t0);
2033         cris_cc_mask(dc, CC_MASK_NZ);
2034         cris_alu(dc, CC_OP_MOVE,
2035                 cpu_R[dc->op2], cpu_R[dc->op2], t0, memsize);
2036     }
2037     do_postinc(dc, memsize);
2038     return insn_len;
2039 }
2040 
2041 static inline void cris_alu_m_alloc_temps(TCGv *t)
2042 {
2043     t[0] = tcg_temp_new();
2044     t[1] = tcg_temp_new();
2045 }
2046 
2047 static int dec_movs_m(CPUCRISState *env, DisasContext *dc)
2048 {
2049     TCGv t[2];
2050     int memsize = memsize_z(dc);
2051     int insn_len;
2052     LOG_DIS("movs.%c [$r%u%s, $r%u\n",
2053             memsize_char(memsize),
2054             dc->op1, dc->postinc ? "+]" : "]",
2055             dc->op2);
2056 
2057     cris_alu_m_alloc_temps(t);
2058     /* sign extend.  */
2059         insn_len = dec_prep_alu_m(env, dc, 1, memsize, t[0], t[1]);
2060     cris_cc_mask(dc, CC_MASK_NZ);
2061     cris_alu(dc, CC_OP_MOVE,
2062             cpu_R[dc->op2], cpu_R[dc->op2], t[1], 4);
2063     do_postinc(dc, memsize);
2064     return insn_len;
2065 }
2066 
2067 static int dec_addu_m(CPUCRISState *env, DisasContext *dc)
2068 {
2069     TCGv t[2];
2070     int memsize = memsize_z(dc);
2071     int insn_len;
2072     LOG_DIS("addu.%c [$r%u%s, $r%u\n",
2073             memsize_char(memsize),
2074             dc->op1, dc->postinc ? "+]" : "]",
2075             dc->op2);
2076 
2077     cris_alu_m_alloc_temps(t);
2078     /* sign extend.  */
2079         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2080     cris_cc_mask(dc, CC_MASK_NZVC);
2081     cris_alu(dc, CC_OP_ADD,
2082             cpu_R[dc->op2], cpu_R[dc->op2], t[1], 4);
2083     do_postinc(dc, memsize);
2084     return insn_len;
2085 }
2086 
2087 static int dec_adds_m(CPUCRISState *env, DisasContext *dc)
2088 {
2089     TCGv t[2];
2090     int memsize = memsize_z(dc);
2091     int insn_len;
2092     LOG_DIS("adds.%c [$r%u%s, $r%u\n",
2093             memsize_char(memsize),
2094             dc->op1, dc->postinc ? "+]" : "]",
2095             dc->op2);
2096 
2097     cris_alu_m_alloc_temps(t);
2098     /* sign extend.  */
2099         insn_len = dec_prep_alu_m(env, dc, 1, memsize, t[0], t[1]);
2100     cris_cc_mask(dc, CC_MASK_NZVC);
2101     cris_alu(dc, CC_OP_ADD, cpu_R[dc->op2], cpu_R[dc->op2], t[1], 4);
2102     do_postinc(dc, memsize);
2103     return insn_len;
2104 }
2105 
2106 static int dec_subu_m(CPUCRISState *env, DisasContext *dc)
2107 {
2108     TCGv t[2];
2109     int memsize = memsize_z(dc);
2110     int insn_len;
2111     LOG_DIS("subu.%c [$r%u%s, $r%u\n",
2112             memsize_char(memsize),
2113             dc->op1, dc->postinc ? "+]" : "]",
2114             dc->op2);
2115 
2116     cris_alu_m_alloc_temps(t);
2117     /* sign extend.  */
2118         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2119     cris_cc_mask(dc, CC_MASK_NZVC);
2120     cris_alu(dc, CC_OP_SUB, cpu_R[dc->op2], cpu_R[dc->op2], t[1], 4);
2121     do_postinc(dc, memsize);
2122     return insn_len;
2123 }
2124 
2125 static int dec_subs_m(CPUCRISState *env, DisasContext *dc)
2126 {
2127     TCGv t[2];
2128     int memsize = memsize_z(dc);
2129     int insn_len;
2130     LOG_DIS("subs.%c [$r%u%s, $r%u\n",
2131             memsize_char(memsize),
2132             dc->op1, dc->postinc ? "+]" : "]",
2133             dc->op2);
2134 
2135     cris_alu_m_alloc_temps(t);
2136     /* sign extend.  */
2137         insn_len = dec_prep_alu_m(env, dc, 1, memsize, t[0], t[1]);
2138     cris_cc_mask(dc, CC_MASK_NZVC);
2139     cris_alu(dc, CC_OP_SUB, cpu_R[dc->op2], cpu_R[dc->op2], t[1], 4);
2140     do_postinc(dc, memsize);
2141     return insn_len;
2142 }
2143 
2144 static int dec_movu_m(CPUCRISState *env, DisasContext *dc)
2145 {
2146     TCGv t[2];
2147     int memsize = memsize_z(dc);
2148     int insn_len;
2149 
2150     LOG_DIS("movu.%c [$r%u%s, $r%u\n",
2151             memsize_char(memsize),
2152             dc->op1, dc->postinc ? "+]" : "]",
2153             dc->op2);
2154 
2155     cris_alu_m_alloc_temps(t);
2156         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2157     cris_cc_mask(dc, CC_MASK_NZ);
2158     cris_alu(dc, CC_OP_MOVE, cpu_R[dc->op2], cpu_R[dc->op2], t[1], 4);
2159     do_postinc(dc, memsize);
2160     return insn_len;
2161 }
2162 
2163 static int dec_cmpu_m(CPUCRISState *env, DisasContext *dc)
2164 {
2165     TCGv t[2];
2166     int memsize = memsize_z(dc);
2167     int insn_len;
2168     LOG_DIS("cmpu.%c [$r%u%s, $r%u\n",
2169             memsize_char(memsize),
2170             dc->op1, dc->postinc ? "+]" : "]",
2171             dc->op2);
2172 
2173     cris_alu_m_alloc_temps(t);
2174         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2175     cris_cc_mask(dc, CC_MASK_NZVC);
2176     cris_alu(dc, CC_OP_CMP, cpu_R[dc->op2], cpu_R[dc->op2], t[1], 4);
2177     do_postinc(dc, memsize);
2178     return insn_len;
2179 }
2180 
2181 static int dec_cmps_m(CPUCRISState *env, DisasContext *dc)
2182 {
2183     TCGv t[2];
2184     int memsize = memsize_z(dc);
2185     int insn_len;
2186     LOG_DIS("cmps.%c [$r%u%s, $r%u\n",
2187             memsize_char(memsize),
2188             dc->op1, dc->postinc ? "+]" : "]",
2189             dc->op2);
2190 
2191     cris_alu_m_alloc_temps(t);
2192         insn_len = dec_prep_alu_m(env, dc, 1, memsize, t[0], t[1]);
2193     cris_cc_mask(dc, CC_MASK_NZVC);
2194     cris_alu(dc, CC_OP_CMP,
2195             cpu_R[dc->op2], cpu_R[dc->op2], t[1],
2196             memsize_zz(dc));
2197     do_postinc(dc, memsize);
2198     return insn_len;
2199 }
2200 
2201 static int dec_cmp_m(CPUCRISState *env, DisasContext *dc)
2202 {
2203     TCGv t[2];
2204     int memsize = memsize_zz(dc);
2205     int insn_len;
2206     LOG_DIS("cmp.%c [$r%u%s, $r%u\n",
2207             memsize_char(memsize),
2208             dc->op1, dc->postinc ? "+]" : "]",
2209             dc->op2);
2210 
2211     cris_alu_m_alloc_temps(t);
2212         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2213     cris_cc_mask(dc, CC_MASK_NZVC);
2214     cris_alu(dc, CC_OP_CMP,
2215             cpu_R[dc->op2], cpu_R[dc->op2], t[1],
2216             memsize_zz(dc));
2217     do_postinc(dc, memsize);
2218     return insn_len;
2219 }
2220 
2221 static int dec_test_m(CPUCRISState *env, DisasContext *dc)
2222 {
2223     TCGv t[2], c;
2224     int memsize = memsize_zz(dc);
2225     int insn_len;
2226     LOG_DIS("test.%c [$r%u%s] op2=%x\n",
2227             memsize_char(memsize),
2228             dc->op1, dc->postinc ? "+]" : "]",
2229             dc->op2);
2230 
2231     cris_evaluate_flags(dc);
2232 
2233     cris_alu_m_alloc_temps(t);
2234         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2235     cris_cc_mask(dc, CC_MASK_NZ);
2236     tcg_gen_andi_tl(cpu_PR[PR_CCS], cpu_PR[PR_CCS], ~3);
2237 
2238     c = tcg_constant_tl(0);
2239     cris_alu(dc, CC_OP_CMP,
2240          cpu_R[dc->op2], t[1], c, memsize_zz(dc));
2241     do_postinc(dc, memsize);
2242     return insn_len;
2243 }
2244 
2245 static int dec_and_m(CPUCRISState *env, DisasContext *dc)
2246 {
2247     TCGv t[2];
2248     int memsize = memsize_zz(dc);
2249     int insn_len;
2250     LOG_DIS("and.%c [$r%u%s, $r%u\n",
2251             memsize_char(memsize),
2252             dc->op1, dc->postinc ? "+]" : "]",
2253             dc->op2);
2254 
2255     cris_alu_m_alloc_temps(t);
2256         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2257     cris_cc_mask(dc, CC_MASK_NZ);
2258     cris_alu(dc, CC_OP_AND, cpu_R[dc->op2], t[0], t[1], memsize_zz(dc));
2259     do_postinc(dc, memsize);
2260     return insn_len;
2261 }
2262 
2263 static int dec_add_m(CPUCRISState *env, DisasContext *dc)
2264 {
2265     TCGv t[2];
2266     int memsize = memsize_zz(dc);
2267     int insn_len;
2268     LOG_DIS("add.%c [$r%u%s, $r%u\n",
2269             memsize_char(memsize),
2270             dc->op1, dc->postinc ? "+]" : "]",
2271             dc->op2);
2272 
2273     cris_alu_m_alloc_temps(t);
2274         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2275     cris_cc_mask(dc, CC_MASK_NZVC);
2276     cris_alu(dc, CC_OP_ADD,
2277          cpu_R[dc->op2], t[0], t[1], memsize_zz(dc));
2278     do_postinc(dc, memsize);
2279     return insn_len;
2280 }
2281 
2282 static int dec_addo_m(CPUCRISState *env, DisasContext *dc)
2283 {
2284     TCGv t[2];
2285     int memsize = memsize_zz(dc);
2286     int insn_len;
2287     LOG_DIS("add.%c [$r%u%s, $r%u\n",
2288             memsize_char(memsize),
2289             dc->op1, dc->postinc ? "+]" : "]",
2290             dc->op2);
2291 
2292     cris_alu_m_alloc_temps(t);
2293         insn_len = dec_prep_alu_m(env, dc, 1, memsize, t[0], t[1]);
2294     cris_cc_mask(dc, 0);
2295     cris_alu(dc, CC_OP_ADD, cpu_R[R_ACR], t[0], t[1], 4);
2296     do_postinc(dc, memsize);
2297     return insn_len;
2298 }
2299 
2300 static int dec_bound_m(CPUCRISState *env, DisasContext *dc)
2301 {
2302     TCGv l[2];
2303     int memsize = memsize_zz(dc);
2304     int insn_len;
2305     LOG_DIS("bound.%c [$r%u%s, $r%u\n",
2306             memsize_char(memsize),
2307             dc->op1, dc->postinc ? "+]" : "]",
2308             dc->op2);
2309 
2310     l[0] = tcg_temp_new();
2311     l[1] = tcg_temp_new();
2312         insn_len = dec_prep_alu_m(env, dc, 0, memsize, l[0], l[1]);
2313     cris_cc_mask(dc, CC_MASK_NZ);
2314     cris_alu(dc, CC_OP_BOUND, cpu_R[dc->op2], l[0], l[1], 4);
2315     do_postinc(dc, memsize);
2316     return insn_len;
2317 }
2318 
2319 static int dec_addc_mr(CPUCRISState *env, DisasContext *dc)
2320 {
2321     TCGv t[2];
2322     int insn_len = 2;
2323     LOG_DIS("addc [$r%u%s, $r%u\n",
2324             dc->op1, dc->postinc ? "+]" : "]",
2325             dc->op2);
2326 
2327     cris_evaluate_flags(dc);
2328 
2329     /* Set for this insn.  */
2330     dc->flags_x = X_FLAG;
2331 
2332     cris_alu_m_alloc_temps(t);
2333         insn_len = dec_prep_alu_m(env, dc, 0, 4, t[0], t[1]);
2334     cris_cc_mask(dc, CC_MASK_NZVC);
2335     cris_alu(dc, CC_OP_ADDC, cpu_R[dc->op2], t[0], t[1], 4);
2336     do_postinc(dc, 4);
2337     return insn_len;
2338 }
2339 
2340 static int dec_sub_m(CPUCRISState *env, DisasContext *dc)
2341 {
2342     TCGv t[2];
2343     int memsize = memsize_zz(dc);
2344     int insn_len;
2345     LOG_DIS("sub.%c [$r%u%s, $r%u ir=%x zz=%x\n",
2346             memsize_char(memsize),
2347             dc->op1, dc->postinc ? "+]" : "]",
2348             dc->op2, dc->ir, dc->zzsize);
2349 
2350     cris_alu_m_alloc_temps(t);
2351         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2352     cris_cc_mask(dc, CC_MASK_NZVC);
2353     cris_alu(dc, CC_OP_SUB, cpu_R[dc->op2], t[0], t[1], memsize);
2354     do_postinc(dc, memsize);
2355     return insn_len;
2356 }
2357 
2358 static int dec_or_m(CPUCRISState *env, DisasContext *dc)
2359 {
2360     TCGv t[2];
2361     int memsize = memsize_zz(dc);
2362     int insn_len;
2363     LOG_DIS("or.%c [$r%u%s, $r%u pc=%x\n",
2364             memsize_char(memsize),
2365             dc->op1, dc->postinc ? "+]" : "]",
2366             dc->op2, dc->pc);
2367 
2368     cris_alu_m_alloc_temps(t);
2369         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2370     cris_cc_mask(dc, CC_MASK_NZ);
2371     cris_alu(dc, CC_OP_OR,
2372             cpu_R[dc->op2], t[0], t[1], memsize_zz(dc));
2373     do_postinc(dc, memsize);
2374     return insn_len;
2375 }
2376 
2377 static int dec_move_mp(CPUCRISState *env, DisasContext *dc)
2378 {
2379     TCGv t[2];
2380     int memsize = memsize_zz(dc);
2381     int insn_len = 2;
2382 
2383     LOG_DIS("move.%c [$r%u%s, $p%u\n",
2384             memsize_char(memsize),
2385             dc->op1,
2386             dc->postinc ? "+]" : "]",
2387             dc->op2);
2388 
2389     cris_alu_m_alloc_temps(t);
2390         insn_len = dec_prep_alu_m(env, dc, 0, memsize, t[0], t[1]);
2391     cris_cc_mask(dc, 0);
2392     if (dc->op2 == PR_CCS) {
2393         cris_evaluate_flags(dc);
2394         if (dc->tb_flags & U_FLAG) {
2395             /* User space is not allowed to touch all flags.  */
2396             tcg_gen_andi_tl(t[1], t[1], 0x39f);
2397             tcg_gen_andi_tl(t[0], cpu_PR[PR_CCS], ~0x39f);
2398             tcg_gen_or_tl(t[1], t[0], t[1]);
2399         }
2400     }
2401 
2402     t_gen_mov_preg_TN(dc, dc->op2, t[1]);
2403 
2404     do_postinc(dc, memsize);
2405     return insn_len;
2406 }
2407 
2408 static int dec_move_pm(CPUCRISState *env, DisasContext *dc)
2409 {
2410     TCGv t0;
2411     int memsize;
2412 
2413     memsize = preg_sizes[dc->op2];
2414 
2415     LOG_DIS("move.%c $p%u, [$r%u%s\n",
2416             memsize_char(memsize),
2417             dc->op2, dc->op1, dc->postinc ? "+]" : "]");
2418 
2419     /* prepare store. Address in T0, value in T1.  */
2420     if (dc->op2 == PR_CCS) {
2421         cris_evaluate_flags(dc);
2422     }
2423     t0 = tcg_temp_new();
2424     t_gen_mov_TN_preg(t0, dc->op2);
2425     cris_flush_cc_state(dc);
2426     gen_store(dc, cpu_R[dc->op1], t0, memsize);
2427 
2428     cris_cc_mask(dc, 0);
2429     if (dc->postinc) {
2430         tcg_gen_addi_tl(cpu_R[dc->op1], cpu_R[dc->op1], memsize);
2431     }
2432     return 2;
2433 }
2434 
2435 static int dec_movem_mr(CPUCRISState *env, DisasContext *dc)
2436 {
2437     TCGv_i64 tmp[16];
2438     TCGv tmp32;
2439     TCGv addr;
2440     int i;
2441     int nr = dc->op2 + 1;
2442 
2443     LOG_DIS("movem [$r%u%s, $r%u\n", dc->op1,
2444             dc->postinc ? "+]" : "]", dc->op2);
2445 
2446     addr = tcg_temp_new();
2447     /* There are probably better ways of doing this.  */
2448     cris_flush_cc_state(dc);
2449     for (i = 0; i < (nr >> 1); i++) {
2450         tmp[i] = tcg_temp_new_i64();
2451         tcg_gen_addi_tl(addr, cpu_R[dc->op1], i * 8);
2452         gen_load64(dc, tmp[i], addr);
2453     }
2454     if (nr & 1) {
2455         tmp32 = tcg_temp_new_i32();
2456         tcg_gen_addi_tl(addr, cpu_R[dc->op1], i * 8);
2457         gen_load(dc, tmp32, addr, 4, 0);
2458     } else {
2459         tmp32 = NULL;
2460     }
2461 
2462     for (i = 0; i < (nr >> 1); i++) {
2463         tcg_gen_extrl_i64_i32(cpu_R[i * 2], tmp[i]);
2464         tcg_gen_shri_i64(tmp[i], tmp[i], 32);
2465         tcg_gen_extrl_i64_i32(cpu_R[i * 2 + 1], tmp[i]);
2466     }
2467     if (nr & 1) {
2468         tcg_gen_mov_tl(cpu_R[dc->op2], tmp32);
2469     }
2470 
2471     /* writeback the updated pointer value.  */
2472     if (dc->postinc) {
2473         tcg_gen_addi_tl(cpu_R[dc->op1], cpu_R[dc->op1], nr * 4);
2474     }
2475 
2476     /* gen_load might want to evaluate the previous insns flags.  */
2477     cris_cc_mask(dc, 0);
2478     return 2;
2479 }
2480 
2481 static int dec_movem_rm(CPUCRISState *env, DisasContext *dc)
2482 {
2483     TCGv tmp;
2484     TCGv addr;
2485     int i;
2486 
2487     LOG_DIS("movem $r%u, [$r%u%s\n", dc->op2, dc->op1,
2488             dc->postinc ? "+]" : "]");
2489 
2490     cris_flush_cc_state(dc);
2491 
2492     tmp = tcg_temp_new();
2493     addr = tcg_temp_new();
2494     tcg_gen_movi_tl(tmp, 4);
2495     tcg_gen_mov_tl(addr, cpu_R[dc->op1]);
2496     for (i = 0; i <= dc->op2; i++) {
2497         /* Displace addr.  */
2498         /* Perform the store.  */
2499         gen_store(dc, addr, cpu_R[i], 4);
2500         tcg_gen_add_tl(addr, addr, tmp);
2501     }
2502     if (dc->postinc) {
2503         tcg_gen_mov_tl(cpu_R[dc->op1], addr);
2504     }
2505     cris_cc_mask(dc, 0);
2506     return 2;
2507 }
2508 
2509 static int dec_move_rm(CPUCRISState *env, DisasContext *dc)
2510 {
2511     int memsize;
2512 
2513     memsize = memsize_zz(dc);
2514 
2515     LOG_DIS("move.%c $r%u, [$r%u]\n",
2516             memsize_char(memsize), dc->op2, dc->op1);
2517 
2518     /* prepare store.  */
2519     cris_flush_cc_state(dc);
2520     gen_store(dc, cpu_R[dc->op1], cpu_R[dc->op2], memsize);
2521 
2522     if (dc->postinc) {
2523         tcg_gen_addi_tl(cpu_R[dc->op1], cpu_R[dc->op1], memsize);
2524     }
2525     cris_cc_mask(dc, 0);
2526     return 2;
2527 }
2528 
2529 static int dec_lapcq(CPUCRISState *env, DisasContext *dc)
2530 {
2531     LOG_DIS("lapcq %x, $r%u\n",
2532             dc->pc + dc->op1*2, dc->op2);
2533     cris_cc_mask(dc, 0);
2534     tcg_gen_movi_tl(cpu_R[dc->op2], dc->pc + dc->op1 * 2);
2535     return 2;
2536 }
2537 
2538 static int dec_lapc_im(CPUCRISState *env, DisasContext *dc)
2539 {
2540     unsigned int rd;
2541     int32_t imm;
2542     int32_t pc;
2543 
2544     rd = dc->op2;
2545 
2546     cris_cc_mask(dc, 0);
2547     imm = cris_fetch(env, dc, dc->pc + 2, 4, 0);
2548     LOG_DIS("lapc 0x%x, $r%u\n", imm + dc->pc, dc->op2);
2549 
2550     pc = dc->pc;
2551     pc += imm;
2552     tcg_gen_movi_tl(cpu_R[rd], pc);
2553     return 6;
2554 }
2555 
2556 /* Jump to special reg.  */
2557 static int dec_jump_p(CPUCRISState *env, DisasContext *dc)
2558 {
2559     LOG_DIS("jump $p%u\n", dc->op2);
2560 
2561     if (dc->op2 == PR_CCS) {
2562         cris_evaluate_flags(dc);
2563     }
2564     t_gen_mov_TN_preg(env_btarget, dc->op2);
2565     /* rete will often have low bit set to indicate delayslot.  */
2566     tcg_gen_andi_tl(env_btarget, env_btarget, ~1);
2567     cris_cc_mask(dc, 0);
2568     cris_prepare_jmp(dc, JMP_INDIRECT);
2569     return 2;
2570 }
2571 
2572 /* Jump and save.  */
2573 static int dec_jas_r(CPUCRISState *env, DisasContext *dc)
2574 {
2575     TCGv c;
2576     LOG_DIS("jas $r%u, $p%u\n", dc->op1, dc->op2);
2577     cris_cc_mask(dc, 0);
2578     /* Store the return address in Pd.  */
2579     tcg_gen_mov_tl(env_btarget, cpu_R[dc->op1]);
2580     if (dc->op2 > 15) {
2581         abort();
2582     }
2583     c = tcg_constant_tl(dc->pc + 4);
2584     t_gen_mov_preg_TN(dc, dc->op2, c);
2585 
2586     cris_prepare_jmp(dc, JMP_INDIRECT);
2587     return 2;
2588 }
2589 
2590 static int dec_jas_im(CPUCRISState *env, DisasContext *dc)
2591 {
2592     uint32_t imm;
2593     TCGv c;
2594 
2595     imm = cris_fetch(env, dc, dc->pc + 2, 4, 0);
2596 
2597     LOG_DIS("jas 0x%x\n", imm);
2598     cris_cc_mask(dc, 0);
2599     c = tcg_constant_tl(dc->pc + 8);
2600     /* Store the return address in Pd.  */
2601     t_gen_mov_preg_TN(dc, dc->op2, c);
2602 
2603     dc->jmp_pc = imm;
2604     cris_prepare_jmp(dc, JMP_DIRECT);
2605     return 6;
2606 }
2607 
2608 static int dec_jasc_im(CPUCRISState *env, DisasContext *dc)
2609 {
2610     uint32_t imm;
2611     TCGv c;
2612 
2613     imm = cris_fetch(env, dc, dc->pc + 2, 4, 0);
2614 
2615     LOG_DIS("jasc 0x%x\n", imm);
2616     cris_cc_mask(dc, 0);
2617     c = tcg_constant_tl(dc->pc + 8 + 4);
2618     /* Store the return address in Pd.  */
2619     t_gen_mov_preg_TN(dc, dc->op2, c);
2620 
2621     dc->jmp_pc = imm;
2622     cris_prepare_jmp(dc, JMP_DIRECT);
2623     return 6;
2624 }
2625 
2626 static int dec_jasc_r(CPUCRISState *env, DisasContext *dc)
2627 {
2628     TCGv c;
2629     LOG_DIS("jasc_r $r%u, $p%u\n", dc->op1, dc->op2);
2630     cris_cc_mask(dc, 0);
2631     /* Store the return address in Pd.  */
2632     tcg_gen_mov_tl(env_btarget, cpu_R[dc->op1]);
2633     c = tcg_constant_tl(dc->pc + 4 + 4);
2634     t_gen_mov_preg_TN(dc, dc->op2, c);
2635     cris_prepare_jmp(dc, JMP_INDIRECT);
2636     return 2;
2637 }
2638 
2639 static int dec_bcc_im(CPUCRISState *env, DisasContext *dc)
2640 {
2641     int32_t offset;
2642     uint32_t cond = dc->op2;
2643 
2644     offset = cris_fetch(env, dc, dc->pc + 2, 2, 1);
2645 
2646     LOG_DIS("b%s %d pc=%x dst=%x\n",
2647             cc_name(cond), offset,
2648             dc->pc, dc->pc + offset);
2649 
2650     cris_cc_mask(dc, 0);
2651     /* op2 holds the condition-code.  */
2652     cris_prepare_cc_branch(dc, offset, cond);
2653     return 4;
2654 }
2655 
2656 static int dec_bas_im(CPUCRISState *env, DisasContext *dc)
2657 {
2658     int32_t simm;
2659     TCGv c;
2660 
2661     simm = cris_fetch(env, dc, dc->pc + 2, 4, 0);
2662 
2663     LOG_DIS("bas 0x%x, $p%u\n", dc->pc + simm, dc->op2);
2664     cris_cc_mask(dc, 0);
2665     c = tcg_constant_tl(dc->pc + 8);
2666     /* Store the return address in Pd.  */
2667     t_gen_mov_preg_TN(dc, dc->op2, c);
2668 
2669     dc->jmp_pc = dc->pc + simm;
2670     cris_prepare_jmp(dc, JMP_DIRECT);
2671     return 6;
2672 }
2673 
2674 static int dec_basc_im(CPUCRISState *env, DisasContext *dc)
2675 {
2676     int32_t simm;
2677     TCGv c;
2678     simm = cris_fetch(env, dc, dc->pc + 2, 4, 0);
2679 
2680     LOG_DIS("basc 0x%x, $p%u\n", dc->pc + simm, dc->op2);
2681     cris_cc_mask(dc, 0);
2682     c = tcg_constant_tl(dc->pc + 12);
2683     /* Store the return address in Pd.  */
2684     t_gen_mov_preg_TN(dc, dc->op2, c);
2685 
2686     dc->jmp_pc = dc->pc + simm;
2687     cris_prepare_jmp(dc, JMP_DIRECT);
2688     return 6;
2689 }
2690 
2691 static int dec_rfe_etc(CPUCRISState *env, DisasContext *dc)
2692 {
2693     cris_cc_mask(dc, 0);
2694 
2695     if (dc->op2 == 15) {
2696         tcg_gen_st_i32(tcg_constant_i32(1), cpu_env,
2697                        -offsetof(CRISCPU, env) + offsetof(CPUState, halted));
2698         tcg_gen_movi_tl(env_pc, dc->pc + 2);
2699         t_gen_raise_exception(EXCP_HLT);
2700         dc->base.is_jmp = DISAS_NORETURN;
2701         return 2;
2702     }
2703 
2704     switch (dc->op2 & 7) {
2705     case 2:
2706         /* rfe.  */
2707         LOG_DIS("rfe\n");
2708         cris_evaluate_flags(dc);
2709         gen_helper_rfe(cpu_env);
2710         dc->base.is_jmp = DISAS_UPDATE;
2711         dc->cpustate_changed = true;
2712         break;
2713     case 5:
2714         /* rfn.  */
2715         LOG_DIS("rfn\n");
2716         cris_evaluate_flags(dc);
2717         gen_helper_rfn(cpu_env);
2718         dc->base.is_jmp = DISAS_UPDATE;
2719         dc->cpustate_changed = true;
2720         break;
2721     case 6:
2722         LOG_DIS("break %d\n", dc->op1);
2723         cris_evaluate_flags(dc);
2724         /* break.  */
2725         tcg_gen_movi_tl(env_pc, dc->pc + 2);
2726 
2727         /* Breaks start at 16 in the exception vector.  */
2728         t_gen_movi_env_TN(trap_vector, dc->op1 + 16);
2729         t_gen_raise_exception(EXCP_BREAK);
2730         dc->base.is_jmp = DISAS_NORETURN;
2731         break;
2732     default:
2733         printf("op2=%x\n", dc->op2);
2734         BUG();
2735         break;
2736 
2737     }
2738     return 2;
2739 }
2740 
2741 static int dec_ftag_fidx_d_m(CPUCRISState *env, DisasContext *dc)
2742 {
2743     return 2;
2744 }
2745 
2746 static int dec_ftag_fidx_i_m(CPUCRISState *env, DisasContext *dc)
2747 {
2748     return 2;
2749 }
2750 
2751 static int dec_null(CPUCRISState *env, DisasContext *dc)
2752 {
2753     printf("unknown insn pc=%x opc=%x op1=%x op2=%x\n",
2754         dc->pc, dc->opcode, dc->op1, dc->op2);
2755     fflush(NULL);
2756     BUG();
2757     return 2;
2758 }
2759 
2760 static const struct decoder_info {
2761     struct {
2762         uint32_t bits;
2763         uint32_t mask;
2764     };
2765     int (*dec)(CPUCRISState *env, DisasContext *dc);
2766 } decinfo[] = {
2767     /* Order matters here.  */
2768     {DEC_MOVEQ, dec_moveq},
2769     {DEC_BTSTQ, dec_btstq},
2770     {DEC_CMPQ, dec_cmpq},
2771     {DEC_ADDOQ, dec_addoq},
2772     {DEC_ADDQ, dec_addq},
2773     {DEC_SUBQ, dec_subq},
2774     {DEC_ANDQ, dec_andq},
2775     {DEC_ORQ, dec_orq},
2776     {DEC_ASRQ, dec_asrq},
2777     {DEC_LSLQ, dec_lslq},
2778     {DEC_LSRQ, dec_lsrq},
2779     {DEC_BCCQ, dec_bccq},
2780 
2781     {DEC_BCC_IM, dec_bcc_im},
2782     {DEC_JAS_IM, dec_jas_im},
2783     {DEC_JAS_R, dec_jas_r},
2784     {DEC_JASC_IM, dec_jasc_im},
2785     {DEC_JASC_R, dec_jasc_r},
2786     {DEC_BAS_IM, dec_bas_im},
2787     {DEC_BASC_IM, dec_basc_im},
2788     {DEC_JUMP_P, dec_jump_p},
2789     {DEC_LAPC_IM, dec_lapc_im},
2790     {DEC_LAPCQ, dec_lapcq},
2791 
2792     {DEC_RFE_ETC, dec_rfe_etc},
2793     {DEC_ADDC_MR, dec_addc_mr},
2794 
2795     {DEC_MOVE_MP, dec_move_mp},
2796     {DEC_MOVE_PM, dec_move_pm},
2797     {DEC_MOVEM_MR, dec_movem_mr},
2798     {DEC_MOVEM_RM, dec_movem_rm},
2799     {DEC_MOVE_PR, dec_move_pr},
2800     {DEC_SCC_R, dec_scc_r},
2801     {DEC_SETF, dec_setclrf},
2802     {DEC_CLEARF, dec_setclrf},
2803 
2804     {DEC_MOVE_SR, dec_move_sr},
2805     {DEC_MOVE_RP, dec_move_rp},
2806     {DEC_SWAP_R, dec_swap_r},
2807     {DEC_ABS_R, dec_abs_r},
2808     {DEC_LZ_R, dec_lz_r},
2809     {DEC_MOVE_RS, dec_move_rs},
2810     {DEC_BTST_R, dec_btst_r},
2811     {DEC_ADDC_R, dec_addc_r},
2812 
2813     {DEC_DSTEP_R, dec_dstep_r},
2814     {DEC_XOR_R, dec_xor_r},
2815     {DEC_MCP_R, dec_mcp_r},
2816     {DEC_CMP_R, dec_cmp_r},
2817 
2818     {DEC_ADDI_R, dec_addi_r},
2819     {DEC_ADDI_ACR, dec_addi_acr},
2820 
2821     {DEC_ADD_R, dec_add_r},
2822     {DEC_SUB_R, dec_sub_r},
2823 
2824     {DEC_ADDU_R, dec_addu_r},
2825     {DEC_ADDS_R, dec_adds_r},
2826     {DEC_SUBU_R, dec_subu_r},
2827     {DEC_SUBS_R, dec_subs_r},
2828     {DEC_LSL_R, dec_lsl_r},
2829 
2830     {DEC_AND_R, dec_and_r},
2831     {DEC_OR_R, dec_or_r},
2832     {DEC_BOUND_R, dec_bound_r},
2833     {DEC_ASR_R, dec_asr_r},
2834     {DEC_LSR_R, dec_lsr_r},
2835 
2836     {DEC_MOVU_R, dec_movu_r},
2837     {DEC_MOVS_R, dec_movs_r},
2838     {DEC_NEG_R, dec_neg_r},
2839     {DEC_MOVE_R, dec_move_r},
2840 
2841     {DEC_FTAG_FIDX_I_M, dec_ftag_fidx_i_m},
2842     {DEC_FTAG_FIDX_D_M, dec_ftag_fidx_d_m},
2843 
2844     {DEC_MULS_R, dec_muls_r},
2845     {DEC_MULU_R, dec_mulu_r},
2846 
2847     {DEC_ADDU_M, dec_addu_m},
2848     {DEC_ADDS_M, dec_adds_m},
2849     {DEC_SUBU_M, dec_subu_m},
2850     {DEC_SUBS_M, dec_subs_m},
2851 
2852     {DEC_CMPU_M, dec_cmpu_m},
2853     {DEC_CMPS_M, dec_cmps_m},
2854     {DEC_MOVU_M, dec_movu_m},
2855     {DEC_MOVS_M, dec_movs_m},
2856 
2857     {DEC_CMP_M, dec_cmp_m},
2858     {DEC_ADDO_M, dec_addo_m},
2859     {DEC_BOUND_M, dec_bound_m},
2860     {DEC_ADD_M, dec_add_m},
2861     {DEC_SUB_M, dec_sub_m},
2862     {DEC_AND_M, dec_and_m},
2863     {DEC_OR_M, dec_or_m},
2864     {DEC_MOVE_RM, dec_move_rm},
2865     {DEC_TEST_M, dec_test_m},
2866     {DEC_MOVE_MR, dec_move_mr},
2867 
2868     {{0, 0}, dec_null}
2869 };
2870 
2871 static unsigned int crisv32_decoder(CPUCRISState *env, DisasContext *dc)
2872 {
2873     int insn_len = 2;
2874     int i;
2875 
2876     /* Load a halfword onto the instruction register.  */
2877         dc->ir = cris_fetch(env, dc, dc->pc, 2, 0);
2878 
2879     /* Now decode it.  */
2880     dc->opcode   = EXTRACT_FIELD(dc->ir, 4, 11);
2881     dc->op1      = EXTRACT_FIELD(dc->ir, 0, 3);
2882     dc->op2      = EXTRACT_FIELD(dc->ir, 12, 15);
2883     dc->zsize    = EXTRACT_FIELD(dc->ir, 4, 4);
2884     dc->zzsize   = EXTRACT_FIELD(dc->ir, 4, 5);
2885     dc->postinc  = EXTRACT_FIELD(dc->ir, 10, 10);
2886 
2887     /* Large switch for all insns.  */
2888     for (i = 0; i < ARRAY_SIZE(decinfo); i++) {
2889         if ((dc->opcode & decinfo[i].mask) == decinfo[i].bits) {
2890             insn_len = decinfo[i].dec(env, dc);
2891             break;
2892         }
2893     }
2894 
2895 #if !defined(CONFIG_USER_ONLY)
2896     /* Single-stepping ?  */
2897     if (dc->tb_flags & S_FLAG) {
2898         TCGLabel *l1 = gen_new_label();
2899         tcg_gen_brcondi_tl(TCG_COND_NE, cpu_PR[PR_SPC], dc->pc, l1);
2900         /* We treat SPC as a break with an odd trap vector.  */
2901         cris_evaluate_flags(dc);
2902         t_gen_movi_env_TN(trap_vector, 3);
2903         tcg_gen_movi_tl(env_pc, dc->pc + insn_len);
2904         tcg_gen_movi_tl(cpu_PR[PR_SPC], dc->pc + insn_len);
2905         t_gen_raise_exception(EXCP_BREAK);
2906         gen_set_label(l1);
2907     }
2908 #endif
2909     return insn_len;
2910 }
2911 
2912 #include "translate_v10.c.inc"
2913 
2914 /*
2915  * Delay slots on QEMU/CRIS.
2916  *
2917  * If an exception hits on a delayslot, the core will let ERP (the Exception
2918  * Return Pointer) point to the branch (the previous) insn and set the lsb to
2919  * to give SW a hint that the exception actually hit on the dslot.
2920  *
2921  * CRIS expects all PC addresses to be 16-bit aligned. The lsb is ignored by
2922  * the core and any jmp to an odd addresses will mask off that lsb. It is
2923  * simply there to let sw know there was an exception on a dslot.
2924  *
2925  * When the software returns from an exception, the branch will re-execute.
2926  * On QEMU care needs to be taken when a branch+delayslot sequence is broken
2927  * and the branch and delayslot don't share pages.
2928  *
2929  * The TB containing the branch insn will set up env->btarget and evaluate
2930  * env->btaken. When the translation loop exits we will note that the branch
2931  * sequence is broken and let env->dslot be the size of the branch insn (those
2932  * vary in length).
2933  *
2934  * The TB containing the delayslot will have the PC of its real insn (i.e no lsb
2935  * set). It will also expect to have env->dslot setup with the size of the
2936  * delay slot so that env->pc - env->dslot point to the branch insn. This TB
2937  * will execute the dslot and take the branch, either to btarget or just one
2938  * insn ahead.
2939  *
2940  * When exceptions occur, we check for env->dslot in do_interrupt to detect
2941  * broken branch sequences and setup $erp accordingly (i.e let it point to the
2942  * branch and set lsb). Then env->dslot gets cleared so that the exception
2943  * handler can enter. When returning from exceptions (jump $erp) the lsb gets
2944  * masked off and we will reexecute the branch insn.
2945  *
2946  */
2947 
2948 static void cris_tr_init_disas_context(DisasContextBase *dcbase, CPUState *cs)
2949 {
2950     DisasContext *dc = container_of(dcbase, DisasContext, base);
2951     CPUCRISState *env = cs->env_ptr;
2952     uint32_t tb_flags = dc->base.tb->flags;
2953     uint32_t pc_start;
2954 
2955     if (env->pregs[PR_VR] == 32) {
2956         dc->decoder = crisv32_decoder;
2957         dc->clear_locked_irq = 0;
2958     } else {
2959         dc->decoder = crisv10_decoder;
2960         dc->clear_locked_irq = 1;
2961     }
2962 
2963     /*
2964      * Odd PC indicates that branch is rexecuting due to exception in the
2965      * delayslot, like in real hw.
2966      */
2967     pc_start = dc->base.pc_first & ~1;
2968     dc->base.pc_first = pc_start;
2969     dc->base.pc_next = pc_start;
2970 
2971     dc->cpu = env_archcpu(env);
2972     dc->ppc = pc_start;
2973     dc->pc = pc_start;
2974     dc->flags_uptodate = 1;
2975     dc->flags_x = tb_flags & X_FLAG;
2976     dc->cc_x_uptodate = 0;
2977     dc->cc_mask = 0;
2978     dc->update_cc = 0;
2979     dc->clear_prefix = 0;
2980     dc->cpustate_changed = 0;
2981 
2982     cris_update_cc_op(dc, CC_OP_FLAGS, 4);
2983     dc->cc_size_uptodate = -1;
2984 
2985     /* Decode TB flags.  */
2986     dc->tb_flags = tb_flags & (S_FLAG | P_FLAG | U_FLAG | X_FLAG | PFIX_FLAG);
2987     dc->delayed_branch = !!(tb_flags & 7);
2988     if (dc->delayed_branch) {
2989         dc->jmp = JMP_INDIRECT;
2990     } else {
2991         dc->jmp = JMP_NOJMP;
2992     }
2993 }
2994 
2995 static void cris_tr_tb_start(DisasContextBase *db, CPUState *cpu)
2996 {
2997 }
2998 
2999 static void cris_tr_insn_start(DisasContextBase *dcbase, CPUState *cpu)
3000 {
3001     DisasContext *dc = container_of(dcbase, DisasContext, base);
3002 
3003     tcg_gen_insn_start(dc->delayed_branch == 1 ? dc->ppc | 1 : dc->pc);
3004 }
3005 
3006 static void cris_tr_translate_insn(DisasContextBase *dcbase, CPUState *cs)
3007 {
3008     DisasContext *dc = container_of(dcbase, DisasContext, base);
3009     CPUCRISState *env = cs->env_ptr;
3010     unsigned int insn_len;
3011 
3012     /* Pretty disas.  */
3013     LOG_DIS("%8.8x:\t", dc->pc);
3014 
3015     dc->clear_x = 1;
3016 
3017     insn_len = dc->decoder(env, dc);
3018     dc->ppc = dc->pc;
3019     dc->pc += insn_len;
3020     dc->base.pc_next += insn_len;
3021 
3022     if (dc->base.is_jmp == DISAS_NORETURN) {
3023         return;
3024     }
3025 
3026     if (dc->clear_x) {
3027         cris_clear_x_flag(dc);
3028     }
3029 
3030     /*
3031      * All branches are delayed branches, handled immediately below.
3032      * We don't expect to see odd combinations of exit conditions.
3033      */
3034     assert(dc->base.is_jmp == DISAS_NEXT || dc->cpustate_changed);
3035 
3036     if (dc->delayed_branch && --dc->delayed_branch == 0) {
3037         dc->base.is_jmp = DISAS_DBRANCH;
3038         return;
3039     }
3040 
3041     if (dc->base.is_jmp != DISAS_NEXT) {
3042         return;
3043     }
3044 
3045     /* Force an update if the per-tb cpu state has changed.  */
3046     if (dc->cpustate_changed) {
3047         dc->base.is_jmp = DISAS_UPDATE_NEXT;
3048         return;
3049     }
3050 
3051     /*
3052      * FIXME: Only the first insn in the TB should cross a page boundary.
3053      * If we can detect the length of the next insn easily, we should.
3054      * In the meantime, simply stop when we do cross.
3055      */
3056     if ((dc->pc ^ dc->base.pc_first) & TARGET_PAGE_MASK) {
3057         dc->base.is_jmp = DISAS_TOO_MANY;
3058     }
3059 }
3060 
3061 static void cris_tr_tb_stop(DisasContextBase *dcbase, CPUState *cpu)
3062 {
3063     DisasContext *dc = container_of(dcbase, DisasContext, base);
3064     DisasJumpType is_jmp = dc->base.is_jmp;
3065     target_ulong npc = dc->pc;
3066 
3067     if (is_jmp == DISAS_NORETURN) {
3068         /* If we have a broken branch+delayslot sequence, it's too late. */
3069         assert(dc->delayed_branch != 1);
3070         return;
3071     }
3072 
3073     if (dc->clear_locked_irq) {
3074         t_gen_movi_env_TN(locked_irq, 0);
3075     }
3076 
3077     /* Broken branch+delayslot sequence.  */
3078     if (dc->delayed_branch == 1) {
3079         /* Set env->dslot to the size of the branch insn.  */
3080         t_gen_movi_env_TN(dslot, dc->pc - dc->ppc);
3081         cris_store_direct_jmp(dc);
3082     }
3083 
3084     cris_evaluate_flags(dc);
3085 
3086     /* Evaluate delayed branch destination and fold to another is_jmp case. */
3087     if (is_jmp == DISAS_DBRANCH) {
3088         if (dc->base.tb->flags & 7) {
3089             t_gen_movi_env_TN(dslot, 0);
3090         }
3091 
3092         switch (dc->jmp) {
3093         case JMP_DIRECT:
3094             npc = dc->jmp_pc;
3095             is_jmp = dc->cpustate_changed ? DISAS_UPDATE_NEXT : DISAS_TOO_MANY;
3096             break;
3097 
3098         case JMP_DIRECT_CC:
3099             /*
3100              * Use a conditional branch if either taken or not-taken path
3101              * can use goto_tb.  If neither can, then treat it as indirect.
3102              */
3103             if (likely(!dc->cpustate_changed)
3104                 && (use_goto_tb(dc, dc->jmp_pc) || use_goto_tb(dc, npc))) {
3105                 TCGLabel *not_taken = gen_new_label();
3106 
3107                 tcg_gen_brcondi_tl(TCG_COND_EQ, env_btaken, 0, not_taken);
3108                 gen_goto_tb(dc, 1, dc->jmp_pc);
3109                 gen_set_label(not_taken);
3110 
3111                 /* not-taken case handled below. */
3112                 is_jmp = DISAS_TOO_MANY;
3113                 break;
3114             }
3115             tcg_gen_movi_tl(env_btarget, dc->jmp_pc);
3116             /* fall through */
3117 
3118         case JMP_INDIRECT:
3119             tcg_gen_movcond_tl(TCG_COND_NE, env_pc,
3120                                env_btaken, tcg_constant_tl(0),
3121                                env_btarget, tcg_constant_tl(npc));
3122             is_jmp = dc->cpustate_changed ? DISAS_UPDATE : DISAS_JUMP;
3123 
3124             /*
3125              * We have now consumed btaken and btarget.  Hint to the
3126              * tcg compiler that the writeback to env may be dropped.
3127              */
3128             tcg_gen_discard_tl(env_btaken);
3129             tcg_gen_discard_tl(env_btarget);
3130             break;
3131 
3132         default:
3133             g_assert_not_reached();
3134         }
3135     }
3136 
3137     switch (is_jmp) {
3138     case DISAS_TOO_MANY:
3139         gen_goto_tb(dc, 0, npc);
3140         break;
3141     case DISAS_UPDATE_NEXT:
3142         tcg_gen_movi_tl(env_pc, npc);
3143         /* fall through */
3144     case DISAS_JUMP:
3145         tcg_gen_lookup_and_goto_ptr();
3146         break;
3147     case DISAS_UPDATE:
3148         /* Indicate that interrupts must be re-evaluated before the next TB. */
3149         tcg_gen_exit_tb(NULL, 0);
3150         break;
3151     default:
3152         g_assert_not_reached();
3153     }
3154 }
3155 
3156 static void cris_tr_disas_log(const DisasContextBase *dcbase,
3157                               CPUState *cpu, FILE *logfile)
3158 {
3159     if (!DISAS_CRIS) {
3160         fprintf(logfile, "IN: %s\n", lookup_symbol(dcbase->pc_first));
3161         target_disas(logfile, cpu, dcbase->pc_first, dcbase->tb->size);
3162     }
3163 }
3164 
3165 static const TranslatorOps cris_tr_ops = {
3166     .init_disas_context = cris_tr_init_disas_context,
3167     .tb_start           = cris_tr_tb_start,
3168     .insn_start         = cris_tr_insn_start,
3169     .translate_insn     = cris_tr_translate_insn,
3170     .tb_stop            = cris_tr_tb_stop,
3171     .disas_log          = cris_tr_disas_log,
3172 };
3173 
3174 void gen_intermediate_code(CPUState *cs, TranslationBlock *tb, int *max_insns,
3175                            target_ulong pc, void *host_pc)
3176 {
3177     DisasContext dc;
3178     translator_loop(cs, tb, max_insns, pc, host_pc, &cris_tr_ops, &dc.base);
3179 }
3180 
3181 void cris_cpu_dump_state(CPUState *cs, FILE *f, int flags)
3182 {
3183     CRISCPU *cpu = CRIS_CPU(cs);
3184     CPUCRISState *env = &cpu->env;
3185     const char * const *regnames;
3186     const char * const *pregnames;
3187     int i;
3188 
3189     if (!env) {
3190         return;
3191     }
3192     if (env->pregs[PR_VR] < 32) {
3193         pregnames = pregnames_v10;
3194         regnames = regnames_v10;
3195     } else {
3196         pregnames = pregnames_v32;
3197         regnames = regnames_v32;
3198     }
3199 
3200     qemu_fprintf(f, "PC=%x CCS=%x btaken=%d btarget=%x\n"
3201                  "cc_op=%d cc_src=%d cc_dest=%d cc_result=%x cc_mask=%x\n",
3202                  env->pc, env->pregs[PR_CCS], env->btaken, env->btarget,
3203                  env->cc_op,
3204                  env->cc_src, env->cc_dest, env->cc_result, env->cc_mask);
3205 
3206 
3207     for (i = 0; i < 16; i++) {
3208         qemu_fprintf(f, "%s=%8.8x ", regnames[i], env->regs[i]);
3209         if ((i + 1) % 4 == 0) {
3210             qemu_fprintf(f, "\n");
3211         }
3212     }
3213     qemu_fprintf(f, "\nspecial regs:\n");
3214     for (i = 0; i < 16; i++) {
3215         qemu_fprintf(f, "%s=%8.8x ", pregnames[i], env->pregs[i]);
3216         if ((i + 1) % 4 == 0) {
3217             qemu_fprintf(f, "\n");
3218         }
3219     }
3220     if (env->pregs[PR_VR] >= 32) {
3221         uint32_t srs = env->pregs[PR_SRS];
3222         qemu_fprintf(f, "\nsupport function regs bank %x:\n", srs);
3223         if (srs < ARRAY_SIZE(env->sregs)) {
3224             for (i = 0; i < 16; i++) {
3225                 qemu_fprintf(f, "s%2.2d=%8.8x ",
3226                              i, env->sregs[srs][i]);
3227                 if ((i + 1) % 4 == 0) {
3228                     qemu_fprintf(f, "\n");
3229                 }
3230             }
3231         }
3232     }
3233     qemu_fprintf(f, "\n\n");
3234 
3235 }
3236 
3237 void cris_initialize_tcg(void)
3238 {
3239     int i;
3240 
3241     cc_x = tcg_global_mem_new(cpu_env,
3242                               offsetof(CPUCRISState, cc_x), "cc_x");
3243     cc_src = tcg_global_mem_new(cpu_env,
3244                                 offsetof(CPUCRISState, cc_src), "cc_src");
3245     cc_dest = tcg_global_mem_new(cpu_env,
3246                                  offsetof(CPUCRISState, cc_dest),
3247                                  "cc_dest");
3248     cc_result = tcg_global_mem_new(cpu_env,
3249                                    offsetof(CPUCRISState, cc_result),
3250                                    "cc_result");
3251     cc_op = tcg_global_mem_new(cpu_env,
3252                                offsetof(CPUCRISState, cc_op), "cc_op");
3253     cc_size = tcg_global_mem_new(cpu_env,
3254                                  offsetof(CPUCRISState, cc_size),
3255                                  "cc_size");
3256     cc_mask = tcg_global_mem_new(cpu_env,
3257                                  offsetof(CPUCRISState, cc_mask),
3258                                  "cc_mask");
3259 
3260     env_pc = tcg_global_mem_new(cpu_env,
3261                                 offsetof(CPUCRISState, pc),
3262                                 "pc");
3263     env_btarget = tcg_global_mem_new(cpu_env,
3264                                      offsetof(CPUCRISState, btarget),
3265                                      "btarget");
3266     env_btaken = tcg_global_mem_new(cpu_env,
3267                                     offsetof(CPUCRISState, btaken),
3268                                     "btaken");
3269     for (i = 0; i < 16; i++) {
3270         cpu_R[i] = tcg_global_mem_new(cpu_env,
3271                                       offsetof(CPUCRISState, regs[i]),
3272                                       regnames_v32[i]);
3273     }
3274     for (i = 0; i < 16; i++) {
3275         cpu_PR[i] = tcg_global_mem_new(cpu_env,
3276                                        offsetof(CPUCRISState, pregs[i]),
3277                                        pregnames_v32[i]);
3278     }
3279 }
3280