]> Git Repo - qemu.git/blob - target-ppc/translate.c
target-ppc: consolidate store conditional
[qemu.git] / target-ppc / translate.c
1 /*
2  *  PowerPC emulation for qemu: main translation routines.
3  *
4  *  Copyright (c) 2003-2007 Jocelyn Mayer
5  *  Copyright (C) 2011 Freescale Semiconductor, Inc.
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 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 #include "qemu/osdep.h"
22 #include "cpu.h"
23 #include "disas/disas.h"
24 #include "exec/exec-all.h"
25 #include "tcg-op.h"
26 #include "qemu/host-utils.h"
27 #include "exec/cpu_ldst.h"
28
29 #include "exec/helper-proto.h"
30 #include "exec/helper-gen.h"
31
32 #include "trace-tcg.h"
33 #include "exec/log.h"
34
35
36 #define CPU_SINGLE_STEP 0x1
37 #define CPU_BRANCH_STEP 0x2
38 #define GDBSTUB_SINGLE_STEP 0x4
39
40 /* Include definitions for instructions classes and implementations flags */
41 //#define PPC_DEBUG_DISAS
42 //#define DO_PPC_STATISTICS
43
44 #ifdef PPC_DEBUG_DISAS
45 #  define LOG_DISAS(...) qemu_log_mask(CPU_LOG_TB_IN_ASM, ## __VA_ARGS__)
46 #else
47 #  define LOG_DISAS(...) do { } while (0)
48 #endif
49 /*****************************************************************************/
50 /* Code translation helpers                                                  */
51
52 /* global register indexes */
53 static TCGv_env cpu_env;
54 static char cpu_reg_names[10*3 + 22*4 /* GPR */
55     + 10*4 + 22*5 /* SPE GPRh */
56     + 10*4 + 22*5 /* FPR */
57     + 2*(10*6 + 22*7) /* AVRh, AVRl */
58     + 10*5 + 22*6 /* VSR */
59     + 8*5 /* CRF */];
60 static TCGv cpu_gpr[32];
61 static TCGv cpu_gprh[32];
62 static TCGv_i64 cpu_fpr[32];
63 static TCGv_i64 cpu_avrh[32], cpu_avrl[32];
64 static TCGv_i64 cpu_vsr[32];
65 static TCGv_i32 cpu_crf[8];
66 static TCGv cpu_nip;
67 static TCGv cpu_msr;
68 static TCGv cpu_ctr;
69 static TCGv cpu_lr;
70 #if defined(TARGET_PPC64)
71 static TCGv cpu_cfar;
72 #endif
73 static TCGv cpu_xer, cpu_so, cpu_ov, cpu_ca;
74 static TCGv cpu_reserve;
75 static TCGv cpu_fpscr;
76 static TCGv_i32 cpu_access_type;
77
78 #include "exec/gen-icount.h"
79
80 void ppc_translate_init(void)
81 {
82     int i;
83     char* p;
84     size_t cpu_reg_names_size;
85     static int done_init = 0;
86
87     if (done_init)
88         return;
89
90     cpu_env = tcg_global_reg_new_ptr(TCG_AREG0, "env");
91     tcg_ctx.tcg_env = cpu_env;
92
93     p = cpu_reg_names;
94     cpu_reg_names_size = sizeof(cpu_reg_names);
95
96     for (i = 0; i < 8; i++) {
97         snprintf(p, cpu_reg_names_size, "crf%d", i);
98         cpu_crf[i] = tcg_global_mem_new_i32(cpu_env,
99                                             offsetof(CPUPPCState, crf[i]), p);
100         p += 5;
101         cpu_reg_names_size -= 5;
102     }
103
104     for (i = 0; i < 32; i++) {
105         snprintf(p, cpu_reg_names_size, "r%d", i);
106         cpu_gpr[i] = tcg_global_mem_new(cpu_env,
107                                         offsetof(CPUPPCState, gpr[i]), p);
108         p += (i < 10) ? 3 : 4;
109         cpu_reg_names_size -= (i < 10) ? 3 : 4;
110         snprintf(p, cpu_reg_names_size, "r%dH", i);
111         cpu_gprh[i] = tcg_global_mem_new(cpu_env,
112                                          offsetof(CPUPPCState, gprh[i]), p);
113         p += (i < 10) ? 4 : 5;
114         cpu_reg_names_size -= (i < 10) ? 4 : 5;
115
116         snprintf(p, cpu_reg_names_size, "fp%d", i);
117         cpu_fpr[i] = tcg_global_mem_new_i64(cpu_env,
118                                             offsetof(CPUPPCState, fpr[i]), p);
119         p += (i < 10) ? 4 : 5;
120         cpu_reg_names_size -= (i < 10) ? 4 : 5;
121
122         snprintf(p, cpu_reg_names_size, "avr%dH", i);
123 #ifdef HOST_WORDS_BIGENDIAN
124         cpu_avrh[i] = tcg_global_mem_new_i64(cpu_env,
125                                              offsetof(CPUPPCState, avr[i].u64[0]), p);
126 #else
127         cpu_avrh[i] = tcg_global_mem_new_i64(cpu_env,
128                                              offsetof(CPUPPCState, avr[i].u64[1]), p);
129 #endif
130         p += (i < 10) ? 6 : 7;
131         cpu_reg_names_size -= (i < 10) ? 6 : 7;
132
133         snprintf(p, cpu_reg_names_size, "avr%dL", i);
134 #ifdef HOST_WORDS_BIGENDIAN
135         cpu_avrl[i] = tcg_global_mem_new_i64(cpu_env,
136                                              offsetof(CPUPPCState, avr[i].u64[1]), p);
137 #else
138         cpu_avrl[i] = tcg_global_mem_new_i64(cpu_env,
139                                              offsetof(CPUPPCState, avr[i].u64[0]), p);
140 #endif
141         p += (i < 10) ? 6 : 7;
142         cpu_reg_names_size -= (i < 10) ? 6 : 7;
143         snprintf(p, cpu_reg_names_size, "vsr%d", i);
144         cpu_vsr[i] = tcg_global_mem_new_i64(cpu_env,
145                                             offsetof(CPUPPCState, vsr[i]), p);
146         p += (i < 10) ? 5 : 6;
147         cpu_reg_names_size -= (i < 10) ? 5 : 6;
148     }
149
150     cpu_nip = tcg_global_mem_new(cpu_env,
151                                  offsetof(CPUPPCState, nip), "nip");
152
153     cpu_msr = tcg_global_mem_new(cpu_env,
154                                  offsetof(CPUPPCState, msr), "msr");
155
156     cpu_ctr = tcg_global_mem_new(cpu_env,
157                                  offsetof(CPUPPCState, ctr), "ctr");
158
159     cpu_lr = tcg_global_mem_new(cpu_env,
160                                 offsetof(CPUPPCState, lr), "lr");
161
162 #if defined(TARGET_PPC64)
163     cpu_cfar = tcg_global_mem_new(cpu_env,
164                                   offsetof(CPUPPCState, cfar), "cfar");
165 #endif
166
167     cpu_xer = tcg_global_mem_new(cpu_env,
168                                  offsetof(CPUPPCState, xer), "xer");
169     cpu_so = tcg_global_mem_new(cpu_env,
170                                 offsetof(CPUPPCState, so), "SO");
171     cpu_ov = tcg_global_mem_new(cpu_env,
172                                 offsetof(CPUPPCState, ov), "OV");
173     cpu_ca = tcg_global_mem_new(cpu_env,
174                                 offsetof(CPUPPCState, ca), "CA");
175
176     cpu_reserve = tcg_global_mem_new(cpu_env,
177                                      offsetof(CPUPPCState, reserve_addr),
178                                      "reserve_addr");
179
180     cpu_fpscr = tcg_global_mem_new(cpu_env,
181                                    offsetof(CPUPPCState, fpscr), "fpscr");
182
183     cpu_access_type = tcg_global_mem_new_i32(cpu_env,
184                                              offsetof(CPUPPCState, access_type), "access_type");
185
186     done_init = 1;
187 }
188
189 /* internal defines */
190 struct DisasContext {
191     struct TranslationBlock *tb;
192     target_ulong nip;
193     uint32_t opcode;
194     uint32_t exception;
195     /* Routine used to access memory */
196     bool pr, hv, dr, le_mode;
197     bool lazy_tlb_flush;
198     bool need_access_type;
199     int mem_idx;
200     int access_type;
201     /* Translation flags */
202     TCGMemOp default_tcg_memop_mask;
203 #if defined(TARGET_PPC64)
204     bool sf_mode;
205     bool has_cfar;
206 #endif
207     bool fpu_enabled;
208     bool altivec_enabled;
209     bool vsx_enabled;
210     bool spe_enabled;
211     bool tm_enabled;
212     ppc_spr_t *spr_cb; /* Needed to check rights for mfspr/mtspr */
213     int singlestep_enabled;
214     uint64_t insns_flags;
215     uint64_t insns_flags2;
216 };
217
218 /* Return true iff byteswap is needed in a scalar memop */
219 static inline bool need_byteswap(const DisasContext *ctx)
220 {
221 #if defined(TARGET_WORDS_BIGENDIAN)
222      return ctx->le_mode;
223 #else
224      return !ctx->le_mode;
225 #endif
226 }
227
228 /* True when active word size < size of target_long.  */
229 #ifdef TARGET_PPC64
230 # define NARROW_MODE(C)  (!(C)->sf_mode)
231 #else
232 # define NARROW_MODE(C)  0
233 #endif
234
235 struct opc_handler_t {
236     /* invalid bits for instruction 1 (Rc(opcode) == 0) */
237     uint32_t inval1;
238     /* invalid bits for instruction 2 (Rc(opcode) == 1) */
239     uint32_t inval2;
240     /* instruction type */
241     uint64_t type;
242     /* extended instruction type */
243     uint64_t type2;
244     /* handler */
245     void (*handler)(DisasContext *ctx);
246 #if defined(DO_PPC_STATISTICS) || defined(PPC_DUMP_CPU)
247     const char *oname;
248 #endif
249 #if defined(DO_PPC_STATISTICS)
250     uint64_t count;
251 #endif
252 };
253
254 static inline void gen_set_access_type(DisasContext *ctx, int access_type)
255 {
256     if (ctx->need_access_type && ctx->access_type != access_type) {
257         tcg_gen_movi_i32(cpu_access_type, access_type);
258         ctx->access_type = access_type;
259     }
260 }
261
262 static inline void gen_update_nip(DisasContext *ctx, target_ulong nip)
263 {
264     if (NARROW_MODE(ctx)) {
265         nip = (uint32_t)nip;
266     }
267     tcg_gen_movi_tl(cpu_nip, nip);
268 }
269
270 static void gen_exception_err(DisasContext *ctx, uint32_t excp, uint32_t error)
271 {
272     TCGv_i32 t0, t1;
273
274     /* These are all synchronous exceptions, we set the PC back to
275      * the faulting instruction
276      */
277     if (ctx->exception == POWERPC_EXCP_NONE) {
278         gen_update_nip(ctx, ctx->nip - 4);
279     }
280     t0 = tcg_const_i32(excp);
281     t1 = tcg_const_i32(error);
282     gen_helper_raise_exception_err(cpu_env, t0, t1);
283     tcg_temp_free_i32(t0);
284     tcg_temp_free_i32(t1);
285     ctx->exception = (excp);
286 }
287
288 static void gen_exception(DisasContext *ctx, uint32_t excp)
289 {
290     TCGv_i32 t0;
291
292     /* These are all synchronous exceptions, we set the PC back to
293      * the faulting instruction
294      */
295     if (ctx->exception == POWERPC_EXCP_NONE) {
296         gen_update_nip(ctx, ctx->nip - 4);
297     }
298     t0 = tcg_const_i32(excp);
299     gen_helper_raise_exception(cpu_env, t0);
300     tcg_temp_free_i32(t0);
301     ctx->exception = (excp);
302 }
303
304 static void gen_exception_nip(DisasContext *ctx, uint32_t excp,
305                               target_ulong nip)
306 {
307     TCGv_i32 t0;
308
309     gen_update_nip(ctx, nip);
310     t0 = tcg_const_i32(excp);
311     gen_helper_raise_exception(cpu_env, t0);
312     tcg_temp_free_i32(t0);
313     ctx->exception = (excp);
314 }
315
316 static void gen_debug_exception(DisasContext *ctx)
317 {
318     TCGv_i32 t0;
319
320     /* These are all synchronous exceptions, we set the PC back to
321      * the faulting instruction
322      */
323     if ((ctx->exception != POWERPC_EXCP_BRANCH) &&
324         (ctx->exception != POWERPC_EXCP_SYNC)) {
325         gen_update_nip(ctx, ctx->nip - 4);
326     }
327     t0 = tcg_const_i32(EXCP_DEBUG);
328     gen_helper_raise_exception(cpu_env, t0);
329     tcg_temp_free_i32(t0);
330 }
331
332 static inline void gen_inval_exception(DisasContext *ctx, uint32_t error)
333 {
334     /* Will be converted to program check if needed */
335     gen_exception_err(ctx, POWERPC_EXCP_HV_EMU, POWERPC_EXCP_INVAL | error);
336 }
337
338 static inline void gen_priv_exception(DisasContext *ctx, uint32_t error)
339 {
340     gen_exception_err(ctx, POWERPC_EXCP_PROGRAM, POWERPC_EXCP_PRIV | error);
341 }
342
343 static inline void gen_hvpriv_exception(DisasContext *ctx, uint32_t error)
344 {
345     /* Will be converted to program check if needed */
346     gen_exception_err(ctx, POWERPC_EXCP_HV_EMU, POWERPC_EXCP_PRIV | error);
347 }
348
349 /* Stop translation */
350 static inline void gen_stop_exception(DisasContext *ctx)
351 {
352     gen_update_nip(ctx, ctx->nip);
353     ctx->exception = POWERPC_EXCP_STOP;
354 }
355
356 #ifndef CONFIG_USER_ONLY
357 /* No need to update nip here, as execution flow will change */
358 static inline void gen_sync_exception(DisasContext *ctx)
359 {
360     ctx->exception = POWERPC_EXCP_SYNC;
361 }
362 #endif
363
364 #define GEN_HANDLER(name, opc1, opc2, opc3, inval, type)                      \
365 GEN_OPCODE(name, opc1, opc2, opc3, inval, type, PPC_NONE)
366
367 #define GEN_HANDLER_E(name, opc1, opc2, opc3, inval, type, type2)             \
368 GEN_OPCODE(name, opc1, opc2, opc3, inval, type, type2)
369
370 #define GEN_HANDLER2(name, onam, opc1, opc2, opc3, inval, type)               \
371 GEN_OPCODE2(name, onam, opc1, opc2, opc3, inval, type, PPC_NONE)
372
373 #define GEN_HANDLER2_E(name, onam, opc1, opc2, opc3, inval, type, type2)      \
374 GEN_OPCODE2(name, onam, opc1, opc2, opc3, inval, type, type2)
375
376 #define GEN_HANDLER_E_2(name, opc1, opc2, opc3, opc4, inval, type, type2)     \
377 GEN_OPCODE3(name, opc1, opc2, opc3, opc4, inval, type, type2)
378
379 typedef struct opcode_t {
380     unsigned char opc1, opc2, opc3, opc4;
381 #if HOST_LONG_BITS == 64 /* Explicitly align to 64 bits */
382     unsigned char pad[4];
383 #endif
384     opc_handler_t handler;
385     const char *oname;
386 } opcode_t;
387
388 /* Helpers for priv. check */
389 #define GEN_PRIV                                                \
390     do {                                                        \
391         gen_priv_exception(ctx, POWERPC_EXCP_PRIV_OPC); return; \
392     } while (0)
393
394 #if defined(CONFIG_USER_ONLY)
395 #define CHK_HV GEN_PRIV
396 #define CHK_SV GEN_PRIV
397 #define CHK_HVRM GEN_PRIV
398 #else
399 #define CHK_HV                                                          \
400     do {                                                                \
401         if (unlikely(ctx->pr || !ctx->hv)) {                            \
402             GEN_PRIV;                                                   \
403         }                                                               \
404     } while (0)
405 #define CHK_SV                   \
406     do {                         \
407         if (unlikely(ctx->pr)) { \
408             GEN_PRIV;            \
409         }                        \
410     } while (0)
411 #define CHK_HVRM                                            \
412     do {                                                    \
413         if (unlikely(ctx->pr || !ctx->hv || ctx->dr)) {     \
414             GEN_PRIV;                                       \
415         }                                                   \
416     } while (0)
417 #endif
418
419 #define CHK_NONE
420
421
422 /*****************************************************************************/
423 /***                           Instruction decoding                        ***/
424 #define EXTRACT_HELPER(name, shift, nb)                                       \
425 static inline uint32_t name(uint32_t opcode)                                  \
426 {                                                                             \
427     return (opcode >> (shift)) & ((1 << (nb)) - 1);                           \
428 }
429
430 #define EXTRACT_SHELPER(name, shift, nb)                                      \
431 static inline int32_t name(uint32_t opcode)                                   \
432 {                                                                             \
433     return (int16_t)((opcode >> (shift)) & ((1 << (nb)) - 1));                \
434 }
435
436 #define EXTRACT_HELPER_SPLIT(name, shift1, nb1, shift2, nb2)                  \
437 static inline uint32_t name(uint32_t opcode)                                  \
438 {                                                                             \
439     return (((opcode >> (shift1)) & ((1 << (nb1)) - 1)) << nb2) |             \
440             ((opcode >> (shift2)) & ((1 << (nb2)) - 1));                      \
441 }
442
443 #define EXTRACT_HELPER_DXFORM(name,                                           \
444                               d0_bits, shift_op_d0, shift_d0,                 \
445                               d1_bits, shift_op_d1, shift_d1,                 \
446                               d2_bits, shift_op_d2, shift_d2)                 \
447 static inline int16_t name(uint32_t opcode)                                   \
448 {                                                                             \
449     return                                                                    \
450         (((opcode >> (shift_op_d0)) & ((1 << (d0_bits)) - 1)) << (shift_d0)) | \
451         (((opcode >> (shift_op_d1)) & ((1 << (d1_bits)) - 1)) << (shift_d1)) | \
452         (((opcode >> (shift_op_d2)) & ((1 << (d2_bits)) - 1)) << (shift_d2));  \
453 }
454
455
456 /* Opcode part 1 */
457 EXTRACT_HELPER(opc1, 26, 6);
458 /* Opcode part 2 */
459 EXTRACT_HELPER(opc2, 1, 5);
460 /* Opcode part 3 */
461 EXTRACT_HELPER(opc3, 6, 5);
462 /* Opcode part 4 */
463 EXTRACT_HELPER(opc4, 16, 5);
464 /* Update Cr0 flags */
465 EXTRACT_HELPER(Rc, 0, 1);
466 /* Update Cr6 flags (Altivec) */
467 EXTRACT_HELPER(Rc21, 10, 1);
468 /* Destination */
469 EXTRACT_HELPER(rD, 21, 5);
470 /* Source */
471 EXTRACT_HELPER(rS, 21, 5);
472 /* First operand */
473 EXTRACT_HELPER(rA, 16, 5);
474 /* Second operand */
475 EXTRACT_HELPER(rB, 11, 5);
476 /* Third operand */
477 EXTRACT_HELPER(rC, 6, 5);
478 /***                               Get CRn                                 ***/
479 EXTRACT_HELPER(crfD, 23, 3);
480 EXTRACT_HELPER(crfS, 18, 3);
481 EXTRACT_HELPER(crbD, 21, 5);
482 EXTRACT_HELPER(crbA, 16, 5);
483 EXTRACT_HELPER(crbB, 11, 5);
484 /* SPR / TBL */
485 EXTRACT_HELPER(_SPR, 11, 10);
486 static inline uint32_t SPR(uint32_t opcode)
487 {
488     uint32_t sprn = _SPR(opcode);
489
490     return ((sprn >> 5) & 0x1F) | ((sprn & 0x1F) << 5);
491 }
492 /***                              Get constants                            ***/
493 /* 16 bits signed immediate value */
494 EXTRACT_SHELPER(SIMM, 0, 16);
495 /* 16 bits unsigned immediate value */
496 EXTRACT_HELPER(UIMM, 0, 16);
497 /* 5 bits signed immediate value */
498 EXTRACT_HELPER(SIMM5, 16, 5);
499 /* 5 bits signed immediate value */
500 EXTRACT_HELPER(UIMM5, 16, 5);
501 /* 4 bits unsigned immediate value */
502 EXTRACT_HELPER(UIMM4, 16, 4);
503 /* Bit count */
504 EXTRACT_HELPER(NB, 11, 5);
505 /* Shift count */
506 EXTRACT_HELPER(SH, 11, 5);
507 /* Vector shift count */
508 EXTRACT_HELPER(VSH, 6, 4);
509 /* Mask start */
510 EXTRACT_HELPER(MB, 6, 5);
511 /* Mask end */
512 EXTRACT_HELPER(ME, 1, 5);
513 /* Trap operand */
514 EXTRACT_HELPER(TO, 21, 5);
515
516 EXTRACT_HELPER(CRM, 12, 8);
517
518 #ifndef CONFIG_USER_ONLY
519 EXTRACT_HELPER(SR, 16, 4);
520 #endif
521
522 /* mtfsf/mtfsfi */
523 EXTRACT_HELPER(FPBF, 23, 3);
524 EXTRACT_HELPER(FPIMM, 12, 4);
525 EXTRACT_HELPER(FPL, 25, 1);
526 EXTRACT_HELPER(FPFLM, 17, 8);
527 EXTRACT_HELPER(FPW, 16, 1);
528
529 /* addpcis */
530 EXTRACT_HELPER_DXFORM(DX, 10, 6, 6, 5, 16, 1, 1, 0, 0)
531
532 /***                            Jump target decoding                       ***/
533 /* Immediate address */
534 static inline target_ulong LI(uint32_t opcode)
535 {
536     return (opcode >> 0) & 0x03FFFFFC;
537 }
538
539 static inline uint32_t BD(uint32_t opcode)
540 {
541     return (opcode >> 0) & 0xFFFC;
542 }
543
544 EXTRACT_HELPER(BO, 21, 5);
545 EXTRACT_HELPER(BI, 16, 5);
546 /* Absolute/relative address */
547 EXTRACT_HELPER(AA, 1, 1);
548 /* Link */
549 EXTRACT_HELPER(LK, 0, 1);
550
551 /* DFP Z22-form */
552 EXTRACT_HELPER(DCM, 10, 6)
553
554 /* DFP Z23-form */
555 EXTRACT_HELPER(RMC, 9, 2)
556
557 /* Create a mask between <start> and <end> bits */
558 static inline target_ulong MASK(uint32_t start, uint32_t end)
559 {
560     target_ulong ret;
561
562 #if defined(TARGET_PPC64)
563     if (likely(start == 0)) {
564         ret = UINT64_MAX << (63 - end);
565     } else if (likely(end == 63)) {
566         ret = UINT64_MAX >> start;
567     }
568 #else
569     if (likely(start == 0)) {
570         ret = UINT32_MAX << (31  - end);
571     } else if (likely(end == 31)) {
572         ret = UINT32_MAX >> start;
573     }
574 #endif
575     else {
576         ret = (((target_ulong)(-1ULL)) >> (start)) ^
577             (((target_ulong)(-1ULL) >> (end)) >> 1);
578         if (unlikely(start > end))
579             return ~ret;
580     }
581
582     return ret;
583 }
584
585 EXTRACT_HELPER_SPLIT(xT, 0, 1, 21, 5);
586 EXTRACT_HELPER_SPLIT(xS, 0, 1, 21, 5);
587 EXTRACT_HELPER_SPLIT(xA, 2, 1, 16, 5);
588 EXTRACT_HELPER_SPLIT(xB, 1, 1, 11, 5);
589 EXTRACT_HELPER_SPLIT(xC, 3, 1,  6, 5);
590 EXTRACT_HELPER(DM, 8, 2);
591 EXTRACT_HELPER(UIM, 16, 2);
592 EXTRACT_HELPER(SHW, 8, 2);
593 EXTRACT_HELPER(SP, 19, 2);
594 /*****************************************************************************/
595 /* PowerPC instructions table                                                */
596
597 #if defined(DO_PPC_STATISTICS)
598 #define GEN_OPCODE(name, op1, op2, op3, invl, _typ, _typ2)                    \
599 {                                                                             \
600     .opc1 = op1,                                                              \
601     .opc2 = op2,                                                              \
602     .opc3 = op3,                                                              \
603     .opc4 = 0xff,                                                             \
604     .handler = {                                                              \
605         .inval1  = invl,                                                      \
606         .type = _typ,                                                         \
607         .type2 = _typ2,                                                       \
608         .handler = &gen_##name,                                               \
609         .oname = stringify(name),                                             \
610     },                                                                        \
611     .oname = stringify(name),                                                 \
612 }
613 #define GEN_OPCODE_DUAL(name, op1, op2, op3, invl1, invl2, _typ, _typ2)       \
614 {                                                                             \
615     .opc1 = op1,                                                              \
616     .opc2 = op2,                                                              \
617     .opc3 = op3,                                                              \
618     .opc4 = 0xff,                                                             \
619     .handler = {                                                              \
620         .inval1  = invl1,                                                     \
621         .inval2  = invl2,                                                     \
622         .type = _typ,                                                         \
623         .type2 = _typ2,                                                       \
624         .handler = &gen_##name,                                               \
625         .oname = stringify(name),                                             \
626     },                                                                        \
627     .oname = stringify(name),                                                 \
628 }
629 #define GEN_OPCODE2(name, onam, op1, op2, op3, invl, _typ, _typ2)             \
630 {                                                                             \
631     .opc1 = op1,                                                              \
632     .opc2 = op2,                                                              \
633     .opc3 = op3,                                                              \
634     .opc4 = 0xff,                                                             \
635     .handler = {                                                              \
636         .inval1  = invl,                                                      \
637         .type = _typ,                                                         \
638         .type2 = _typ2,                                                       \
639         .handler = &gen_##name,                                               \
640         .oname = onam,                                                        \
641     },                                                                        \
642     .oname = onam,                                                            \
643 }
644 #define GEN_OPCODE3(name, op1, op2, op3, op4, invl, _typ, _typ2)              \
645 {                                                                             \
646     .opc1 = op1,                                                              \
647     .opc2 = op2,                                                              \
648     .opc3 = op3,                                                              \
649     .opc4 = op4,                                                              \
650     .handler = {                                                              \
651         .inval1  = invl,                                                      \
652         .type = _typ,                                                         \
653         .type2 = _typ2,                                                       \
654         .handler = &gen_##name,                                               \
655         .oname = stringify(name),                                             \
656     },                                                                        \
657     .oname = stringify(name),                                                 \
658 }
659 #else
660 #define GEN_OPCODE(name, op1, op2, op3, invl, _typ, _typ2)                    \
661 {                                                                             \
662     .opc1 = op1,                                                              \
663     .opc2 = op2,                                                              \
664     .opc3 = op3,                                                              \
665     .opc4 = 0xff,                                                             \
666     .handler = {                                                              \
667         .inval1  = invl,                                                      \
668         .type = _typ,                                                         \
669         .type2 = _typ2,                                                       \
670         .handler = &gen_##name,                                               \
671     },                                                                        \
672     .oname = stringify(name),                                                 \
673 }
674 #define GEN_OPCODE_DUAL(name, op1, op2, op3, invl1, invl2, _typ, _typ2)       \
675 {                                                                             \
676     .opc1 = op1,                                                              \
677     .opc2 = op2,                                                              \
678     .opc3 = op3,                                                              \
679     .opc4 = 0xff,                                                             \
680     .handler = {                                                              \
681         .inval1  = invl1,                                                     \
682         .inval2  = invl2,                                                     \
683         .type = _typ,                                                         \
684         .type2 = _typ2,                                                       \
685         .handler = &gen_##name,                                               \
686     },                                                                        \
687     .oname = stringify(name),                                                 \
688 }
689 #define GEN_OPCODE2(name, onam, op1, op2, op3, invl, _typ, _typ2)             \
690 {                                                                             \
691     .opc1 = op1,                                                              \
692     .opc2 = op2,                                                              \
693     .opc3 = op3,                                                              \
694     .opc4 = 0xff,                                                             \
695     .handler = {                                                              \
696         .inval1  = invl,                                                      \
697         .type = _typ,                                                         \
698         .type2 = _typ2,                                                       \
699         .handler = &gen_##name,                                               \
700     },                                                                        \
701     .oname = onam,                                                            \
702 }
703 #define GEN_OPCODE3(name, op1, op2, op3, op4, invl, _typ, _typ2)              \
704 {                                                                             \
705     .opc1 = op1,                                                              \
706     .opc2 = op2,                                                              \
707     .opc3 = op3,                                                              \
708     .opc4 = op4,                                                              \
709     .handler = {                                                              \
710         .inval1  = invl,                                                      \
711         .type = _typ,                                                         \
712         .type2 = _typ2,                                                       \
713         .handler = &gen_##name,                                               \
714     },                                                                        \
715     .oname = stringify(name),                                                 \
716 }
717 #endif
718
719 /* SPR load/store helpers */
720 static inline void gen_load_spr(TCGv t, int reg)
721 {
722     tcg_gen_ld_tl(t, cpu_env, offsetof(CPUPPCState, spr[reg]));
723 }
724
725 static inline void gen_store_spr(int reg, TCGv t)
726 {
727     tcg_gen_st_tl(t, cpu_env, offsetof(CPUPPCState, spr[reg]));
728 }
729
730 /* Invalid instruction */
731 static void gen_invalid(DisasContext *ctx)
732 {
733     gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
734 }
735
736 static opc_handler_t invalid_handler = {
737     .inval1  = 0xFFFFFFFF,
738     .inval2  = 0xFFFFFFFF,
739     .type    = PPC_NONE,
740     .type2   = PPC_NONE,
741     .handler = gen_invalid,
742 };
743
744 /***                           Integer comparison                          ***/
745
746 static inline void gen_op_cmp(TCGv arg0, TCGv arg1, int s, int crf)
747 {
748     TCGv t0 = tcg_temp_new();
749     TCGv_i32 t1 = tcg_temp_new_i32();
750
751     tcg_gen_trunc_tl_i32(cpu_crf[crf], cpu_so);
752
753     tcg_gen_setcond_tl((s ? TCG_COND_LT: TCG_COND_LTU), t0, arg0, arg1);
754     tcg_gen_trunc_tl_i32(t1, t0);
755     tcg_gen_shli_i32(t1, t1, CRF_LT);
756     tcg_gen_or_i32(cpu_crf[crf], cpu_crf[crf], t1);
757
758     tcg_gen_setcond_tl((s ? TCG_COND_GT: TCG_COND_GTU), t0, arg0, arg1);
759     tcg_gen_trunc_tl_i32(t1, t0);
760     tcg_gen_shli_i32(t1, t1, CRF_GT);
761     tcg_gen_or_i32(cpu_crf[crf], cpu_crf[crf], t1);
762
763     tcg_gen_setcond_tl(TCG_COND_EQ, t0, arg0, arg1);
764     tcg_gen_trunc_tl_i32(t1, t0);
765     tcg_gen_shli_i32(t1, t1, CRF_EQ);
766     tcg_gen_or_i32(cpu_crf[crf], cpu_crf[crf], t1);
767
768     tcg_temp_free(t0);
769     tcg_temp_free_i32(t1);
770 }
771
772 static inline void gen_op_cmpi(TCGv arg0, target_ulong arg1, int s, int crf)
773 {
774     TCGv t0 = tcg_const_tl(arg1);
775     gen_op_cmp(arg0, t0, s, crf);
776     tcg_temp_free(t0);
777 }
778
779 static inline void gen_op_cmp32(TCGv arg0, TCGv arg1, int s, int crf)
780 {
781     TCGv t0, t1;
782     t0 = tcg_temp_new();
783     t1 = tcg_temp_new();
784     if (s) {
785         tcg_gen_ext32s_tl(t0, arg0);
786         tcg_gen_ext32s_tl(t1, arg1);
787     } else {
788         tcg_gen_ext32u_tl(t0, arg0);
789         tcg_gen_ext32u_tl(t1, arg1);
790     }
791     gen_op_cmp(t0, t1, s, crf);
792     tcg_temp_free(t1);
793     tcg_temp_free(t0);
794 }
795
796 static inline void gen_op_cmpi32(TCGv arg0, target_ulong arg1, int s, int crf)
797 {
798     TCGv t0 = tcg_const_tl(arg1);
799     gen_op_cmp32(arg0, t0, s, crf);
800     tcg_temp_free(t0);
801 }
802
803 static inline void gen_set_Rc0(DisasContext *ctx, TCGv reg)
804 {
805     if (NARROW_MODE(ctx)) {
806         gen_op_cmpi32(reg, 0, 1, 0);
807     } else {
808         gen_op_cmpi(reg, 0, 1, 0);
809     }
810 }
811
812 /* cmp */
813 static void gen_cmp(DisasContext *ctx)
814 {
815     if ((ctx->opcode & 0x00200000) && (ctx->insns_flags & PPC_64B)) {
816         gen_op_cmp(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
817                    1, crfD(ctx->opcode));
818     } else {
819         gen_op_cmp32(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
820                      1, crfD(ctx->opcode));
821     }
822 }
823
824 /* cmpi */
825 static void gen_cmpi(DisasContext *ctx)
826 {
827     if ((ctx->opcode & 0x00200000) && (ctx->insns_flags & PPC_64B)) {
828         gen_op_cmpi(cpu_gpr[rA(ctx->opcode)], SIMM(ctx->opcode),
829                     1, crfD(ctx->opcode));
830     } else {
831         gen_op_cmpi32(cpu_gpr[rA(ctx->opcode)], SIMM(ctx->opcode),
832                       1, crfD(ctx->opcode));
833     }
834 }
835
836 /* cmpl */
837 static void gen_cmpl(DisasContext *ctx)
838 {
839     if ((ctx->opcode & 0x00200000) && (ctx->insns_flags & PPC_64B)) {
840         gen_op_cmp(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
841                    0, crfD(ctx->opcode));
842     } else {
843         gen_op_cmp32(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
844                      0, crfD(ctx->opcode));
845     }
846 }
847
848 /* cmpli */
849 static void gen_cmpli(DisasContext *ctx)
850 {
851     if ((ctx->opcode & 0x00200000) && (ctx->insns_flags & PPC_64B)) {
852         gen_op_cmpi(cpu_gpr[rA(ctx->opcode)], UIMM(ctx->opcode),
853                     0, crfD(ctx->opcode));
854     } else {
855         gen_op_cmpi32(cpu_gpr[rA(ctx->opcode)], UIMM(ctx->opcode),
856                       0, crfD(ctx->opcode));
857     }
858 }
859
860 /* cmprb - range comparison: isupper, isaplha, islower*/
861 static void gen_cmprb(DisasContext *ctx)
862 {
863     TCGv_i32 src1 = tcg_temp_new_i32();
864     TCGv_i32 src2 = tcg_temp_new_i32();
865     TCGv_i32 src2lo = tcg_temp_new_i32();
866     TCGv_i32 src2hi = tcg_temp_new_i32();
867     TCGv_i32 crf = cpu_crf[crfD(ctx->opcode)];
868
869     tcg_gen_trunc_tl_i32(src1, cpu_gpr[rA(ctx->opcode)]);
870     tcg_gen_trunc_tl_i32(src2, cpu_gpr[rB(ctx->opcode)]);
871
872     tcg_gen_andi_i32(src1, src1, 0xFF);
873     tcg_gen_ext8u_i32(src2lo, src2);
874     tcg_gen_shri_i32(src2, src2, 8);
875     tcg_gen_ext8u_i32(src2hi, src2);
876
877     tcg_gen_setcond_i32(TCG_COND_LEU, src2lo, src2lo, src1);
878     tcg_gen_setcond_i32(TCG_COND_LEU, src2hi, src1, src2hi);
879     tcg_gen_and_i32(crf, src2lo, src2hi);
880
881     if (ctx->opcode & 0x00200000) {
882         tcg_gen_shri_i32(src2, src2, 8);
883         tcg_gen_ext8u_i32(src2lo, src2);
884         tcg_gen_shri_i32(src2, src2, 8);
885         tcg_gen_ext8u_i32(src2hi, src2);
886         tcg_gen_setcond_i32(TCG_COND_LEU, src2lo, src2lo, src1);
887         tcg_gen_setcond_i32(TCG_COND_LEU, src2hi, src1, src2hi);
888         tcg_gen_and_i32(src2lo, src2lo, src2hi);
889         tcg_gen_or_i32(crf, crf, src2lo);
890     }
891     tcg_gen_shli_i32(crf, crf, CRF_GT);
892     tcg_temp_free_i32(src1);
893     tcg_temp_free_i32(src2);
894     tcg_temp_free_i32(src2lo);
895     tcg_temp_free_i32(src2hi);
896 }
897
898 #if defined(TARGET_PPC64)
899 /* cmpeqb */
900 static void gen_cmpeqb(DisasContext *ctx)
901 {
902     gen_helper_cmpeqb(cpu_crf[crfD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)],
903                       cpu_gpr[rB(ctx->opcode)]);
904 }
905 #endif
906
907 /* isel (PowerPC 2.03 specification) */
908 static void gen_isel(DisasContext *ctx)
909 {
910     uint32_t bi = rC(ctx->opcode);
911     uint32_t mask = 0x08 >> (bi & 0x03);
912     TCGv t0 = tcg_temp_new();
913     TCGv zr;
914
915     tcg_gen_extu_i32_tl(t0, cpu_crf[bi >> 2]);
916     tcg_gen_andi_tl(t0, t0, mask);
917
918     zr = tcg_const_tl(0);
919     tcg_gen_movcond_tl(TCG_COND_NE, cpu_gpr[rD(ctx->opcode)], t0, zr,
920                        rA(ctx->opcode) ? cpu_gpr[rA(ctx->opcode)] : zr,
921                        cpu_gpr[rB(ctx->opcode)]);
922     tcg_temp_free(zr);
923     tcg_temp_free(t0);
924 }
925
926 /* cmpb: PowerPC 2.05 specification */
927 static void gen_cmpb(DisasContext *ctx)
928 {
929     gen_helper_cmpb(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)],
930                     cpu_gpr[rB(ctx->opcode)]);
931 }
932
933 /***                           Integer arithmetic                          ***/
934
935 static inline void gen_op_arith_compute_ov(DisasContext *ctx, TCGv arg0,
936                                            TCGv arg1, TCGv arg2, int sub)
937 {
938     TCGv t0 = tcg_temp_new();
939
940     tcg_gen_xor_tl(cpu_ov, arg0, arg2);
941     tcg_gen_xor_tl(t0, arg1, arg2);
942     if (sub) {
943         tcg_gen_and_tl(cpu_ov, cpu_ov, t0);
944     } else {
945         tcg_gen_andc_tl(cpu_ov, cpu_ov, t0);
946     }
947     tcg_temp_free(t0);
948     if (NARROW_MODE(ctx)) {
949         tcg_gen_ext32s_tl(cpu_ov, cpu_ov);
950     }
951     tcg_gen_shri_tl(cpu_ov, cpu_ov, TARGET_LONG_BITS - 1);
952     tcg_gen_or_tl(cpu_so, cpu_so, cpu_ov);
953 }
954
955 /* Common add function */
956 static inline void gen_op_arith_add(DisasContext *ctx, TCGv ret, TCGv arg1,
957                                     TCGv arg2, bool add_ca, bool compute_ca,
958                                     bool compute_ov, bool compute_rc0)
959 {
960     TCGv t0 = ret;
961
962     if (compute_ca || compute_ov) {
963         t0 = tcg_temp_new();
964     }
965
966     if (compute_ca) {
967         if (NARROW_MODE(ctx)) {
968             /* Caution: a non-obvious corner case of the spec is that we
969                must produce the *entire* 64-bit addition, but produce the
970                carry into bit 32.  */
971             TCGv t1 = tcg_temp_new();
972             tcg_gen_xor_tl(t1, arg1, arg2);        /* add without carry */
973             tcg_gen_add_tl(t0, arg1, arg2);
974             if (add_ca) {
975                 tcg_gen_add_tl(t0, t0, cpu_ca);
976             }
977             tcg_gen_xor_tl(cpu_ca, t0, t1);        /* bits changed w/ carry */
978             tcg_temp_free(t1);
979             tcg_gen_shri_tl(cpu_ca, cpu_ca, 32);   /* extract bit 32 */
980             tcg_gen_andi_tl(cpu_ca, cpu_ca, 1);
981         } else {
982             TCGv zero = tcg_const_tl(0);
983             if (add_ca) {
984                 tcg_gen_add2_tl(t0, cpu_ca, arg1, zero, cpu_ca, zero);
985                 tcg_gen_add2_tl(t0, cpu_ca, t0, cpu_ca, arg2, zero);
986             } else {
987                 tcg_gen_add2_tl(t0, cpu_ca, arg1, zero, arg2, zero);
988             }
989             tcg_temp_free(zero);
990         }
991     } else {
992         tcg_gen_add_tl(t0, arg1, arg2);
993         if (add_ca) {
994             tcg_gen_add_tl(t0, t0, cpu_ca);
995         }
996     }
997
998     if (compute_ov) {
999         gen_op_arith_compute_ov(ctx, t0, arg1, arg2, 0);
1000     }
1001     if (unlikely(compute_rc0)) {
1002         gen_set_Rc0(ctx, t0);
1003     }
1004
1005     if (!TCGV_EQUAL(t0, ret)) {
1006         tcg_gen_mov_tl(ret, t0);
1007         tcg_temp_free(t0);
1008     }
1009 }
1010 /* Add functions with two operands */
1011 #define GEN_INT_ARITH_ADD(name, opc3, add_ca, compute_ca, compute_ov)         \
1012 static void glue(gen_, name)(DisasContext *ctx)                               \
1013 {                                                                             \
1014     gen_op_arith_add(ctx, cpu_gpr[rD(ctx->opcode)],                           \
1015                      cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],      \
1016                      add_ca, compute_ca, compute_ov, Rc(ctx->opcode));        \
1017 }
1018 /* Add functions with one operand and one immediate */
1019 #define GEN_INT_ARITH_ADD_CONST(name, opc3, const_val,                        \
1020                                 add_ca, compute_ca, compute_ov)               \
1021 static void glue(gen_, name)(DisasContext *ctx)                               \
1022 {                                                                             \
1023     TCGv t0 = tcg_const_tl(const_val);                                        \
1024     gen_op_arith_add(ctx, cpu_gpr[rD(ctx->opcode)],                           \
1025                      cpu_gpr[rA(ctx->opcode)], t0,                            \
1026                      add_ca, compute_ca, compute_ov, Rc(ctx->opcode));        \
1027     tcg_temp_free(t0);                                                        \
1028 }
1029
1030 /* add  add.  addo  addo. */
1031 GEN_INT_ARITH_ADD(add, 0x08, 0, 0, 0)
1032 GEN_INT_ARITH_ADD(addo, 0x18, 0, 0, 1)
1033 /* addc  addc.  addco  addco. */
1034 GEN_INT_ARITH_ADD(addc, 0x00, 0, 1, 0)
1035 GEN_INT_ARITH_ADD(addco, 0x10, 0, 1, 1)
1036 /* adde  adde.  addeo  addeo. */
1037 GEN_INT_ARITH_ADD(adde, 0x04, 1, 1, 0)
1038 GEN_INT_ARITH_ADD(addeo, 0x14, 1, 1, 1)
1039 /* addme  addme.  addmeo  addmeo.  */
1040 GEN_INT_ARITH_ADD_CONST(addme, 0x07, -1LL, 1, 1, 0)
1041 GEN_INT_ARITH_ADD_CONST(addmeo, 0x17, -1LL, 1, 1, 1)
1042 /* addze  addze.  addzeo  addzeo.*/
1043 GEN_INT_ARITH_ADD_CONST(addze, 0x06, 0, 1, 1, 0)
1044 GEN_INT_ARITH_ADD_CONST(addzeo, 0x16, 0, 1, 1, 1)
1045 /* addi */
1046 static void gen_addi(DisasContext *ctx)
1047 {
1048     target_long simm = SIMM(ctx->opcode);
1049
1050     if (rA(ctx->opcode) == 0) {
1051         /* li case */
1052         tcg_gen_movi_tl(cpu_gpr[rD(ctx->opcode)], simm);
1053     } else {
1054         tcg_gen_addi_tl(cpu_gpr[rD(ctx->opcode)],
1055                         cpu_gpr[rA(ctx->opcode)], simm);
1056     }
1057 }
1058 /* addic  addic.*/
1059 static inline void gen_op_addic(DisasContext *ctx, bool compute_rc0)
1060 {
1061     TCGv c = tcg_const_tl(SIMM(ctx->opcode));
1062     gen_op_arith_add(ctx, cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)],
1063                      c, 0, 1, 0, compute_rc0);
1064     tcg_temp_free(c);
1065 }
1066
1067 static void gen_addic(DisasContext *ctx)
1068 {
1069     gen_op_addic(ctx, 0);
1070 }
1071
1072 static void gen_addic_(DisasContext *ctx)
1073 {
1074     gen_op_addic(ctx, 1);
1075 }
1076
1077 /* addis */
1078 static void gen_addis(DisasContext *ctx)
1079 {
1080     target_long simm = SIMM(ctx->opcode);
1081
1082     if (rA(ctx->opcode) == 0) {
1083         /* lis case */
1084         tcg_gen_movi_tl(cpu_gpr[rD(ctx->opcode)], simm << 16);
1085     } else {
1086         tcg_gen_addi_tl(cpu_gpr[rD(ctx->opcode)],
1087                         cpu_gpr[rA(ctx->opcode)], simm << 16);
1088     }
1089 }
1090
1091 /* addpcis */
1092 static void gen_addpcis(DisasContext *ctx)
1093 {
1094     target_long d = DX(ctx->opcode);
1095
1096     tcg_gen_movi_tl(cpu_gpr[rD(ctx->opcode)], ctx->nip + (d << 16));
1097 }
1098
1099 static inline void gen_op_arith_divw(DisasContext *ctx, TCGv ret, TCGv arg1,
1100                                      TCGv arg2, int sign, int compute_ov)
1101 {
1102     TCGv_i32 t0 = tcg_temp_new_i32();
1103     TCGv_i32 t1 = tcg_temp_new_i32();
1104     TCGv_i32 t2 = tcg_temp_new_i32();
1105     TCGv_i32 t3 = tcg_temp_new_i32();
1106
1107     tcg_gen_trunc_tl_i32(t0, arg1);
1108     tcg_gen_trunc_tl_i32(t1, arg2);
1109     if (sign) {
1110         tcg_gen_setcondi_i32(TCG_COND_EQ, t2, t0, INT_MIN);
1111         tcg_gen_setcondi_i32(TCG_COND_EQ, t3, t1, -1);
1112         tcg_gen_and_i32(t2, t2, t3);
1113         tcg_gen_setcondi_i32(TCG_COND_EQ, t3, t1, 0);
1114         tcg_gen_or_i32(t2, t2, t3);
1115         tcg_gen_movi_i32(t3, 0);
1116         tcg_gen_movcond_i32(TCG_COND_NE, t1, t2, t3, t2, t1);
1117         tcg_gen_div_i32(t3, t0, t1);
1118         tcg_gen_extu_i32_tl(ret, t3);
1119     } else {
1120         tcg_gen_setcondi_i32(TCG_COND_EQ, t2, t1, 0);
1121         tcg_gen_movi_i32(t3, 0);
1122         tcg_gen_movcond_i32(TCG_COND_NE, t1, t2, t3, t2, t1);
1123         tcg_gen_divu_i32(t3, t0, t1);
1124         tcg_gen_extu_i32_tl(ret, t3);
1125     }
1126     if (compute_ov) {
1127         tcg_gen_extu_i32_tl(cpu_ov, t2);
1128         tcg_gen_or_tl(cpu_so, cpu_so, cpu_ov);
1129     }
1130     tcg_temp_free_i32(t0);
1131     tcg_temp_free_i32(t1);
1132     tcg_temp_free_i32(t2);
1133     tcg_temp_free_i32(t3);
1134
1135     if (unlikely(Rc(ctx->opcode) != 0))
1136         gen_set_Rc0(ctx, ret);
1137 }
1138 /* Div functions */
1139 #define GEN_INT_ARITH_DIVW(name, opc3, sign, compute_ov)                      \
1140 static void glue(gen_, name)(DisasContext *ctx)                                       \
1141 {                                                                             \
1142     gen_op_arith_divw(ctx, cpu_gpr[rD(ctx->opcode)],                          \
1143                      cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],      \
1144                      sign, compute_ov);                                       \
1145 }
1146 /* divwu  divwu.  divwuo  divwuo.   */
1147 GEN_INT_ARITH_DIVW(divwu, 0x0E, 0, 0);
1148 GEN_INT_ARITH_DIVW(divwuo, 0x1E, 0, 1);
1149 /* divw  divw.  divwo  divwo.   */
1150 GEN_INT_ARITH_DIVW(divw, 0x0F, 1, 0);
1151 GEN_INT_ARITH_DIVW(divwo, 0x1F, 1, 1);
1152
1153 /* div[wd]eu[o][.] */
1154 #define GEN_DIVE(name, hlpr, compute_ov)                                      \
1155 static void gen_##name(DisasContext *ctx)                                     \
1156 {                                                                             \
1157     TCGv_i32 t0 = tcg_const_i32(compute_ov);                                  \
1158     gen_helper_##hlpr(cpu_gpr[rD(ctx->opcode)], cpu_env,                      \
1159                      cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)], t0); \
1160     tcg_temp_free_i32(t0);                                                    \
1161     if (unlikely(Rc(ctx->opcode) != 0)) {                                     \
1162         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);                           \
1163     }                                                                         \
1164 }
1165
1166 GEN_DIVE(divweu, divweu, 0);
1167 GEN_DIVE(divweuo, divweu, 1);
1168 GEN_DIVE(divwe, divwe, 0);
1169 GEN_DIVE(divweo, divwe, 1);
1170
1171 #if defined(TARGET_PPC64)
1172 static inline void gen_op_arith_divd(DisasContext *ctx, TCGv ret, TCGv arg1,
1173                                      TCGv arg2, int sign, int compute_ov)
1174 {
1175     TCGv_i64 t0 = tcg_temp_new_i64();
1176     TCGv_i64 t1 = tcg_temp_new_i64();
1177     TCGv_i64 t2 = tcg_temp_new_i64();
1178     TCGv_i64 t3 = tcg_temp_new_i64();
1179
1180     tcg_gen_mov_i64(t0, arg1);
1181     tcg_gen_mov_i64(t1, arg2);
1182     if (sign) {
1183         tcg_gen_setcondi_i64(TCG_COND_EQ, t2, t0, INT64_MIN);
1184         tcg_gen_setcondi_i64(TCG_COND_EQ, t3, t1, -1);
1185         tcg_gen_and_i64(t2, t2, t3);
1186         tcg_gen_setcondi_i64(TCG_COND_EQ, t3, t1, 0);
1187         tcg_gen_or_i64(t2, t2, t3);
1188         tcg_gen_movi_i64(t3, 0);
1189         tcg_gen_movcond_i64(TCG_COND_NE, t1, t2, t3, t2, t1);
1190         tcg_gen_div_i64(ret, t0, t1);
1191     } else {
1192         tcg_gen_setcondi_i64(TCG_COND_EQ, t2, t1, 0);
1193         tcg_gen_movi_i64(t3, 0);
1194         tcg_gen_movcond_i64(TCG_COND_NE, t1, t2, t3, t2, t1);
1195         tcg_gen_divu_i64(ret, t0, t1);
1196     }
1197     if (compute_ov) {
1198         tcg_gen_mov_tl(cpu_ov, t2);
1199         tcg_gen_or_tl(cpu_so, cpu_so, cpu_ov);
1200     }
1201     tcg_temp_free_i64(t0);
1202     tcg_temp_free_i64(t1);
1203     tcg_temp_free_i64(t2);
1204     tcg_temp_free_i64(t3);
1205
1206     if (unlikely(Rc(ctx->opcode) != 0))
1207         gen_set_Rc0(ctx, ret);
1208 }
1209
1210 #define GEN_INT_ARITH_DIVD(name, opc3, sign, compute_ov)                      \
1211 static void glue(gen_, name)(DisasContext *ctx)                                       \
1212 {                                                                             \
1213     gen_op_arith_divd(ctx, cpu_gpr[rD(ctx->opcode)],                          \
1214                       cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],     \
1215                       sign, compute_ov);                                      \
1216 }
1217 /* divwu  divwu.  divwuo  divwuo.   */
1218 GEN_INT_ARITH_DIVD(divdu, 0x0E, 0, 0);
1219 GEN_INT_ARITH_DIVD(divduo, 0x1E, 0, 1);
1220 /* divw  divw.  divwo  divwo.   */
1221 GEN_INT_ARITH_DIVD(divd, 0x0F, 1, 0);
1222 GEN_INT_ARITH_DIVD(divdo, 0x1F, 1, 1);
1223
1224 GEN_DIVE(divdeu, divdeu, 0);
1225 GEN_DIVE(divdeuo, divdeu, 1);
1226 GEN_DIVE(divde, divde, 0);
1227 GEN_DIVE(divdeo, divde, 1);
1228 #endif
1229
1230 static inline void gen_op_arith_modw(DisasContext *ctx, TCGv ret, TCGv arg1,
1231                                      TCGv arg2, int sign)
1232 {
1233     TCGv_i32 t0 = tcg_temp_new_i32();
1234     TCGv_i32 t1 = tcg_temp_new_i32();
1235
1236     tcg_gen_trunc_tl_i32(t0, arg1);
1237     tcg_gen_trunc_tl_i32(t1, arg2);
1238     if (sign) {
1239         TCGv_i32 t2 = tcg_temp_new_i32();
1240         TCGv_i32 t3 = tcg_temp_new_i32();
1241         tcg_gen_setcondi_i32(TCG_COND_EQ, t2, t0, INT_MIN);
1242         tcg_gen_setcondi_i32(TCG_COND_EQ, t3, t1, -1);
1243         tcg_gen_and_i32(t2, t2, t3);
1244         tcg_gen_setcondi_i32(TCG_COND_EQ, t3, t1, 0);
1245         tcg_gen_or_i32(t2, t2, t3);
1246         tcg_gen_movi_i32(t3, 0);
1247         tcg_gen_movcond_i32(TCG_COND_NE, t1, t2, t3, t2, t1);
1248         tcg_gen_rem_i32(t3, t0, t1);
1249         tcg_gen_ext_i32_tl(ret, t3);
1250         tcg_temp_free_i32(t2);
1251         tcg_temp_free_i32(t3);
1252     } else {
1253         TCGv_i32 t2 = tcg_const_i32(1);
1254         TCGv_i32 t3 = tcg_const_i32(0);
1255         tcg_gen_movcond_i32(TCG_COND_EQ, t1, t1, t3, t2, t1);
1256         tcg_gen_remu_i32(t3, t0, t1);
1257         tcg_gen_extu_i32_tl(ret, t3);
1258         tcg_temp_free_i32(t2);
1259         tcg_temp_free_i32(t3);
1260     }
1261     tcg_temp_free_i32(t0);
1262     tcg_temp_free_i32(t1);
1263 }
1264
1265 #define GEN_INT_ARITH_MODW(name, opc3, sign)                                \
1266 static void glue(gen_, name)(DisasContext *ctx)                             \
1267 {                                                                           \
1268     gen_op_arith_modw(ctx, cpu_gpr[rD(ctx->opcode)],                        \
1269                       cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],   \
1270                       sign);                                                \
1271 }
1272
1273 GEN_INT_ARITH_MODW(moduw, 0x08, 0);
1274 GEN_INT_ARITH_MODW(modsw, 0x18, 1);
1275
1276 #if defined(TARGET_PPC64)
1277 static inline void gen_op_arith_modd(DisasContext *ctx, TCGv ret, TCGv arg1,
1278                                      TCGv arg2, int sign)
1279 {
1280     TCGv_i64 t0 = tcg_temp_new_i64();
1281     TCGv_i64 t1 = tcg_temp_new_i64();
1282
1283     tcg_gen_mov_i64(t0, arg1);
1284     tcg_gen_mov_i64(t1, arg2);
1285     if (sign) {
1286         TCGv_i64 t2 = tcg_temp_new_i64();
1287         TCGv_i64 t3 = tcg_temp_new_i64();
1288         tcg_gen_setcondi_i64(TCG_COND_EQ, t2, t0, INT64_MIN);
1289         tcg_gen_setcondi_i64(TCG_COND_EQ, t3, t1, -1);
1290         tcg_gen_and_i64(t2, t2, t3);
1291         tcg_gen_setcondi_i64(TCG_COND_EQ, t3, t1, 0);
1292         tcg_gen_or_i64(t2, t2, t3);
1293         tcg_gen_movi_i64(t3, 0);
1294         tcg_gen_movcond_i64(TCG_COND_NE, t1, t2, t3, t2, t1);
1295         tcg_gen_rem_i64(ret, t0, t1);
1296         tcg_temp_free_i64(t2);
1297         tcg_temp_free_i64(t3);
1298     } else {
1299         TCGv_i64 t2 = tcg_const_i64(1);
1300         TCGv_i64 t3 = tcg_const_i64(0);
1301         tcg_gen_movcond_i64(TCG_COND_EQ, t1, t1, t3, t2, t1);
1302         tcg_gen_remu_i64(ret, t0, t1);
1303         tcg_temp_free_i64(t2);
1304         tcg_temp_free_i64(t3);
1305     }
1306     tcg_temp_free_i64(t0);
1307     tcg_temp_free_i64(t1);
1308 }
1309
1310 #define GEN_INT_ARITH_MODD(name, opc3, sign)                            \
1311 static void glue(gen_, name)(DisasContext *ctx)                           \
1312 {                                                                         \
1313   gen_op_arith_modd(ctx, cpu_gpr[rD(ctx->opcode)],                        \
1314                     cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],   \
1315                     sign);                                                \
1316 }
1317
1318 GEN_INT_ARITH_MODD(modud, 0x08, 0);
1319 GEN_INT_ARITH_MODD(modsd, 0x18, 1);
1320 #endif
1321
1322 /* mulhw  mulhw. */
1323 static void gen_mulhw(DisasContext *ctx)
1324 {
1325     TCGv_i32 t0 = tcg_temp_new_i32();
1326     TCGv_i32 t1 = tcg_temp_new_i32();
1327
1328     tcg_gen_trunc_tl_i32(t0, cpu_gpr[rA(ctx->opcode)]);
1329     tcg_gen_trunc_tl_i32(t1, cpu_gpr[rB(ctx->opcode)]);
1330     tcg_gen_muls2_i32(t0, t1, t0, t1);
1331     tcg_gen_extu_i32_tl(cpu_gpr[rD(ctx->opcode)], t1);
1332     tcg_temp_free_i32(t0);
1333     tcg_temp_free_i32(t1);
1334     if (unlikely(Rc(ctx->opcode) != 0))
1335         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
1336 }
1337
1338 /* mulhwu  mulhwu.  */
1339 static void gen_mulhwu(DisasContext *ctx)
1340 {
1341     TCGv_i32 t0 = tcg_temp_new_i32();
1342     TCGv_i32 t1 = tcg_temp_new_i32();
1343
1344     tcg_gen_trunc_tl_i32(t0, cpu_gpr[rA(ctx->opcode)]);
1345     tcg_gen_trunc_tl_i32(t1, cpu_gpr[rB(ctx->opcode)]);
1346     tcg_gen_mulu2_i32(t0, t1, t0, t1);
1347     tcg_gen_extu_i32_tl(cpu_gpr[rD(ctx->opcode)], t1);
1348     tcg_temp_free_i32(t0);
1349     tcg_temp_free_i32(t1);
1350     if (unlikely(Rc(ctx->opcode) != 0))
1351         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
1352 }
1353
1354 /* mullw  mullw. */
1355 static void gen_mullw(DisasContext *ctx)
1356 {
1357 #if defined(TARGET_PPC64)
1358     TCGv_i64 t0, t1;
1359     t0 = tcg_temp_new_i64();
1360     t1 = tcg_temp_new_i64();
1361     tcg_gen_ext32s_tl(t0, cpu_gpr[rA(ctx->opcode)]);
1362     tcg_gen_ext32s_tl(t1, cpu_gpr[rB(ctx->opcode)]);
1363     tcg_gen_mul_i64(cpu_gpr[rD(ctx->opcode)], t0, t1);
1364     tcg_temp_free(t0);
1365     tcg_temp_free(t1);
1366 #else
1367     tcg_gen_mul_i32(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)],
1368                     cpu_gpr[rB(ctx->opcode)]);
1369 #endif
1370     if (unlikely(Rc(ctx->opcode) != 0))
1371         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
1372 }
1373
1374 /* mullwo  mullwo. */
1375 static void gen_mullwo(DisasContext *ctx)
1376 {
1377     TCGv_i32 t0 = tcg_temp_new_i32();
1378     TCGv_i32 t1 = tcg_temp_new_i32();
1379
1380     tcg_gen_trunc_tl_i32(t0, cpu_gpr[rA(ctx->opcode)]);
1381     tcg_gen_trunc_tl_i32(t1, cpu_gpr[rB(ctx->opcode)]);
1382     tcg_gen_muls2_i32(t0, t1, t0, t1);
1383 #if defined(TARGET_PPC64)
1384     tcg_gen_concat_i32_i64(cpu_gpr[rD(ctx->opcode)], t0, t1);
1385 #else
1386     tcg_gen_mov_i32(cpu_gpr[rD(ctx->opcode)], t0);
1387 #endif
1388
1389     tcg_gen_sari_i32(t0, t0, 31);
1390     tcg_gen_setcond_i32(TCG_COND_NE, t0, t0, t1);
1391     tcg_gen_extu_i32_tl(cpu_ov, t0);
1392     tcg_gen_or_tl(cpu_so, cpu_so, cpu_ov);
1393
1394     tcg_temp_free_i32(t0);
1395     tcg_temp_free_i32(t1);
1396     if (unlikely(Rc(ctx->opcode) != 0))
1397         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
1398 }
1399
1400 /* mulli */
1401 static void gen_mulli(DisasContext *ctx)
1402 {
1403     tcg_gen_muli_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)],
1404                     SIMM(ctx->opcode));
1405 }
1406
1407 #if defined(TARGET_PPC64)
1408 /* mulhd  mulhd. */
1409 static void gen_mulhd(DisasContext *ctx)
1410 {
1411     TCGv lo = tcg_temp_new();
1412     tcg_gen_muls2_tl(lo, cpu_gpr[rD(ctx->opcode)],
1413                      cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
1414     tcg_temp_free(lo);
1415     if (unlikely(Rc(ctx->opcode) != 0)) {
1416         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
1417     }
1418 }
1419
1420 /* mulhdu  mulhdu. */
1421 static void gen_mulhdu(DisasContext *ctx)
1422 {
1423     TCGv lo = tcg_temp_new();
1424     tcg_gen_mulu2_tl(lo, cpu_gpr[rD(ctx->opcode)],
1425                      cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
1426     tcg_temp_free(lo);
1427     if (unlikely(Rc(ctx->opcode) != 0)) {
1428         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
1429     }
1430 }
1431
1432 /* mulld  mulld. */
1433 static void gen_mulld(DisasContext *ctx)
1434 {
1435     tcg_gen_mul_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)],
1436                    cpu_gpr[rB(ctx->opcode)]);
1437     if (unlikely(Rc(ctx->opcode) != 0))
1438         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
1439 }
1440
1441 /* mulldo  mulldo. */
1442 static void gen_mulldo(DisasContext *ctx)
1443 {
1444     TCGv_i64 t0 = tcg_temp_new_i64();
1445     TCGv_i64 t1 = tcg_temp_new_i64();
1446
1447     tcg_gen_muls2_i64(t0, t1, cpu_gpr[rA(ctx->opcode)],
1448                       cpu_gpr[rB(ctx->opcode)]);
1449     tcg_gen_mov_i64(cpu_gpr[rD(ctx->opcode)], t0);
1450
1451     tcg_gen_sari_i64(t0, t0, 63);
1452     tcg_gen_setcond_i64(TCG_COND_NE, cpu_ov, t0, t1);
1453     tcg_gen_or_tl(cpu_so, cpu_so, cpu_ov);
1454
1455     tcg_temp_free_i64(t0);
1456     tcg_temp_free_i64(t1);
1457
1458     if (unlikely(Rc(ctx->opcode) != 0)) {
1459         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
1460     }
1461 }
1462 #endif
1463
1464 /* Common subf function */
1465 static inline void gen_op_arith_subf(DisasContext *ctx, TCGv ret, TCGv arg1,
1466                                      TCGv arg2, bool add_ca, bool compute_ca,
1467                                      bool compute_ov, bool compute_rc0)
1468 {
1469     TCGv t0 = ret;
1470
1471     if (compute_ca || compute_ov) {
1472         t0 = tcg_temp_new();
1473     }
1474
1475     if (compute_ca) {
1476         /* dest = ~arg1 + arg2 [+ ca].  */
1477         if (NARROW_MODE(ctx)) {
1478             /* Caution: a non-obvious corner case of the spec is that we
1479                must produce the *entire* 64-bit addition, but produce the
1480                carry into bit 32.  */
1481             TCGv inv1 = tcg_temp_new();
1482             TCGv t1 = tcg_temp_new();
1483             tcg_gen_not_tl(inv1, arg1);
1484             if (add_ca) {
1485                 tcg_gen_add_tl(t0, arg2, cpu_ca);
1486             } else {
1487                 tcg_gen_addi_tl(t0, arg2, 1);
1488             }
1489             tcg_gen_xor_tl(t1, arg2, inv1);         /* add without carry */
1490             tcg_gen_add_tl(t0, t0, inv1);
1491             tcg_temp_free(inv1);
1492             tcg_gen_xor_tl(cpu_ca, t0, t1);         /* bits changes w/ carry */
1493             tcg_temp_free(t1);
1494             tcg_gen_shri_tl(cpu_ca, cpu_ca, 32);    /* extract bit 32 */
1495             tcg_gen_andi_tl(cpu_ca, cpu_ca, 1);
1496         } else if (add_ca) {
1497             TCGv zero, inv1 = tcg_temp_new();
1498             tcg_gen_not_tl(inv1, arg1);
1499             zero = tcg_const_tl(0);
1500             tcg_gen_add2_tl(t0, cpu_ca, arg2, zero, cpu_ca, zero);
1501             tcg_gen_add2_tl(t0, cpu_ca, t0, cpu_ca, inv1, zero);
1502             tcg_temp_free(zero);
1503             tcg_temp_free(inv1);
1504         } else {
1505             tcg_gen_setcond_tl(TCG_COND_GEU, cpu_ca, arg2, arg1);
1506             tcg_gen_sub_tl(t0, arg2, arg1);
1507         }
1508     } else if (add_ca) {
1509         /* Since we're ignoring carry-out, we can simplify the
1510            standard ~arg1 + arg2 + ca to arg2 - arg1 + ca - 1.  */
1511         tcg_gen_sub_tl(t0, arg2, arg1);
1512         tcg_gen_add_tl(t0, t0, cpu_ca);
1513         tcg_gen_subi_tl(t0, t0, 1);
1514     } else {
1515         tcg_gen_sub_tl(t0, arg2, arg1);
1516     }
1517
1518     if (compute_ov) {
1519         gen_op_arith_compute_ov(ctx, t0, arg1, arg2, 1);
1520     }
1521     if (unlikely(compute_rc0)) {
1522         gen_set_Rc0(ctx, t0);
1523     }
1524
1525     if (!TCGV_EQUAL(t0, ret)) {
1526         tcg_gen_mov_tl(ret, t0);
1527         tcg_temp_free(t0);
1528     }
1529 }
1530 /* Sub functions with Two operands functions */
1531 #define GEN_INT_ARITH_SUBF(name, opc3, add_ca, compute_ca, compute_ov)        \
1532 static void glue(gen_, name)(DisasContext *ctx)                               \
1533 {                                                                             \
1534     gen_op_arith_subf(ctx, cpu_gpr[rD(ctx->opcode)],                          \
1535                       cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],     \
1536                       add_ca, compute_ca, compute_ov, Rc(ctx->opcode));       \
1537 }
1538 /* Sub functions with one operand and one immediate */
1539 #define GEN_INT_ARITH_SUBF_CONST(name, opc3, const_val,                       \
1540                                 add_ca, compute_ca, compute_ov)               \
1541 static void glue(gen_, name)(DisasContext *ctx)                               \
1542 {                                                                             \
1543     TCGv t0 = tcg_const_tl(const_val);                                        \
1544     gen_op_arith_subf(ctx, cpu_gpr[rD(ctx->opcode)],                          \
1545                       cpu_gpr[rA(ctx->opcode)], t0,                           \
1546                       add_ca, compute_ca, compute_ov, Rc(ctx->opcode));       \
1547     tcg_temp_free(t0);                                                        \
1548 }
1549 /* subf  subf.  subfo  subfo. */
1550 GEN_INT_ARITH_SUBF(subf, 0x01, 0, 0, 0)
1551 GEN_INT_ARITH_SUBF(subfo, 0x11, 0, 0, 1)
1552 /* subfc  subfc.  subfco  subfco. */
1553 GEN_INT_ARITH_SUBF(subfc, 0x00, 0, 1, 0)
1554 GEN_INT_ARITH_SUBF(subfco, 0x10, 0, 1, 1)
1555 /* subfe  subfe.  subfeo  subfo. */
1556 GEN_INT_ARITH_SUBF(subfe, 0x04, 1, 1, 0)
1557 GEN_INT_ARITH_SUBF(subfeo, 0x14, 1, 1, 1)
1558 /* subfme  subfme.  subfmeo  subfmeo.  */
1559 GEN_INT_ARITH_SUBF_CONST(subfme, 0x07, -1LL, 1, 1, 0)
1560 GEN_INT_ARITH_SUBF_CONST(subfmeo, 0x17, -1LL, 1, 1, 1)
1561 /* subfze  subfze.  subfzeo  subfzeo.*/
1562 GEN_INT_ARITH_SUBF_CONST(subfze, 0x06, 0, 1, 1, 0)
1563 GEN_INT_ARITH_SUBF_CONST(subfzeo, 0x16, 0, 1, 1, 1)
1564
1565 /* subfic */
1566 static void gen_subfic(DisasContext *ctx)
1567 {
1568     TCGv c = tcg_const_tl(SIMM(ctx->opcode));
1569     gen_op_arith_subf(ctx, cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)],
1570                       c, 0, 1, 0, 0);
1571     tcg_temp_free(c);
1572 }
1573
1574 /* neg neg. nego nego. */
1575 static inline void gen_op_arith_neg(DisasContext *ctx, bool compute_ov)
1576 {
1577     TCGv zero = tcg_const_tl(0);
1578     gen_op_arith_subf(ctx, cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)],
1579                       zero, 0, 0, compute_ov, Rc(ctx->opcode));
1580     tcg_temp_free(zero);
1581 }
1582
1583 static void gen_neg(DisasContext *ctx)
1584 {
1585     gen_op_arith_neg(ctx, 0);
1586 }
1587
1588 static void gen_nego(DisasContext *ctx)
1589 {
1590     gen_op_arith_neg(ctx, 1);
1591 }
1592
1593 /***                            Integer logical                            ***/
1594 #define GEN_LOGICAL2(name, tcg_op, opc, type)                                 \
1595 static void glue(gen_, name)(DisasContext *ctx)                                       \
1596 {                                                                             \
1597     tcg_op(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)],                \
1598        cpu_gpr[rB(ctx->opcode)]);                                             \
1599     if (unlikely(Rc(ctx->opcode) != 0))                                       \
1600         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);                           \
1601 }
1602
1603 #define GEN_LOGICAL1(name, tcg_op, opc, type)                                 \
1604 static void glue(gen_, name)(DisasContext *ctx)                                       \
1605 {                                                                             \
1606     tcg_op(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)]);               \
1607     if (unlikely(Rc(ctx->opcode) != 0))                                       \
1608         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);                           \
1609 }
1610
1611 /* and & and. */
1612 GEN_LOGICAL2(and, tcg_gen_and_tl, 0x00, PPC_INTEGER);
1613 /* andc & andc. */
1614 GEN_LOGICAL2(andc, tcg_gen_andc_tl, 0x01, PPC_INTEGER);
1615
1616 /* andi. */
1617 static void gen_andi_(DisasContext *ctx)
1618 {
1619     tcg_gen_andi_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)], UIMM(ctx->opcode));
1620     gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
1621 }
1622
1623 /* andis. */
1624 static void gen_andis_(DisasContext *ctx)
1625 {
1626     tcg_gen_andi_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)], UIMM(ctx->opcode) << 16);
1627     gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
1628 }
1629
1630 /* cntlzw */
1631 static void gen_cntlzw(DisasContext *ctx)
1632 {
1633     gen_helper_cntlzw(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)]);
1634     if (unlikely(Rc(ctx->opcode) != 0))
1635         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
1636 }
1637
1638 /* cnttzw */
1639 static void gen_cnttzw(DisasContext *ctx)
1640 {
1641     gen_helper_cnttzw(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)]);
1642     if (unlikely(Rc(ctx->opcode) != 0)) {
1643         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
1644     }
1645 }
1646
1647 /* eqv & eqv. */
1648 GEN_LOGICAL2(eqv, tcg_gen_eqv_tl, 0x08, PPC_INTEGER);
1649 /* extsb & extsb. */
1650 GEN_LOGICAL1(extsb, tcg_gen_ext8s_tl, 0x1D, PPC_INTEGER);
1651 /* extsh & extsh. */
1652 GEN_LOGICAL1(extsh, tcg_gen_ext16s_tl, 0x1C, PPC_INTEGER);
1653 /* nand & nand. */
1654 GEN_LOGICAL2(nand, tcg_gen_nand_tl, 0x0E, PPC_INTEGER);
1655 /* nor & nor. */
1656 GEN_LOGICAL2(nor, tcg_gen_nor_tl, 0x03, PPC_INTEGER);
1657
1658 #if defined(TARGET_PPC64) && !defined(CONFIG_USER_ONLY)
1659 static void gen_pause(DisasContext *ctx)
1660 {
1661     TCGv_i32 t0 = tcg_const_i32(0);
1662     tcg_gen_st_i32(t0, cpu_env,
1663                    -offsetof(PowerPCCPU, env) + offsetof(CPUState, halted));
1664     tcg_temp_free_i32(t0);
1665
1666     /* Stop translation, this gives other CPUs a chance to run */
1667     gen_exception_nip(ctx, EXCP_HLT, ctx->nip);
1668 }
1669 #endif /* defined(TARGET_PPC64) */
1670
1671 /* or & or. */
1672 static void gen_or(DisasContext *ctx)
1673 {
1674     int rs, ra, rb;
1675
1676     rs = rS(ctx->opcode);
1677     ra = rA(ctx->opcode);
1678     rb = rB(ctx->opcode);
1679     /* Optimisation for mr. ri case */
1680     if (rs != ra || rs != rb) {
1681         if (rs != rb)
1682             tcg_gen_or_tl(cpu_gpr[ra], cpu_gpr[rs], cpu_gpr[rb]);
1683         else
1684             tcg_gen_mov_tl(cpu_gpr[ra], cpu_gpr[rs]);
1685         if (unlikely(Rc(ctx->opcode) != 0))
1686             gen_set_Rc0(ctx, cpu_gpr[ra]);
1687     } else if (unlikely(Rc(ctx->opcode) != 0)) {
1688         gen_set_Rc0(ctx, cpu_gpr[rs]);
1689 #if defined(TARGET_PPC64)
1690     } else if (rs != 0) { /* 0 is nop */
1691         int prio = 0;
1692
1693         switch (rs) {
1694         case 1:
1695             /* Set process priority to low */
1696             prio = 2;
1697             break;
1698         case 6:
1699             /* Set process priority to medium-low */
1700             prio = 3;
1701             break;
1702         case 2:
1703             /* Set process priority to normal */
1704             prio = 4;
1705             break;
1706 #if !defined(CONFIG_USER_ONLY)
1707         case 31:
1708             if (!ctx->pr) {
1709                 /* Set process priority to very low */
1710                 prio = 1;
1711             }
1712             break;
1713         case 5:
1714             if (!ctx->pr) {
1715                 /* Set process priority to medium-hight */
1716                 prio = 5;
1717             }
1718             break;
1719         case 3:
1720             if (!ctx->pr) {
1721                 /* Set process priority to high */
1722                 prio = 6;
1723             }
1724             break;
1725         case 7:
1726             if (ctx->hv && !ctx->pr) {
1727                 /* Set process priority to very high */
1728                 prio = 7;
1729             }
1730             break;
1731 #endif
1732         default:
1733             break;
1734         }
1735         if (prio) {
1736             TCGv t0 = tcg_temp_new();
1737             gen_load_spr(t0, SPR_PPR);
1738             tcg_gen_andi_tl(t0, t0, ~0x001C000000000000ULL);
1739             tcg_gen_ori_tl(t0, t0, ((uint64_t)prio) << 50);
1740             gen_store_spr(SPR_PPR, t0);
1741             tcg_temp_free(t0);
1742         }
1743 #if !defined(CONFIG_USER_ONLY)
1744         /* Pause out of TCG otherwise spin loops with smt_low eat too much
1745          * CPU and the kernel hangs.  This applies to all encodings other
1746          * than no-op, e.g., miso(rs=26), yield(27), mdoio(29), mdoom(30),
1747          * and all currently undefined.
1748          */
1749         gen_pause(ctx);
1750 #endif
1751 #endif
1752     }
1753 }
1754 /* orc & orc. */
1755 GEN_LOGICAL2(orc, tcg_gen_orc_tl, 0x0C, PPC_INTEGER);
1756
1757 /* xor & xor. */
1758 static void gen_xor(DisasContext *ctx)
1759 {
1760     /* Optimisation for "set to zero" case */
1761     if (rS(ctx->opcode) != rB(ctx->opcode))
1762         tcg_gen_xor_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
1763     else
1764         tcg_gen_movi_tl(cpu_gpr[rA(ctx->opcode)], 0);
1765     if (unlikely(Rc(ctx->opcode) != 0))
1766         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
1767 }
1768
1769 /* ori */
1770 static void gen_ori(DisasContext *ctx)
1771 {
1772     target_ulong uimm = UIMM(ctx->opcode);
1773
1774     if (rS(ctx->opcode) == rA(ctx->opcode) && uimm == 0) {
1775         return;
1776     }
1777     tcg_gen_ori_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)], uimm);
1778 }
1779
1780 /* oris */
1781 static void gen_oris(DisasContext *ctx)
1782 {
1783     target_ulong uimm = UIMM(ctx->opcode);
1784
1785     if (rS(ctx->opcode) == rA(ctx->opcode) && uimm == 0) {
1786         /* NOP */
1787         return;
1788     }
1789     tcg_gen_ori_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)], uimm << 16);
1790 }
1791
1792 /* xori */
1793 static void gen_xori(DisasContext *ctx)
1794 {
1795     target_ulong uimm = UIMM(ctx->opcode);
1796
1797     if (rS(ctx->opcode) == rA(ctx->opcode) && uimm == 0) {
1798         /* NOP */
1799         return;
1800     }
1801     tcg_gen_xori_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)], uimm);
1802 }
1803
1804 /* xoris */
1805 static void gen_xoris(DisasContext *ctx)
1806 {
1807     target_ulong uimm = UIMM(ctx->opcode);
1808
1809     if (rS(ctx->opcode) == rA(ctx->opcode) && uimm == 0) {
1810         /* NOP */
1811         return;
1812     }
1813     tcg_gen_xori_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)], uimm << 16);
1814 }
1815
1816 /* popcntb : PowerPC 2.03 specification */
1817 static void gen_popcntb(DisasContext *ctx)
1818 {
1819     gen_helper_popcntb(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)]);
1820 }
1821
1822 static void gen_popcntw(DisasContext *ctx)
1823 {
1824     gen_helper_popcntw(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)]);
1825 }
1826
1827 #if defined(TARGET_PPC64)
1828 /* popcntd: PowerPC 2.06 specification */
1829 static void gen_popcntd(DisasContext *ctx)
1830 {
1831     gen_helper_popcntd(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)]);
1832 }
1833 #endif
1834
1835 /* prtyw: PowerPC 2.05 specification */
1836 static void gen_prtyw(DisasContext *ctx)
1837 {
1838     TCGv ra = cpu_gpr[rA(ctx->opcode)];
1839     TCGv rs = cpu_gpr[rS(ctx->opcode)];
1840     TCGv t0 = tcg_temp_new();
1841     tcg_gen_shri_tl(t0, rs, 16);
1842     tcg_gen_xor_tl(ra, rs, t0);
1843     tcg_gen_shri_tl(t0, ra, 8);
1844     tcg_gen_xor_tl(ra, ra, t0);
1845     tcg_gen_andi_tl(ra, ra, (target_ulong)0x100000001ULL);
1846     tcg_temp_free(t0);
1847 }
1848
1849 #if defined(TARGET_PPC64)
1850 /* prtyd: PowerPC 2.05 specification */
1851 static void gen_prtyd(DisasContext *ctx)
1852 {
1853     TCGv ra = cpu_gpr[rA(ctx->opcode)];
1854     TCGv rs = cpu_gpr[rS(ctx->opcode)];
1855     TCGv t0 = tcg_temp_new();
1856     tcg_gen_shri_tl(t0, rs, 32);
1857     tcg_gen_xor_tl(ra, rs, t0);
1858     tcg_gen_shri_tl(t0, ra, 16);
1859     tcg_gen_xor_tl(ra, ra, t0);
1860     tcg_gen_shri_tl(t0, ra, 8);
1861     tcg_gen_xor_tl(ra, ra, t0);
1862     tcg_gen_andi_tl(ra, ra, 1);
1863     tcg_temp_free(t0);
1864 }
1865 #endif
1866
1867 #if defined(TARGET_PPC64)
1868 /* bpermd */
1869 static void gen_bpermd(DisasContext *ctx)
1870 {
1871     gen_helper_bpermd(cpu_gpr[rA(ctx->opcode)],
1872                       cpu_gpr[rS(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
1873 }
1874 #endif
1875
1876 #if defined(TARGET_PPC64)
1877 /* extsw & extsw. */
1878 GEN_LOGICAL1(extsw, tcg_gen_ext32s_tl, 0x1E, PPC_64B);
1879
1880 /* cntlzd */
1881 static void gen_cntlzd(DisasContext *ctx)
1882 {
1883     gen_helper_cntlzd(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)]);
1884     if (unlikely(Rc(ctx->opcode) != 0))
1885         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
1886 }
1887
1888 /* cnttzd */
1889 static void gen_cnttzd(DisasContext *ctx)
1890 {
1891     gen_helper_cnttzd(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)]);
1892     if (unlikely(Rc(ctx->opcode) != 0)) {
1893         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
1894     }
1895 }
1896 #endif
1897
1898 /***                             Integer rotate                            ***/
1899
1900 /* rlwimi & rlwimi. */
1901 static void gen_rlwimi(DisasContext *ctx)
1902 {
1903     TCGv t_ra = cpu_gpr[rA(ctx->opcode)];
1904     TCGv t_rs = cpu_gpr[rS(ctx->opcode)];
1905     uint32_t sh = SH(ctx->opcode);
1906     uint32_t mb = MB(ctx->opcode);
1907     uint32_t me = ME(ctx->opcode);
1908
1909     if (sh == (31-me) && mb <= me) {
1910         tcg_gen_deposit_tl(t_ra, t_ra, t_rs, sh, me - mb + 1);
1911     } else {
1912         target_ulong mask;
1913         TCGv t1;
1914
1915 #if defined(TARGET_PPC64)
1916         mb += 32;
1917         me += 32;
1918 #endif
1919         mask = MASK(mb, me);
1920
1921         t1 = tcg_temp_new();
1922         if (mask <= 0xffffffffu) {
1923             TCGv_i32 t0 = tcg_temp_new_i32();
1924             tcg_gen_trunc_tl_i32(t0, t_rs);
1925             tcg_gen_rotli_i32(t0, t0, sh);
1926             tcg_gen_extu_i32_tl(t1, t0);
1927             tcg_temp_free_i32(t0);
1928         } else {
1929 #if defined(TARGET_PPC64)
1930             tcg_gen_deposit_i64(t1, t_rs, t_rs, 32, 32);
1931             tcg_gen_rotli_i64(t1, t1, sh);
1932 #else
1933             g_assert_not_reached();
1934 #endif
1935         }
1936
1937         tcg_gen_andi_tl(t1, t1, mask);
1938         tcg_gen_andi_tl(t_ra, t_ra, ~mask);
1939         tcg_gen_or_tl(t_ra, t_ra, t1);
1940         tcg_temp_free(t1);
1941     }
1942     if (unlikely(Rc(ctx->opcode) != 0)) {
1943         gen_set_Rc0(ctx, t_ra);
1944     }
1945 }
1946
1947 /* rlwinm & rlwinm. */
1948 static void gen_rlwinm(DisasContext *ctx)
1949 {
1950     TCGv t_ra = cpu_gpr[rA(ctx->opcode)];
1951     TCGv t_rs = cpu_gpr[rS(ctx->opcode)];
1952     uint32_t sh = SH(ctx->opcode);
1953     uint32_t mb = MB(ctx->opcode);
1954     uint32_t me = ME(ctx->opcode);
1955
1956     if (mb == 0 && me == (31 - sh)) {
1957         tcg_gen_shli_tl(t_ra, t_rs, sh);
1958         tcg_gen_ext32u_tl(t_ra, t_ra);
1959     } else if (sh != 0 && me == 31 && sh == (32 - mb)) {
1960         tcg_gen_ext32u_tl(t_ra, t_rs);
1961         tcg_gen_shri_tl(t_ra, t_ra, mb);
1962     } else {
1963         target_ulong mask;
1964 #if defined(TARGET_PPC64)
1965         mb += 32;
1966         me += 32;
1967 #endif
1968         mask = MASK(mb, me);
1969
1970         if (mask <= 0xffffffffu) {
1971             TCGv_i32 t0 = tcg_temp_new_i32();
1972             tcg_gen_trunc_tl_i32(t0, t_rs);
1973             tcg_gen_rotli_i32(t0, t0, sh);
1974             tcg_gen_andi_i32(t0, t0, mask);
1975             tcg_gen_extu_i32_tl(t_ra, t0);
1976             tcg_temp_free_i32(t0);
1977         } else {
1978 #if defined(TARGET_PPC64)
1979             tcg_gen_deposit_i64(t_ra, t_rs, t_rs, 32, 32);
1980             tcg_gen_rotli_i64(t_ra, t_ra, sh);
1981             tcg_gen_andi_i64(t_ra, t_ra, mask);
1982 #else
1983             g_assert_not_reached();
1984 #endif
1985         }
1986     }
1987     if (unlikely(Rc(ctx->opcode) != 0)) {
1988         gen_set_Rc0(ctx, t_ra);
1989     }
1990 }
1991
1992 /* rlwnm & rlwnm. */
1993 static void gen_rlwnm(DisasContext *ctx)
1994 {
1995     TCGv t_ra = cpu_gpr[rA(ctx->opcode)];
1996     TCGv t_rs = cpu_gpr[rS(ctx->opcode)];
1997     TCGv t_rb = cpu_gpr[rB(ctx->opcode)];
1998     uint32_t mb = MB(ctx->opcode);
1999     uint32_t me = ME(ctx->opcode);
2000     target_ulong mask;
2001
2002 #if defined(TARGET_PPC64)
2003     mb += 32;
2004     me += 32;
2005 #endif
2006     mask = MASK(mb, me);
2007
2008     if (mask <= 0xffffffffu) {
2009         TCGv_i32 t0 = tcg_temp_new_i32();
2010         TCGv_i32 t1 = tcg_temp_new_i32();
2011         tcg_gen_trunc_tl_i32(t0, t_rb);
2012         tcg_gen_trunc_tl_i32(t1, t_rs);
2013         tcg_gen_andi_i32(t0, t0, 0x1f);
2014         tcg_gen_rotl_i32(t1, t1, t0);
2015         tcg_gen_extu_i32_tl(t_ra, t1);
2016         tcg_temp_free_i32(t0);
2017         tcg_temp_free_i32(t1);
2018     } else {
2019 #if defined(TARGET_PPC64)
2020         TCGv_i64 t0 = tcg_temp_new_i64();
2021         tcg_gen_andi_i64(t0, t_rb, 0x1f);
2022         tcg_gen_deposit_i64(t_ra, t_rs, t_rs, 32, 32);
2023         tcg_gen_rotl_i64(t_ra, t_ra, t0);
2024         tcg_temp_free_i64(t0);
2025 #else
2026         g_assert_not_reached();
2027 #endif
2028     }
2029
2030     tcg_gen_andi_tl(t_ra, t_ra, mask);
2031
2032     if (unlikely(Rc(ctx->opcode) != 0)) {
2033         gen_set_Rc0(ctx, t_ra);
2034     }
2035 }
2036
2037 #if defined(TARGET_PPC64)
2038 #define GEN_PPC64_R2(name, opc1, opc2)                                        \
2039 static void glue(gen_, name##0)(DisasContext *ctx)                            \
2040 {                                                                             \
2041     gen_##name(ctx, 0);                                                       \
2042 }                                                                             \
2043                                                                               \
2044 static void glue(gen_, name##1)(DisasContext *ctx)                            \
2045 {                                                                             \
2046     gen_##name(ctx, 1);                                                       \
2047 }
2048 #define GEN_PPC64_R4(name, opc1, opc2)                                        \
2049 static void glue(gen_, name##0)(DisasContext *ctx)                            \
2050 {                                                                             \
2051     gen_##name(ctx, 0, 0);                                                    \
2052 }                                                                             \
2053                                                                               \
2054 static void glue(gen_, name##1)(DisasContext *ctx)                            \
2055 {                                                                             \
2056     gen_##name(ctx, 0, 1);                                                    \
2057 }                                                                             \
2058                                                                               \
2059 static void glue(gen_, name##2)(DisasContext *ctx)                            \
2060 {                                                                             \
2061     gen_##name(ctx, 1, 0);                                                    \
2062 }                                                                             \
2063                                                                               \
2064 static void glue(gen_, name##3)(DisasContext *ctx)                            \
2065 {                                                                             \
2066     gen_##name(ctx, 1, 1);                                                    \
2067 }
2068
2069 static void gen_rldinm(DisasContext *ctx, int mb, int me, int sh)
2070 {
2071     TCGv t_ra = cpu_gpr[rA(ctx->opcode)];
2072     TCGv t_rs = cpu_gpr[rS(ctx->opcode)];
2073
2074     if (sh != 0 && mb == 0 && me == (63 - sh)) {
2075         tcg_gen_shli_tl(t_ra, t_rs, sh);
2076     } else if (sh != 0 && me == 63 && sh == (64 - mb)) {
2077         tcg_gen_shri_tl(t_ra, t_rs, mb);
2078     } else {
2079         tcg_gen_rotli_tl(t_ra, t_rs, sh);
2080         tcg_gen_andi_tl(t_ra, t_ra, MASK(mb, me));
2081     }
2082     if (unlikely(Rc(ctx->opcode) != 0)) {
2083         gen_set_Rc0(ctx, t_ra);
2084     }
2085 }
2086
2087 /* rldicl - rldicl. */
2088 static inline void gen_rldicl(DisasContext *ctx, int mbn, int shn)
2089 {
2090     uint32_t sh, mb;
2091
2092     sh = SH(ctx->opcode) | (shn << 5);
2093     mb = MB(ctx->opcode) | (mbn << 5);
2094     gen_rldinm(ctx, mb, 63, sh);
2095 }
2096 GEN_PPC64_R4(rldicl, 0x1E, 0x00);
2097
2098 /* rldicr - rldicr. */
2099 static inline void gen_rldicr(DisasContext *ctx, int men, int shn)
2100 {
2101     uint32_t sh, me;
2102
2103     sh = SH(ctx->opcode) | (shn << 5);
2104     me = MB(ctx->opcode) | (men << 5);
2105     gen_rldinm(ctx, 0, me, sh);
2106 }
2107 GEN_PPC64_R4(rldicr, 0x1E, 0x02);
2108
2109 /* rldic - rldic. */
2110 static inline void gen_rldic(DisasContext *ctx, int mbn, int shn)
2111 {
2112     uint32_t sh, mb;
2113
2114     sh = SH(ctx->opcode) | (shn << 5);
2115     mb = MB(ctx->opcode) | (mbn << 5);
2116     gen_rldinm(ctx, mb, 63 - sh, sh);
2117 }
2118 GEN_PPC64_R4(rldic, 0x1E, 0x04);
2119
2120 static void gen_rldnm(DisasContext *ctx, int mb, int me)
2121 {
2122     TCGv t_ra = cpu_gpr[rA(ctx->opcode)];
2123     TCGv t_rs = cpu_gpr[rS(ctx->opcode)];
2124     TCGv t_rb = cpu_gpr[rB(ctx->opcode)];
2125     TCGv t0;
2126
2127     t0 = tcg_temp_new();
2128     tcg_gen_andi_tl(t0, t_rb, 0x3f);
2129     tcg_gen_rotl_tl(t_ra, t_rs, t0);
2130     tcg_temp_free(t0);
2131
2132     tcg_gen_andi_tl(t_ra, t_ra, MASK(mb, me));
2133     if (unlikely(Rc(ctx->opcode) != 0)) {
2134         gen_set_Rc0(ctx, t_ra);
2135     }
2136 }
2137
2138 /* rldcl - rldcl. */
2139 static inline void gen_rldcl(DisasContext *ctx, int mbn)
2140 {
2141     uint32_t mb;
2142
2143     mb = MB(ctx->opcode) | (mbn << 5);
2144     gen_rldnm(ctx, mb, 63);
2145 }
2146 GEN_PPC64_R2(rldcl, 0x1E, 0x08);
2147
2148 /* rldcr - rldcr. */
2149 static inline void gen_rldcr(DisasContext *ctx, int men)
2150 {
2151     uint32_t me;
2152
2153     me = MB(ctx->opcode) | (men << 5);
2154     gen_rldnm(ctx, 0, me);
2155 }
2156 GEN_PPC64_R2(rldcr, 0x1E, 0x09);
2157
2158 /* rldimi - rldimi. */
2159 static void gen_rldimi(DisasContext *ctx, int mbn, int shn)
2160 {
2161     TCGv t_ra = cpu_gpr[rA(ctx->opcode)];
2162     TCGv t_rs = cpu_gpr[rS(ctx->opcode)];
2163     uint32_t sh = SH(ctx->opcode) | (shn << 5);
2164     uint32_t mb = MB(ctx->opcode) | (mbn << 5);
2165     uint32_t me = 63 - sh;
2166
2167     if (mb <= me) {
2168         tcg_gen_deposit_tl(t_ra, t_ra, t_rs, sh, me - mb + 1);
2169     } else {
2170         target_ulong mask = MASK(mb, me);
2171         TCGv t1 = tcg_temp_new();
2172
2173         tcg_gen_rotli_tl(t1, t_rs, sh);
2174         tcg_gen_andi_tl(t1, t1, mask);
2175         tcg_gen_andi_tl(t_ra, t_ra, ~mask);
2176         tcg_gen_or_tl(t_ra, t_ra, t1);
2177         tcg_temp_free(t1);
2178     }
2179     if (unlikely(Rc(ctx->opcode) != 0)) {
2180         gen_set_Rc0(ctx, t_ra);
2181     }
2182 }
2183 GEN_PPC64_R4(rldimi, 0x1E, 0x06);
2184 #endif
2185
2186 /***                             Integer shift                             ***/
2187
2188 /* slw & slw. */
2189 static void gen_slw(DisasContext *ctx)
2190 {
2191     TCGv t0, t1;
2192
2193     t0 = tcg_temp_new();
2194     /* AND rS with a mask that is 0 when rB >= 0x20 */
2195 #if defined(TARGET_PPC64)
2196     tcg_gen_shli_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x3a);
2197     tcg_gen_sari_tl(t0, t0, 0x3f);
2198 #else
2199     tcg_gen_shli_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x1a);
2200     tcg_gen_sari_tl(t0, t0, 0x1f);
2201 #endif
2202     tcg_gen_andc_tl(t0, cpu_gpr[rS(ctx->opcode)], t0);
2203     t1 = tcg_temp_new();
2204     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x1f);
2205     tcg_gen_shl_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
2206     tcg_temp_free(t1);
2207     tcg_temp_free(t0);
2208     tcg_gen_ext32u_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
2209     if (unlikely(Rc(ctx->opcode) != 0))
2210         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
2211 }
2212
2213 /* sraw & sraw. */
2214 static void gen_sraw(DisasContext *ctx)
2215 {
2216     gen_helper_sraw(cpu_gpr[rA(ctx->opcode)], cpu_env,
2217                     cpu_gpr[rS(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
2218     if (unlikely(Rc(ctx->opcode) != 0))
2219         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
2220 }
2221
2222 /* srawi & srawi. */
2223 static void gen_srawi(DisasContext *ctx)
2224 {
2225     int sh = SH(ctx->opcode);
2226     TCGv dst = cpu_gpr[rA(ctx->opcode)];
2227     TCGv src = cpu_gpr[rS(ctx->opcode)];
2228     if (sh == 0) {
2229         tcg_gen_ext32s_tl(dst, src);
2230         tcg_gen_movi_tl(cpu_ca, 0);
2231     } else {
2232         TCGv t0;
2233         tcg_gen_ext32s_tl(dst, src);
2234         tcg_gen_andi_tl(cpu_ca, dst, (1ULL << sh) - 1);
2235         t0 = tcg_temp_new();
2236         tcg_gen_sari_tl(t0, dst, TARGET_LONG_BITS - 1);
2237         tcg_gen_and_tl(cpu_ca, cpu_ca, t0);
2238         tcg_temp_free(t0);
2239         tcg_gen_setcondi_tl(TCG_COND_NE, cpu_ca, cpu_ca, 0);
2240         tcg_gen_sari_tl(dst, dst, sh);
2241     }
2242     if (unlikely(Rc(ctx->opcode) != 0)) {
2243         gen_set_Rc0(ctx, dst);
2244     }
2245 }
2246
2247 /* srw & srw. */
2248 static void gen_srw(DisasContext *ctx)
2249 {
2250     TCGv t0, t1;
2251
2252     t0 = tcg_temp_new();
2253     /* AND rS with a mask that is 0 when rB >= 0x20 */
2254 #if defined(TARGET_PPC64)
2255     tcg_gen_shli_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x3a);
2256     tcg_gen_sari_tl(t0, t0, 0x3f);
2257 #else
2258     tcg_gen_shli_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x1a);
2259     tcg_gen_sari_tl(t0, t0, 0x1f);
2260 #endif
2261     tcg_gen_andc_tl(t0, cpu_gpr[rS(ctx->opcode)], t0);
2262     tcg_gen_ext32u_tl(t0, t0);
2263     t1 = tcg_temp_new();
2264     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x1f);
2265     tcg_gen_shr_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
2266     tcg_temp_free(t1);
2267     tcg_temp_free(t0);
2268     if (unlikely(Rc(ctx->opcode) != 0))
2269         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
2270 }
2271
2272 #if defined(TARGET_PPC64)
2273 /* sld & sld. */
2274 static void gen_sld(DisasContext *ctx)
2275 {
2276     TCGv t0, t1;
2277
2278     t0 = tcg_temp_new();
2279     /* AND rS with a mask that is 0 when rB >= 0x40 */
2280     tcg_gen_shli_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x39);
2281     tcg_gen_sari_tl(t0, t0, 0x3f);
2282     tcg_gen_andc_tl(t0, cpu_gpr[rS(ctx->opcode)], t0);
2283     t1 = tcg_temp_new();
2284     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x3f);
2285     tcg_gen_shl_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
2286     tcg_temp_free(t1);
2287     tcg_temp_free(t0);
2288     if (unlikely(Rc(ctx->opcode) != 0))
2289         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
2290 }
2291
2292 /* srad & srad. */
2293 static void gen_srad(DisasContext *ctx)
2294 {
2295     gen_helper_srad(cpu_gpr[rA(ctx->opcode)], cpu_env,
2296                     cpu_gpr[rS(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
2297     if (unlikely(Rc(ctx->opcode) != 0))
2298         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
2299 }
2300 /* sradi & sradi. */
2301 static inline void gen_sradi(DisasContext *ctx, int n)
2302 {
2303     int sh = SH(ctx->opcode) + (n << 5);
2304     TCGv dst = cpu_gpr[rA(ctx->opcode)];
2305     TCGv src = cpu_gpr[rS(ctx->opcode)];
2306     if (sh == 0) {
2307         tcg_gen_mov_tl(dst, src);
2308         tcg_gen_movi_tl(cpu_ca, 0);
2309     } else {
2310         TCGv t0;
2311         tcg_gen_andi_tl(cpu_ca, src, (1ULL << sh) - 1);
2312         t0 = tcg_temp_new();
2313         tcg_gen_sari_tl(t0, src, TARGET_LONG_BITS - 1);
2314         tcg_gen_and_tl(cpu_ca, cpu_ca, t0);
2315         tcg_temp_free(t0);
2316         tcg_gen_setcondi_tl(TCG_COND_NE, cpu_ca, cpu_ca, 0);
2317         tcg_gen_sari_tl(dst, src, sh);
2318     }
2319     if (unlikely(Rc(ctx->opcode) != 0)) {
2320         gen_set_Rc0(ctx, dst);
2321     }
2322 }
2323
2324 static void gen_sradi0(DisasContext *ctx)
2325 {
2326     gen_sradi(ctx, 0);
2327 }
2328
2329 static void gen_sradi1(DisasContext *ctx)
2330 {
2331     gen_sradi(ctx, 1);
2332 }
2333
2334 /* extswsli & extswsli. */
2335 static inline void gen_extswsli(DisasContext *ctx, int n)
2336 {
2337     int sh = SH(ctx->opcode) + (n << 5);
2338     TCGv dst = cpu_gpr[rA(ctx->opcode)];
2339     TCGv src = cpu_gpr[rS(ctx->opcode)];
2340
2341     tcg_gen_ext32s_tl(dst, src);
2342     tcg_gen_shli_tl(dst, dst, sh);
2343     if (unlikely(Rc(ctx->opcode) != 0)) {
2344         gen_set_Rc0(ctx, dst);
2345     }
2346 }
2347
2348 static void gen_extswsli0(DisasContext *ctx)
2349 {
2350     gen_extswsli(ctx, 0);
2351 }
2352
2353 static void gen_extswsli1(DisasContext *ctx)
2354 {
2355     gen_extswsli(ctx, 1);
2356 }
2357
2358 /* srd & srd. */
2359 static void gen_srd(DisasContext *ctx)
2360 {
2361     TCGv t0, t1;
2362
2363     t0 = tcg_temp_new();
2364     /* AND rS with a mask that is 0 when rB >= 0x40 */
2365     tcg_gen_shli_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x39);
2366     tcg_gen_sari_tl(t0, t0, 0x3f);
2367     tcg_gen_andc_tl(t0, cpu_gpr[rS(ctx->opcode)], t0);
2368     t1 = tcg_temp_new();
2369     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x3f);
2370     tcg_gen_shr_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
2371     tcg_temp_free(t1);
2372     tcg_temp_free(t0);
2373     if (unlikely(Rc(ctx->opcode) != 0))
2374         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
2375 }
2376 #endif
2377
2378 /***                           Addressing modes                            ***/
2379 /* Register indirect with immediate index : EA = (rA|0) + SIMM */
2380 static inline void gen_addr_imm_index(DisasContext *ctx, TCGv EA,
2381                                       target_long maskl)
2382 {
2383     target_long simm = SIMM(ctx->opcode);
2384
2385     simm &= ~maskl;
2386     if (rA(ctx->opcode) == 0) {
2387         if (NARROW_MODE(ctx)) {
2388             simm = (uint32_t)simm;
2389         }
2390         tcg_gen_movi_tl(EA, simm);
2391     } else if (likely(simm != 0)) {
2392         tcg_gen_addi_tl(EA, cpu_gpr[rA(ctx->opcode)], simm);
2393         if (NARROW_MODE(ctx)) {
2394             tcg_gen_ext32u_tl(EA, EA);
2395         }
2396     } else {
2397         if (NARROW_MODE(ctx)) {
2398             tcg_gen_ext32u_tl(EA, cpu_gpr[rA(ctx->opcode)]);
2399         } else {
2400             tcg_gen_mov_tl(EA, cpu_gpr[rA(ctx->opcode)]);
2401         }
2402     }
2403 }
2404
2405 static inline void gen_addr_reg_index(DisasContext *ctx, TCGv EA)
2406 {
2407     if (rA(ctx->opcode) == 0) {
2408         if (NARROW_MODE(ctx)) {
2409             tcg_gen_ext32u_tl(EA, cpu_gpr[rB(ctx->opcode)]);
2410         } else {
2411             tcg_gen_mov_tl(EA, cpu_gpr[rB(ctx->opcode)]);
2412         }
2413     } else {
2414         tcg_gen_add_tl(EA, cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
2415         if (NARROW_MODE(ctx)) {
2416             tcg_gen_ext32u_tl(EA, EA);
2417         }
2418     }
2419 }
2420
2421 static inline void gen_addr_register(DisasContext *ctx, TCGv EA)
2422 {
2423     if (rA(ctx->opcode) == 0) {
2424         tcg_gen_movi_tl(EA, 0);
2425     } else if (NARROW_MODE(ctx)) {
2426         tcg_gen_ext32u_tl(EA, cpu_gpr[rA(ctx->opcode)]);
2427     } else {
2428         tcg_gen_mov_tl(EA, cpu_gpr[rA(ctx->opcode)]);
2429     }
2430 }
2431
2432 static inline void gen_addr_add(DisasContext *ctx, TCGv ret, TCGv arg1,
2433                                 target_long val)
2434 {
2435     tcg_gen_addi_tl(ret, arg1, val);
2436     if (NARROW_MODE(ctx)) {
2437         tcg_gen_ext32u_tl(ret, ret);
2438     }
2439 }
2440
2441 static inline void gen_check_align(DisasContext *ctx, TCGv EA, int mask)
2442 {
2443     TCGLabel *l1 = gen_new_label();
2444     TCGv t0 = tcg_temp_new();
2445     TCGv_i32 t1, t2;
2446     tcg_gen_andi_tl(t0, EA, mask);
2447     tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);
2448     t1 = tcg_const_i32(POWERPC_EXCP_ALIGN);
2449     t2 = tcg_const_i32(ctx->opcode & 0x03FF0000);
2450     gen_update_nip(ctx, ctx->nip - 4);
2451     gen_helper_raise_exception_err(cpu_env, t1, t2);
2452     tcg_temp_free_i32(t1);
2453     tcg_temp_free_i32(t2);
2454     gen_set_label(l1);
2455     tcg_temp_free(t0);
2456 }
2457
2458 static inline void gen_align_no_le(DisasContext *ctx)
2459 {
2460     gen_exception_err(ctx, POWERPC_EXCP_ALIGN,
2461                       (ctx->opcode & 0x03FF0000) | POWERPC_EXCP_ALIGN_LE);
2462 }
2463
2464 /***                             Integer load                              ***/
2465 #define DEF_MEMOP(op) ((op) | ctx->default_tcg_memop_mask)
2466 #define BSWAP_MEMOP(op) ((op) | (ctx->default_tcg_memop_mask ^ MO_BSWAP))
2467
2468 #define GEN_QEMU_LOAD_TL(ldop, op)                                      \
2469 static void glue(gen_qemu_, ldop)(DisasContext *ctx,                    \
2470                                   TCGv val,                             \
2471                                   TCGv addr)                            \
2472 {                                                                       \
2473     tcg_gen_qemu_ld_tl(val, addr, ctx->mem_idx, op);                    \
2474 }
2475
2476 GEN_QEMU_LOAD_TL(ld8u,  DEF_MEMOP(MO_UB))
2477 GEN_QEMU_LOAD_TL(ld16u, DEF_MEMOP(MO_UW))
2478 GEN_QEMU_LOAD_TL(ld16s, DEF_MEMOP(MO_SW))
2479 GEN_QEMU_LOAD_TL(ld32u, DEF_MEMOP(MO_UL))
2480 GEN_QEMU_LOAD_TL(ld32s, DEF_MEMOP(MO_SL))
2481
2482 GEN_QEMU_LOAD_TL(ld16ur, BSWAP_MEMOP(MO_UW))
2483 GEN_QEMU_LOAD_TL(ld32ur, BSWAP_MEMOP(MO_UL))
2484
2485 #define GEN_QEMU_LOAD_64(ldop, op)                                  \
2486 static void glue(gen_qemu_, glue(ldop, _i64))(DisasContext *ctx,    \
2487                                              TCGv_i64 val,          \
2488                                              TCGv addr)             \
2489 {                                                                   \
2490     tcg_gen_qemu_ld_i64(val, addr, ctx->mem_idx, op);               \
2491 }
2492
2493 GEN_QEMU_LOAD_64(ld32u, DEF_MEMOP(MO_UL))
2494 GEN_QEMU_LOAD_64(ld32s, DEF_MEMOP(MO_SL))
2495 GEN_QEMU_LOAD_64(ld64,  DEF_MEMOP(MO_Q))
2496
2497 #if defined(TARGET_PPC64)
2498 GEN_QEMU_LOAD_64(ld64ur, BSWAP_MEMOP(MO_Q))
2499 #endif
2500
2501 #define GEN_QEMU_STORE_TL(stop, op)                                     \
2502 static void glue(gen_qemu_, stop)(DisasContext *ctx,                    \
2503                                   TCGv val,                             \
2504                                   TCGv addr)                            \
2505 {                                                                       \
2506     tcg_gen_qemu_st_tl(val, addr, ctx->mem_idx, op);                    \
2507 }
2508
2509 GEN_QEMU_STORE_TL(st8,  DEF_MEMOP(MO_UB))
2510 GEN_QEMU_STORE_TL(st16, DEF_MEMOP(MO_UW))
2511 GEN_QEMU_STORE_TL(st32, DEF_MEMOP(MO_UL))
2512
2513 GEN_QEMU_STORE_TL(st16r, BSWAP_MEMOP(MO_UW))
2514 GEN_QEMU_STORE_TL(st32r, BSWAP_MEMOP(MO_UL))
2515
2516 #define GEN_QEMU_STORE_64(stop, op)                               \
2517 static void glue(gen_qemu_, glue(stop, _i64))(DisasContext *ctx,  \
2518                                               TCGv_i64 val,       \
2519                                               TCGv addr)          \
2520 {                                                                 \
2521     tcg_gen_qemu_st_i64(val, addr, ctx->mem_idx, op);             \
2522 }
2523
2524 GEN_QEMU_STORE_64(st32, DEF_MEMOP(MO_UL))
2525 GEN_QEMU_STORE_64(st64, DEF_MEMOP(MO_Q))
2526
2527 #if defined(TARGET_PPC64)
2528 GEN_QEMU_STORE_64(st64r, BSWAP_MEMOP(MO_Q))
2529 #endif
2530
2531 #define GEN_LD(name, ldop, opc, type)                                         \
2532 static void glue(gen_, name)(DisasContext *ctx)                                       \
2533 {                                                                             \
2534     TCGv EA;                                                                  \
2535     gen_set_access_type(ctx, ACCESS_INT);                                     \
2536     EA = tcg_temp_new();                                                      \
2537     gen_addr_imm_index(ctx, EA, 0);                                           \
2538     gen_qemu_##ldop(ctx, cpu_gpr[rD(ctx->opcode)], EA);                       \
2539     tcg_temp_free(EA);                                                        \
2540 }
2541
2542 #define GEN_LDU(name, ldop, opc, type)                                        \
2543 static void glue(gen_, name##u)(DisasContext *ctx)                                    \
2544 {                                                                             \
2545     TCGv EA;                                                                  \
2546     if (unlikely(rA(ctx->opcode) == 0 ||                                      \
2547                  rA(ctx->opcode) == rD(ctx->opcode))) {                       \
2548         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);                   \
2549         return;                                                               \
2550     }                                                                         \
2551     gen_set_access_type(ctx, ACCESS_INT);                                     \
2552     EA = tcg_temp_new();                                                      \
2553     if (type == PPC_64B)                                                      \
2554         gen_addr_imm_index(ctx, EA, 0x03);                                    \
2555     else                                                                      \
2556         gen_addr_imm_index(ctx, EA, 0);                                       \
2557     gen_qemu_##ldop(ctx, cpu_gpr[rD(ctx->opcode)], EA);                       \
2558     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], EA);                             \
2559     tcg_temp_free(EA);                                                        \
2560 }
2561
2562 #define GEN_LDUX(name, ldop, opc2, opc3, type)                                \
2563 static void glue(gen_, name##ux)(DisasContext *ctx)                                   \
2564 {                                                                             \
2565     TCGv EA;                                                                  \
2566     if (unlikely(rA(ctx->opcode) == 0 ||                                      \
2567                  rA(ctx->opcode) == rD(ctx->opcode))) {                       \
2568         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);                   \
2569         return;                                                               \
2570     }                                                                         \
2571     gen_set_access_type(ctx, ACCESS_INT);                                     \
2572     EA = tcg_temp_new();                                                      \
2573     gen_addr_reg_index(ctx, EA);                                              \
2574     gen_qemu_##ldop(ctx, cpu_gpr[rD(ctx->opcode)], EA);                       \
2575     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], EA);                             \
2576     tcg_temp_free(EA);                                                        \
2577 }
2578
2579 #define GEN_LDX_E(name, ldop, opc2, opc3, type, type2, chk)                   \
2580 static void glue(gen_, name##x)(DisasContext *ctx)                            \
2581 {                                                                             \
2582     TCGv EA;                                                                  \
2583     chk;                                                                      \
2584     gen_set_access_type(ctx, ACCESS_INT);                                     \
2585     EA = tcg_temp_new();                                                      \
2586     gen_addr_reg_index(ctx, EA);                                              \
2587     gen_qemu_##ldop(ctx, cpu_gpr[rD(ctx->opcode)], EA);                       \
2588     tcg_temp_free(EA);                                                        \
2589 }
2590
2591 #define GEN_LDX(name, ldop, opc2, opc3, type)                                 \
2592     GEN_LDX_E(name, ldop, opc2, opc3, type, PPC_NONE, CHK_NONE)
2593
2594 #define GEN_LDX_HVRM(name, ldop, opc2, opc3, type)                            \
2595     GEN_LDX_E(name, ldop, opc2, opc3, type, PPC_NONE, CHK_HVRM)
2596
2597 #define GEN_LDS(name, ldop, op, type)                                         \
2598 GEN_LD(name, ldop, op | 0x20, type);                                          \
2599 GEN_LDU(name, ldop, op | 0x21, type);                                         \
2600 GEN_LDUX(name, ldop, 0x17, op | 0x01, type);                                  \
2601 GEN_LDX(name, ldop, 0x17, op | 0x00, type)
2602
2603 /* lbz lbzu lbzux lbzx */
2604 GEN_LDS(lbz, ld8u, 0x02, PPC_INTEGER);
2605 /* lha lhau lhaux lhax */
2606 GEN_LDS(lha, ld16s, 0x0A, PPC_INTEGER);
2607 /* lhz lhzu lhzux lhzx */
2608 GEN_LDS(lhz, ld16u, 0x08, PPC_INTEGER);
2609 /* lwz lwzu lwzux lwzx */
2610 GEN_LDS(lwz, ld32u, 0x00, PPC_INTEGER);
2611 #if defined(TARGET_PPC64)
2612 /* lwaux */
2613 GEN_LDUX(lwa, ld32s, 0x15, 0x0B, PPC_64B);
2614 /* lwax */
2615 GEN_LDX(lwa, ld32s, 0x15, 0x0A, PPC_64B);
2616 /* ldux */
2617 GEN_LDUX(ld, ld64_i64, 0x15, 0x01, PPC_64B);
2618 /* ldx */
2619 GEN_LDX(ld, ld64_i64, 0x15, 0x00, PPC_64B);
2620
2621 /* CI load/store variants */
2622 GEN_LDX_HVRM(ldcix, ld64_i64, 0x15, 0x1b, PPC_CILDST)
2623 GEN_LDX_HVRM(lwzcix, ld32u, 0x15, 0x15, PPC_CILDST)
2624 GEN_LDX_HVRM(lhzcix, ld16u, 0x15, 0x19, PPC_CILDST)
2625 GEN_LDX_HVRM(lbzcix, ld8u, 0x15, 0x1a, PPC_CILDST)
2626
2627 static void gen_ld(DisasContext *ctx)
2628 {
2629     TCGv EA;
2630     if (Rc(ctx->opcode)) {
2631         if (unlikely(rA(ctx->opcode) == 0 ||
2632                      rA(ctx->opcode) == rD(ctx->opcode))) {
2633             gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
2634             return;
2635         }
2636     }
2637     gen_set_access_type(ctx, ACCESS_INT);
2638     EA = tcg_temp_new();
2639     gen_addr_imm_index(ctx, EA, 0x03);
2640     if (ctx->opcode & 0x02) {
2641         /* lwa (lwau is undefined) */
2642         gen_qemu_ld32s(ctx, cpu_gpr[rD(ctx->opcode)], EA);
2643     } else {
2644         /* ld - ldu */
2645         gen_qemu_ld64_i64(ctx, cpu_gpr[rD(ctx->opcode)], EA);
2646     }
2647     if (Rc(ctx->opcode))
2648         tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], EA);
2649     tcg_temp_free(EA);
2650 }
2651
2652 /* lq */
2653 static void gen_lq(DisasContext *ctx)
2654 {
2655     int ra, rd;
2656     TCGv EA;
2657
2658     /* lq is a legal user mode instruction starting in ISA 2.07 */
2659     bool legal_in_user_mode = (ctx->insns_flags2 & PPC2_LSQ_ISA207) != 0;
2660     bool le_is_supported = (ctx->insns_flags2 & PPC2_LSQ_ISA207) != 0;
2661
2662     if (!legal_in_user_mode && ctx->pr) {
2663         gen_priv_exception(ctx, POWERPC_EXCP_PRIV_OPC);
2664         return;
2665     }
2666
2667     if (!le_is_supported && ctx->le_mode) {
2668         gen_align_no_le(ctx);
2669         return;
2670     }
2671     ra = rA(ctx->opcode);
2672     rd = rD(ctx->opcode);
2673     if (unlikely((rd & 1) || rd == ra)) {
2674         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
2675         return;
2676     }
2677
2678     gen_set_access_type(ctx, ACCESS_INT);
2679     EA = tcg_temp_new();
2680     gen_addr_imm_index(ctx, EA, 0x0F);
2681
2682     /* We only need to swap high and low halves. gen_qemu_ld64_i64 does
2683        necessary 64-bit byteswap already. */
2684     if (unlikely(ctx->le_mode)) {
2685         gen_qemu_ld64_i64(ctx, cpu_gpr[rd + 1], EA);
2686         gen_addr_add(ctx, EA, EA, 8);
2687         gen_qemu_ld64_i64(ctx, cpu_gpr[rd], EA);
2688     } else {
2689         gen_qemu_ld64_i64(ctx, cpu_gpr[rd], EA);
2690         gen_addr_add(ctx, EA, EA, 8);
2691         gen_qemu_ld64_i64(ctx, cpu_gpr[rd + 1], EA);
2692     }
2693     tcg_temp_free(EA);
2694 }
2695 #endif
2696
2697 /***                              Integer store                            ***/
2698 #define GEN_ST(name, stop, opc, type)                                         \
2699 static void glue(gen_, name)(DisasContext *ctx)                                       \
2700 {                                                                             \
2701     TCGv EA;                                                                  \
2702     gen_set_access_type(ctx, ACCESS_INT);                                     \
2703     EA = tcg_temp_new();                                                      \
2704     gen_addr_imm_index(ctx, EA, 0);                                           \
2705     gen_qemu_##stop(ctx, cpu_gpr[rS(ctx->opcode)], EA);                       \
2706     tcg_temp_free(EA);                                                        \
2707 }
2708
2709 #define GEN_STU(name, stop, opc, type)                                        \
2710 static void glue(gen_, stop##u)(DisasContext *ctx)                                    \
2711 {                                                                             \
2712     TCGv EA;                                                                  \
2713     if (unlikely(rA(ctx->opcode) == 0)) {                                     \
2714         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);                   \
2715         return;                                                               \
2716     }                                                                         \
2717     gen_set_access_type(ctx, ACCESS_INT);                                     \
2718     EA = tcg_temp_new();                                                      \
2719     if (type == PPC_64B)                                                      \
2720         gen_addr_imm_index(ctx, EA, 0x03);                                    \
2721     else                                                                      \
2722         gen_addr_imm_index(ctx, EA, 0);                                       \
2723     gen_qemu_##stop(ctx, cpu_gpr[rS(ctx->opcode)], EA);                       \
2724     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], EA);                             \
2725     tcg_temp_free(EA);                                                        \
2726 }
2727
2728 #define GEN_STUX(name, stop, opc2, opc3, type)                                \
2729 static void glue(gen_, name##ux)(DisasContext *ctx)                                   \
2730 {                                                                             \
2731     TCGv EA;                                                                  \
2732     if (unlikely(rA(ctx->opcode) == 0)) {                                     \
2733         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);                   \
2734         return;                                                               \
2735     }                                                                         \
2736     gen_set_access_type(ctx, ACCESS_INT);                                     \
2737     EA = tcg_temp_new();                                                      \
2738     gen_addr_reg_index(ctx, EA);                                              \
2739     gen_qemu_##stop(ctx, cpu_gpr[rS(ctx->opcode)], EA);                       \
2740     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], EA);                             \
2741     tcg_temp_free(EA);                                                        \
2742 }
2743
2744 #define GEN_STX_E(name, stop, opc2, opc3, type, type2, chk)                   \
2745 static void glue(gen_, name##x)(DisasContext *ctx)                            \
2746 {                                                                             \
2747     TCGv EA;                                                                  \
2748     chk;                                                                      \
2749     gen_set_access_type(ctx, ACCESS_INT);                                     \
2750     EA = tcg_temp_new();                                                      \
2751     gen_addr_reg_index(ctx, EA);                                              \
2752     gen_qemu_##stop(ctx, cpu_gpr[rS(ctx->opcode)], EA);                       \
2753     tcg_temp_free(EA);                                                        \
2754 }
2755 #define GEN_STX(name, stop, opc2, opc3, type)                                 \
2756     GEN_STX_E(name, stop, opc2, opc3, type, PPC_NONE, CHK_NONE)
2757
2758 #define GEN_STX_HVRM(name, stop, opc2, opc3, type)                            \
2759     GEN_STX_E(name, stop, opc2, opc3, type, PPC_NONE, CHK_HVRM)
2760
2761 #define GEN_STS(name, stop, op, type)                                         \
2762 GEN_ST(name, stop, op | 0x20, type);                                          \
2763 GEN_STU(name, stop, op | 0x21, type);                                         \
2764 GEN_STUX(name, stop, 0x17, op | 0x01, type);                                  \
2765 GEN_STX(name, stop, 0x17, op | 0x00, type)
2766
2767 /* stb stbu stbux stbx */
2768 GEN_STS(stb, st8, 0x06, PPC_INTEGER);
2769 /* sth sthu sthux sthx */
2770 GEN_STS(sth, st16, 0x0C, PPC_INTEGER);
2771 /* stw stwu stwux stwx */
2772 GEN_STS(stw, st32, 0x04, PPC_INTEGER);
2773 #if defined(TARGET_PPC64)
2774 GEN_STUX(std, st64_i64, 0x15, 0x05, PPC_64B);
2775 GEN_STX(std, st64_i64, 0x15, 0x04, PPC_64B);
2776 GEN_STX_HVRM(stdcix, st64_i64, 0x15, 0x1f, PPC_CILDST)
2777 GEN_STX_HVRM(stwcix, st32, 0x15, 0x1c, PPC_CILDST)
2778 GEN_STX_HVRM(sthcix, st16, 0x15, 0x1d, PPC_CILDST)
2779 GEN_STX_HVRM(stbcix, st8, 0x15, 0x1e, PPC_CILDST)
2780
2781 static void gen_std(DisasContext *ctx)
2782 {
2783     int rs;
2784     TCGv EA;
2785
2786     rs = rS(ctx->opcode);
2787     if ((ctx->opcode & 0x3) == 0x2) { /* stq */
2788         bool legal_in_user_mode = (ctx->insns_flags2 & PPC2_LSQ_ISA207) != 0;
2789         bool le_is_supported = (ctx->insns_flags2 & PPC2_LSQ_ISA207) != 0;
2790
2791         if (!(ctx->insns_flags & PPC_64BX)) {
2792             gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
2793         }
2794
2795         if (!legal_in_user_mode && ctx->pr) {
2796             gen_priv_exception(ctx, POWERPC_EXCP_PRIV_OPC);
2797             return;
2798         }
2799
2800         if (!le_is_supported && ctx->le_mode) {
2801             gen_align_no_le(ctx);
2802             return;
2803         }
2804
2805         if (unlikely(rs & 1)) {
2806             gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
2807             return;
2808         }
2809         gen_set_access_type(ctx, ACCESS_INT);
2810         EA = tcg_temp_new();
2811         gen_addr_imm_index(ctx, EA, 0x03);
2812
2813         /* We only need to swap high and low halves. gen_qemu_st64_i64 does
2814            necessary 64-bit byteswap already. */
2815         if (unlikely(ctx->le_mode)) {
2816             gen_qemu_st64_i64(ctx, cpu_gpr[rs + 1], EA);
2817             gen_addr_add(ctx, EA, EA, 8);
2818             gen_qemu_st64_i64(ctx, cpu_gpr[rs], EA);
2819         } else {
2820             gen_qemu_st64_i64(ctx, cpu_gpr[rs], EA);
2821             gen_addr_add(ctx, EA, EA, 8);
2822             gen_qemu_st64_i64(ctx, cpu_gpr[rs + 1], EA);
2823         }
2824         tcg_temp_free(EA);
2825     } else {
2826         /* std / stdu*/
2827         if (Rc(ctx->opcode)) {
2828             if (unlikely(rA(ctx->opcode) == 0)) {
2829                 gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
2830                 return;
2831             }
2832         }
2833         gen_set_access_type(ctx, ACCESS_INT);
2834         EA = tcg_temp_new();
2835         gen_addr_imm_index(ctx, EA, 0x03);
2836         gen_qemu_st64_i64(ctx, cpu_gpr[rs], EA);
2837         if (Rc(ctx->opcode))
2838             tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], EA);
2839         tcg_temp_free(EA);
2840     }
2841 }
2842 #endif
2843 /***                Integer load and store with byte reverse               ***/
2844
2845 /* lhbrx */
2846 GEN_LDX(lhbr, ld16ur, 0x16, 0x18, PPC_INTEGER);
2847
2848 /* lwbrx */
2849 GEN_LDX(lwbr, ld32ur, 0x16, 0x10, PPC_INTEGER);
2850
2851 #if defined(TARGET_PPC64)
2852 /* ldbrx */
2853 GEN_LDX_E(ldbr, ld64ur_i64, 0x14, 0x10, PPC_NONE, PPC2_DBRX, CHK_NONE);
2854 /* stdbrx */
2855 GEN_STX_E(stdbr, st64r_i64, 0x14, 0x14, PPC_NONE, PPC2_DBRX, CHK_NONE);
2856 #endif  /* TARGET_PPC64 */
2857
2858 /* sthbrx */
2859 GEN_STX(sthbr, st16r, 0x16, 0x1C, PPC_INTEGER);
2860 /* stwbrx */
2861 GEN_STX(stwbr, st32r, 0x16, 0x14, PPC_INTEGER);
2862
2863 /***                    Integer load and store multiple                    ***/
2864
2865 /* lmw */
2866 static void gen_lmw(DisasContext *ctx)
2867 {
2868     TCGv t0;
2869     TCGv_i32 t1;
2870
2871     if (ctx->le_mode) {
2872         gen_align_no_le(ctx);
2873         return;
2874     }
2875     gen_set_access_type(ctx, ACCESS_INT);
2876     t0 = tcg_temp_new();
2877     t1 = tcg_const_i32(rD(ctx->opcode));
2878     gen_addr_imm_index(ctx, t0, 0);
2879     gen_helper_lmw(cpu_env, t0, t1);
2880     tcg_temp_free(t0);
2881     tcg_temp_free_i32(t1);
2882 }
2883
2884 /* stmw */
2885 static void gen_stmw(DisasContext *ctx)
2886 {
2887     TCGv t0;
2888     TCGv_i32 t1;
2889
2890     if (ctx->le_mode) {
2891         gen_align_no_le(ctx);
2892         return;
2893     }
2894     gen_set_access_type(ctx, ACCESS_INT);
2895     t0 = tcg_temp_new();
2896     t1 = tcg_const_i32(rS(ctx->opcode));
2897     gen_addr_imm_index(ctx, t0, 0);
2898     gen_helper_stmw(cpu_env, t0, t1);
2899     tcg_temp_free(t0);
2900     tcg_temp_free_i32(t1);
2901 }
2902
2903 /***                    Integer load and store strings                     ***/
2904
2905 /* lswi */
2906 /* PowerPC32 specification says we must generate an exception if
2907  * rA is in the range of registers to be loaded.
2908  * In an other hand, IBM says this is valid, but rA won't be loaded.
2909  * For now, I'll follow the spec...
2910  */
2911 static void gen_lswi(DisasContext *ctx)
2912 {
2913     TCGv t0;
2914     TCGv_i32 t1, t2;
2915     int nb = NB(ctx->opcode);
2916     int start = rD(ctx->opcode);
2917     int ra = rA(ctx->opcode);
2918     int nr;
2919
2920     if (ctx->le_mode) {
2921         gen_align_no_le(ctx);
2922         return;
2923     }
2924     if (nb == 0)
2925         nb = 32;
2926     nr = (nb + 3) / 4;
2927     if (unlikely(lsw_reg_in_range(start, nr, ra))) {
2928         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_LSWX);
2929         return;
2930     }
2931     gen_set_access_type(ctx, ACCESS_INT);
2932     t0 = tcg_temp_new();
2933     gen_addr_register(ctx, t0);
2934     t1 = tcg_const_i32(nb);
2935     t2 = tcg_const_i32(start);
2936     gen_helper_lsw(cpu_env, t0, t1, t2);
2937     tcg_temp_free(t0);
2938     tcg_temp_free_i32(t1);
2939     tcg_temp_free_i32(t2);
2940 }
2941
2942 /* lswx */
2943 static void gen_lswx(DisasContext *ctx)
2944 {
2945     TCGv t0;
2946     TCGv_i32 t1, t2, t3;
2947
2948     if (ctx->le_mode) {
2949         gen_align_no_le(ctx);
2950         return;
2951     }
2952     gen_set_access_type(ctx, ACCESS_INT);
2953     t0 = tcg_temp_new();
2954     gen_addr_reg_index(ctx, t0);
2955     t1 = tcg_const_i32(rD(ctx->opcode));
2956     t2 = tcg_const_i32(rA(ctx->opcode));
2957     t3 = tcg_const_i32(rB(ctx->opcode));
2958     gen_helper_lswx(cpu_env, t0, t1, t2, t3);
2959     tcg_temp_free(t0);
2960     tcg_temp_free_i32(t1);
2961     tcg_temp_free_i32(t2);
2962     tcg_temp_free_i32(t3);
2963 }
2964
2965 /* stswi */
2966 static void gen_stswi(DisasContext *ctx)
2967 {
2968     TCGv t0;
2969     TCGv_i32 t1, t2;
2970     int nb = NB(ctx->opcode);
2971
2972     if (ctx->le_mode) {
2973         gen_align_no_le(ctx);
2974         return;
2975     }
2976     gen_set_access_type(ctx, ACCESS_INT);
2977     t0 = tcg_temp_new();
2978     gen_addr_register(ctx, t0);
2979     if (nb == 0)
2980         nb = 32;
2981     t1 = tcg_const_i32(nb);
2982     t2 = tcg_const_i32(rS(ctx->opcode));
2983     gen_helper_stsw(cpu_env, t0, t1, t2);
2984     tcg_temp_free(t0);
2985     tcg_temp_free_i32(t1);
2986     tcg_temp_free_i32(t2);
2987 }
2988
2989 /* stswx */
2990 static void gen_stswx(DisasContext *ctx)
2991 {
2992     TCGv t0;
2993     TCGv_i32 t1, t2;
2994
2995     if (ctx->le_mode) {
2996         gen_align_no_le(ctx);
2997         return;
2998     }
2999     gen_set_access_type(ctx, ACCESS_INT);
3000     t0 = tcg_temp_new();
3001     gen_addr_reg_index(ctx, t0);
3002     t1 = tcg_temp_new_i32();
3003     tcg_gen_trunc_tl_i32(t1, cpu_xer);
3004     tcg_gen_andi_i32(t1, t1, 0x7F);
3005     t2 = tcg_const_i32(rS(ctx->opcode));
3006     gen_helper_stsw(cpu_env, t0, t1, t2);
3007     tcg_temp_free(t0);
3008     tcg_temp_free_i32(t1);
3009     tcg_temp_free_i32(t2);
3010 }
3011
3012 /***                        Memory synchronisation                         ***/
3013 /* eieio */
3014 static void gen_eieio(DisasContext *ctx)
3015 {
3016 }
3017
3018 #if !defined(CONFIG_USER_ONLY)
3019 static inline void gen_check_tlb_flush(DisasContext *ctx)
3020 {
3021     TCGv_i32 t;
3022     TCGLabel *l;
3023
3024     if (!ctx->lazy_tlb_flush) {
3025         return;
3026     }
3027     l = gen_new_label();
3028     t = tcg_temp_new_i32();
3029     tcg_gen_ld_i32(t, cpu_env, offsetof(CPUPPCState, tlb_need_flush));
3030     tcg_gen_brcondi_i32(TCG_COND_EQ, t, 0, l);
3031     gen_helper_check_tlb_flush(cpu_env);
3032     gen_set_label(l);
3033     tcg_temp_free_i32(t);
3034 }
3035 #else
3036 static inline void gen_check_tlb_flush(DisasContext *ctx) { }
3037 #endif
3038
3039 /* isync */
3040 static void gen_isync(DisasContext *ctx)
3041 {
3042     /*
3043      * We need to check for a pending TLB flush. This can only happen in
3044      * kernel mode however so check MSR_PR
3045      */
3046     if (!ctx->pr) {
3047         gen_check_tlb_flush(ctx);
3048     }
3049     gen_stop_exception(ctx);
3050 }
3051
3052 #define MEMOP_GET_SIZE(x)  (1 << ((x) & MO_SIZE))
3053
3054 #define LARX(name, memop)                                            \
3055 static void gen_##name(DisasContext *ctx)                            \
3056 {                                                                    \
3057     TCGv t0;                                                         \
3058     TCGv gpr = cpu_gpr[rD(ctx->opcode)];                             \
3059     int len = MEMOP_GET_SIZE(memop);                                 \
3060     gen_set_access_type(ctx, ACCESS_RES);                            \
3061     t0 = tcg_temp_local_new();                                       \
3062     gen_addr_reg_index(ctx, t0);                                     \
3063     if ((len) > 1) {                                                 \
3064         gen_check_align(ctx, t0, (len)-1);                           \
3065     }                                                                \
3066     tcg_gen_qemu_ld_tl(gpr, t0, ctx->mem_idx, memop);                \
3067     tcg_gen_mov_tl(cpu_reserve, t0);                                 \
3068     tcg_gen_st_tl(gpr, cpu_env, offsetof(CPUPPCState, reserve_val)); \
3069     tcg_temp_free(t0);                                               \
3070 }
3071
3072 /* lwarx */
3073 LARX(lbarx, DEF_MEMOP(MO_UB))
3074 LARX(lharx, DEF_MEMOP(MO_UW))
3075 LARX(lwarx, DEF_MEMOP(MO_UL))
3076
3077 #if defined(CONFIG_USER_ONLY)
3078 static void gen_conditional_store(DisasContext *ctx, TCGv EA,
3079                                   int reg, int memop)
3080 {
3081     TCGv t0 = tcg_temp_new();
3082
3083     tcg_gen_st_tl(EA, cpu_env, offsetof(CPUPPCState, reserve_ea));
3084     tcg_gen_movi_tl(t0, (MEMOP_GET_SIZE(memop) << 5) | reg);
3085     tcg_gen_st_tl(t0, cpu_env, offsetof(CPUPPCState, reserve_info));
3086     tcg_temp_free(t0);
3087     gen_exception_err(ctx, POWERPC_EXCP_STCX, 0);
3088 }
3089 #else
3090 static void gen_conditional_store(DisasContext *ctx, TCGv EA,
3091                                   int reg, int memop)
3092 {
3093     TCGLabel *l1;
3094
3095     tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_so);
3096     l1 = gen_new_label();
3097     tcg_gen_brcond_tl(TCG_COND_NE, EA, cpu_reserve, l1);
3098     tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 1 << CRF_EQ);
3099     tcg_gen_qemu_st_tl(cpu_gpr[reg], EA, ctx->mem_idx, memop);
3100     gen_set_label(l1);
3101     tcg_gen_movi_tl(cpu_reserve, -1);
3102 }
3103 #endif
3104
3105 #define STCX(name, memop)                                   \
3106 static void gen_##name(DisasContext *ctx)                   \
3107 {                                                           \
3108     TCGv t0;                                                \
3109     int len = MEMOP_GET_SIZE(memop);                        \
3110     gen_set_access_type(ctx, ACCESS_RES);                   \
3111     t0 = tcg_temp_local_new();                              \
3112     gen_addr_reg_index(ctx, t0);                            \
3113     if (len > 1) {                                          \
3114         gen_check_align(ctx, t0, (len) - 1);                \
3115     }                                                       \
3116     gen_conditional_store(ctx, t0, rS(ctx->opcode), memop); \
3117     tcg_temp_free(t0);                                      \
3118 }
3119
3120 STCX(stbcx_, DEF_MEMOP(MO_UB))
3121 STCX(sthcx_, DEF_MEMOP(MO_UW))
3122 STCX(stwcx_, DEF_MEMOP(MO_UL))
3123
3124 #if defined(TARGET_PPC64)
3125 /* ldarx */
3126 LARX(ldarx, DEF_MEMOP(MO_Q))
3127 /* stdcx. */
3128 STCX(stdcx_, DEF_MEMOP(MO_Q))
3129
3130 /* lqarx */
3131 static void gen_lqarx(DisasContext *ctx)
3132 {
3133     TCGv EA;
3134     int rd = rD(ctx->opcode);
3135     TCGv gpr1, gpr2;
3136
3137     if (unlikely((rd & 1) || (rd == rA(ctx->opcode)) ||
3138                  (rd == rB(ctx->opcode)))) {
3139         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
3140         return;
3141     }
3142
3143     gen_set_access_type(ctx, ACCESS_RES);
3144     EA = tcg_temp_local_new();
3145     gen_addr_reg_index(ctx, EA);
3146     gen_check_align(ctx, EA, 15);
3147     if (unlikely(ctx->le_mode)) {
3148         gpr1 = cpu_gpr[rd+1];
3149         gpr2 = cpu_gpr[rd];
3150     } else {
3151         gpr1 = cpu_gpr[rd];
3152         gpr2 = cpu_gpr[rd+1];
3153     }
3154     tcg_gen_qemu_ld_i64(gpr1, EA, ctx->mem_idx, DEF_MEMOP(MO_Q));
3155     tcg_gen_mov_tl(cpu_reserve, EA);
3156     gen_addr_add(ctx, EA, EA, 8);
3157     tcg_gen_qemu_ld_i64(gpr2, EA, ctx->mem_idx, DEF_MEMOP(MO_Q));
3158
3159     tcg_gen_st_tl(gpr1, cpu_env, offsetof(CPUPPCState, reserve_val));
3160     tcg_gen_st_tl(gpr2, cpu_env, offsetof(CPUPPCState, reserve_val2));
3161     tcg_temp_free(EA);
3162 }
3163
3164 /* stqcx. */
3165 static void gen_stqcx_(DisasContext *ctx)
3166 {
3167     TCGv EA;
3168     int reg = rS(ctx->opcode);
3169     int len = 16;
3170 #if !defined(CONFIG_USER_ONLY)
3171     TCGLabel *l1;
3172     TCGv gpr1, gpr2;
3173 #endif
3174
3175     if (unlikely((rD(ctx->opcode) & 1))) {
3176         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
3177         return;
3178     }
3179     gen_set_access_type(ctx, ACCESS_RES);
3180     EA = tcg_temp_local_new();
3181     gen_addr_reg_index(ctx, EA);
3182     if (len > 1) {
3183         gen_check_align(ctx, EA, (len) - 1);
3184     }
3185
3186 #if defined(CONFIG_USER_ONLY)
3187     gen_conditional_store(ctx, EA, reg, 16);
3188 #else
3189     tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_so);
3190     l1 = gen_new_label();
3191     tcg_gen_brcond_tl(TCG_COND_NE, EA, cpu_reserve, l1);
3192     tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 1 << CRF_EQ);
3193
3194     if (unlikely(ctx->le_mode)) {
3195         gpr1 = cpu_gpr[reg + 1];
3196         gpr2 = cpu_gpr[reg];
3197     } else {
3198         gpr1 = cpu_gpr[reg];
3199         gpr2 = cpu_gpr[reg + 1];
3200     }
3201     tcg_gen_qemu_st_tl(gpr1, EA, ctx->mem_idx, DEF_MEMOP(MO_Q));
3202     gen_addr_add(ctx, EA, EA, 8);
3203     tcg_gen_qemu_st_tl(gpr2, EA, ctx->mem_idx, DEF_MEMOP(MO_Q));
3204
3205     gen_set_label(l1);
3206     tcg_gen_movi_tl(cpu_reserve, -1);
3207 #endif
3208     tcg_temp_free(EA);
3209 }
3210
3211 #endif /* defined(TARGET_PPC64) */
3212
3213 /* sync */
3214 static void gen_sync(DisasContext *ctx)
3215 {
3216     uint32_t l = (ctx->opcode >> 21) & 3;
3217
3218     /*
3219      * We may need to check for a pending TLB flush.
3220      *
3221      * We do this on ptesync (l == 2) on ppc64 and any sync pn ppc32.
3222      *
3223      * Additionally, this can only happen in kernel mode however so
3224      * check MSR_PR as well.
3225      */
3226     if (((l == 2) || !(ctx->insns_flags & PPC_64B)) && !ctx->pr) {
3227         gen_check_tlb_flush(ctx);
3228     }
3229 }
3230
3231 /* wait */
3232 static void gen_wait(DisasContext *ctx)
3233 {
3234     TCGv_i32 t0 = tcg_const_i32(1);
3235     tcg_gen_st_i32(t0, cpu_env,
3236                    -offsetof(PowerPCCPU, env) + offsetof(CPUState, halted));
3237     tcg_temp_free_i32(t0);
3238     /* Stop translation, as the CPU is supposed to sleep from now */
3239     gen_exception_nip(ctx, EXCP_HLT, ctx->nip);
3240 }
3241
3242 #if defined(TARGET_PPC64)
3243 static void gen_doze(DisasContext *ctx)
3244 {
3245 #if defined(CONFIG_USER_ONLY)
3246     GEN_PRIV;
3247 #else
3248     TCGv_i32 t;
3249
3250     CHK_HV;
3251     t = tcg_const_i32(PPC_PM_DOZE);
3252     gen_helper_pminsn(cpu_env, t);
3253     tcg_temp_free_i32(t);
3254     gen_stop_exception(ctx);
3255 #endif /* defined(CONFIG_USER_ONLY) */
3256 }
3257
3258 static void gen_nap(DisasContext *ctx)
3259 {
3260 #if defined(CONFIG_USER_ONLY)
3261     GEN_PRIV;
3262 #else
3263     TCGv_i32 t;
3264
3265     CHK_HV;
3266     t = tcg_const_i32(PPC_PM_NAP);
3267     gen_helper_pminsn(cpu_env, t);
3268     tcg_temp_free_i32(t);
3269     gen_stop_exception(ctx);
3270 #endif /* defined(CONFIG_USER_ONLY) */
3271 }
3272
3273 static void gen_sleep(DisasContext *ctx)
3274 {
3275 #if defined(CONFIG_USER_ONLY)
3276     GEN_PRIV;
3277 #else
3278     TCGv_i32 t;
3279
3280     CHK_HV;
3281     t = tcg_const_i32(PPC_PM_SLEEP);
3282     gen_helper_pminsn(cpu_env, t);
3283     tcg_temp_free_i32(t);
3284     gen_stop_exception(ctx);
3285 #endif /* defined(CONFIG_USER_ONLY) */
3286 }
3287
3288 static void gen_rvwinkle(DisasContext *ctx)
3289 {
3290 #if defined(CONFIG_USER_ONLY)
3291     GEN_PRIV;
3292 #else
3293     TCGv_i32 t;
3294
3295     CHK_HV;
3296     t = tcg_const_i32(PPC_PM_RVWINKLE);
3297     gen_helper_pminsn(cpu_env, t);
3298     tcg_temp_free_i32(t);
3299     gen_stop_exception(ctx);
3300 #endif /* defined(CONFIG_USER_ONLY) */
3301 }
3302 #endif /* #if defined(TARGET_PPC64) */
3303
3304 static inline void gen_update_cfar(DisasContext *ctx, target_ulong nip)
3305 {
3306 #if defined(TARGET_PPC64)
3307     if (ctx->has_cfar)
3308         tcg_gen_movi_tl(cpu_cfar, nip);
3309 #endif
3310 }
3311
3312 static inline bool use_goto_tb(DisasContext *ctx, target_ulong dest)
3313 {
3314     if (unlikely(ctx->singlestep_enabled)) {
3315         return false;
3316     }
3317
3318 #ifndef CONFIG_USER_ONLY
3319     return (ctx->tb->pc & TARGET_PAGE_MASK) == (dest & TARGET_PAGE_MASK);
3320 #else
3321     return true;
3322 #endif
3323 }
3324
3325 /***                                Branch                                 ***/
3326 static inline void gen_goto_tb(DisasContext *ctx, int n, target_ulong dest)
3327 {
3328     if (NARROW_MODE(ctx)) {
3329         dest = (uint32_t) dest;
3330     }
3331     if (use_goto_tb(ctx, dest)) {
3332         tcg_gen_goto_tb(n);
3333         tcg_gen_movi_tl(cpu_nip, dest & ~3);
3334         tcg_gen_exit_tb((uintptr_t)ctx->tb + n);
3335     } else {
3336         tcg_gen_movi_tl(cpu_nip, dest & ~3);
3337         if (unlikely(ctx->singlestep_enabled)) {
3338             if ((ctx->singlestep_enabled &
3339                 (CPU_BRANCH_STEP | CPU_SINGLE_STEP)) &&
3340                 (ctx->exception == POWERPC_EXCP_BRANCH ||
3341                  ctx->exception == POWERPC_EXCP_TRACE)) {
3342                 gen_exception_nip(ctx, POWERPC_EXCP_TRACE, dest);
3343             }
3344             if (ctx->singlestep_enabled & GDBSTUB_SINGLE_STEP) {
3345                 gen_debug_exception(ctx);
3346             }
3347         }
3348         tcg_gen_exit_tb(0);
3349     }
3350 }
3351
3352 static inline void gen_setlr(DisasContext *ctx, target_ulong nip)
3353 {
3354     if (NARROW_MODE(ctx)) {
3355         nip = (uint32_t)nip;
3356     }
3357     tcg_gen_movi_tl(cpu_lr, nip);
3358 }
3359
3360 /* b ba bl bla */
3361 static void gen_b(DisasContext *ctx)
3362 {
3363     target_ulong li, target;
3364
3365     ctx->exception = POWERPC_EXCP_BRANCH;
3366     /* sign extend LI */
3367     li = LI(ctx->opcode);
3368     li = (li ^ 0x02000000) - 0x02000000;
3369     if (likely(AA(ctx->opcode) == 0)) {
3370         target = ctx->nip + li - 4;
3371     } else {
3372         target = li;
3373     }
3374     if (LK(ctx->opcode)) {
3375         gen_setlr(ctx, ctx->nip);
3376     }
3377     gen_update_cfar(ctx, ctx->nip - 4);
3378     gen_goto_tb(ctx, 0, target);
3379 }
3380
3381 #define BCOND_IM  0
3382 #define BCOND_LR  1
3383 #define BCOND_CTR 2
3384 #define BCOND_TAR 3
3385
3386 static inline void gen_bcond(DisasContext *ctx, int type)
3387 {
3388     uint32_t bo = BO(ctx->opcode);
3389     TCGLabel *l1;
3390     TCGv target;
3391
3392     ctx->exception = POWERPC_EXCP_BRANCH;
3393     if (type == BCOND_LR || type == BCOND_CTR || type == BCOND_TAR) {
3394         target = tcg_temp_local_new();
3395         if (type == BCOND_CTR)
3396             tcg_gen_mov_tl(target, cpu_ctr);
3397         else if (type == BCOND_TAR)
3398             gen_load_spr(target, SPR_TAR);
3399         else
3400             tcg_gen_mov_tl(target, cpu_lr);
3401     } else {
3402         TCGV_UNUSED(target);
3403     }
3404     if (LK(ctx->opcode))
3405         gen_setlr(ctx, ctx->nip);
3406     l1 = gen_new_label();
3407     if ((bo & 0x4) == 0) {
3408         /* Decrement and test CTR */
3409         TCGv temp = tcg_temp_new();
3410         if (unlikely(type == BCOND_CTR)) {
3411             gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
3412             return;
3413         }
3414         tcg_gen_subi_tl(cpu_ctr, cpu_ctr, 1);
3415         if (NARROW_MODE(ctx)) {
3416             tcg_gen_ext32u_tl(temp, cpu_ctr);
3417         } else {
3418             tcg_gen_mov_tl(temp, cpu_ctr);
3419         }
3420         if (bo & 0x2) {
3421             tcg_gen_brcondi_tl(TCG_COND_NE, temp, 0, l1);
3422         } else {
3423             tcg_gen_brcondi_tl(TCG_COND_EQ, temp, 0, l1);
3424         }
3425         tcg_temp_free(temp);
3426     }
3427     if ((bo & 0x10) == 0) {
3428         /* Test CR */
3429         uint32_t bi = BI(ctx->opcode);
3430         uint32_t mask = 0x08 >> (bi & 0x03);
3431         TCGv_i32 temp = tcg_temp_new_i32();
3432
3433         if (bo & 0x8) {
3434             tcg_gen_andi_i32(temp, cpu_crf[bi >> 2], mask);
3435             tcg_gen_brcondi_i32(TCG_COND_EQ, temp, 0, l1);
3436         } else {
3437             tcg_gen_andi_i32(temp, cpu_crf[bi >> 2], mask);
3438             tcg_gen_brcondi_i32(TCG_COND_NE, temp, 0, l1);
3439         }
3440         tcg_temp_free_i32(temp);
3441     }
3442     gen_update_cfar(ctx, ctx->nip - 4);
3443     if (type == BCOND_IM) {
3444         target_ulong li = (target_long)((int16_t)(BD(ctx->opcode)));
3445         if (likely(AA(ctx->opcode) == 0)) {
3446             gen_goto_tb(ctx, 0, ctx->nip + li - 4);
3447         } else {
3448             gen_goto_tb(ctx, 0, li);
3449         }
3450         if ((bo & 0x14) != 0x14) {
3451             gen_set_label(l1);
3452             gen_goto_tb(ctx, 1, ctx->nip);
3453         }
3454     } else {
3455         if (NARROW_MODE(ctx)) {
3456             tcg_gen_andi_tl(cpu_nip, target, (uint32_t)~3);
3457         } else {
3458             tcg_gen_andi_tl(cpu_nip, target, ~3);
3459         }
3460         tcg_gen_exit_tb(0);
3461         if ((bo & 0x14) != 0x14) {
3462             gen_set_label(l1);
3463             gen_update_nip(ctx, ctx->nip);
3464             tcg_gen_exit_tb(0);
3465         }
3466     }
3467     if (type == BCOND_LR || type == BCOND_CTR || type == BCOND_TAR) {
3468         tcg_temp_free(target);
3469     }
3470 }
3471
3472 static void gen_bc(DisasContext *ctx)
3473 {
3474     gen_bcond(ctx, BCOND_IM);
3475 }
3476
3477 static void gen_bcctr(DisasContext *ctx)
3478 {
3479     gen_bcond(ctx, BCOND_CTR);
3480 }
3481
3482 static void gen_bclr(DisasContext *ctx)
3483 {
3484     gen_bcond(ctx, BCOND_LR);
3485 }
3486
3487 static void gen_bctar(DisasContext *ctx)
3488 {
3489     gen_bcond(ctx, BCOND_TAR);
3490 }
3491
3492 /***                      Condition register logical                       ***/
3493 #define GEN_CRLOGIC(name, tcg_op, opc)                                        \
3494 static void glue(gen_, name)(DisasContext *ctx)                                       \
3495 {                                                                             \
3496     uint8_t bitmask;                                                          \
3497     int sh;                                                                   \
3498     TCGv_i32 t0, t1;                                                          \
3499     sh = (crbD(ctx->opcode) & 0x03) - (crbA(ctx->opcode) & 0x03);             \
3500     t0 = tcg_temp_new_i32();                                                  \
3501     if (sh > 0)                                                               \
3502         tcg_gen_shri_i32(t0, cpu_crf[crbA(ctx->opcode) >> 2], sh);            \
3503     else if (sh < 0)                                                          \
3504         tcg_gen_shli_i32(t0, cpu_crf[crbA(ctx->opcode) >> 2], -sh);           \
3505     else                                                                      \
3506         tcg_gen_mov_i32(t0, cpu_crf[crbA(ctx->opcode) >> 2]);                 \
3507     t1 = tcg_temp_new_i32();                                                  \
3508     sh = (crbD(ctx->opcode) & 0x03) - (crbB(ctx->opcode) & 0x03);             \
3509     if (sh > 0)                                                               \
3510         tcg_gen_shri_i32(t1, cpu_crf[crbB(ctx->opcode) >> 2], sh);            \
3511     else if (sh < 0)                                                          \
3512         tcg_gen_shli_i32(t1, cpu_crf[crbB(ctx->opcode) >> 2], -sh);           \
3513     else                                                                      \
3514         tcg_gen_mov_i32(t1, cpu_crf[crbB(ctx->opcode) >> 2]);                 \
3515     tcg_op(t0, t0, t1);                                                       \
3516     bitmask = 0x08 >> (crbD(ctx->opcode) & 0x03);                             \
3517     tcg_gen_andi_i32(t0, t0, bitmask);                                        \
3518     tcg_gen_andi_i32(t1, cpu_crf[crbD(ctx->opcode) >> 2], ~bitmask);          \
3519     tcg_gen_or_i32(cpu_crf[crbD(ctx->opcode) >> 2], t0, t1);                  \
3520     tcg_temp_free_i32(t0);                                                    \
3521     tcg_temp_free_i32(t1);                                                    \
3522 }
3523
3524 /* crand */
3525 GEN_CRLOGIC(crand, tcg_gen_and_i32, 0x08);
3526 /* crandc */
3527 GEN_CRLOGIC(crandc, tcg_gen_andc_i32, 0x04);
3528 /* creqv */
3529 GEN_CRLOGIC(creqv, tcg_gen_eqv_i32, 0x09);
3530 /* crnand */
3531 GEN_CRLOGIC(crnand, tcg_gen_nand_i32, 0x07);
3532 /* crnor */
3533 GEN_CRLOGIC(crnor, tcg_gen_nor_i32, 0x01);
3534 /* cror */
3535 GEN_CRLOGIC(cror, tcg_gen_or_i32, 0x0E);
3536 /* crorc */
3537 GEN_CRLOGIC(crorc, tcg_gen_orc_i32, 0x0D);
3538 /* crxor */
3539 GEN_CRLOGIC(crxor, tcg_gen_xor_i32, 0x06);
3540
3541 /* mcrf */
3542 static void gen_mcrf(DisasContext *ctx)
3543 {
3544     tcg_gen_mov_i32(cpu_crf[crfD(ctx->opcode)], cpu_crf[crfS(ctx->opcode)]);
3545 }
3546
3547 /***                           System linkage                              ***/
3548
3549 /* rfi (supervisor only) */
3550 static void gen_rfi(DisasContext *ctx)
3551 {
3552 #if defined(CONFIG_USER_ONLY)
3553     GEN_PRIV;
3554 #else
3555     /* This instruction doesn't exist anymore on 64-bit server
3556      * processors compliant with arch 2.x
3557      */
3558     if (ctx->insns_flags & PPC_SEGMENT_64B) {
3559         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
3560         return;
3561     }
3562     /* Restore CPU state */
3563     CHK_SV;
3564     gen_update_cfar(ctx, ctx->nip - 4);
3565     gen_helper_rfi(cpu_env);
3566     gen_sync_exception(ctx);
3567 #endif
3568 }
3569
3570 #if defined(TARGET_PPC64)
3571 static void gen_rfid(DisasContext *ctx)
3572 {
3573 #if defined(CONFIG_USER_ONLY)
3574     GEN_PRIV;
3575 #else
3576     /* Restore CPU state */
3577     CHK_SV;
3578     gen_update_cfar(ctx, ctx->nip - 4);
3579     gen_helper_rfid(cpu_env);
3580     gen_sync_exception(ctx);
3581 #endif
3582 }
3583
3584 static void gen_hrfid(DisasContext *ctx)
3585 {
3586 #if defined(CONFIG_USER_ONLY)
3587     GEN_PRIV;
3588 #else
3589     /* Restore CPU state */
3590     CHK_HV;
3591     gen_helper_hrfid(cpu_env);
3592     gen_sync_exception(ctx);
3593 #endif
3594 }
3595 #endif
3596
3597 /* sc */
3598 #if defined(CONFIG_USER_ONLY)
3599 #define POWERPC_SYSCALL POWERPC_EXCP_SYSCALL_USER
3600 #else
3601 #define POWERPC_SYSCALL POWERPC_EXCP_SYSCALL
3602 #endif
3603 static void gen_sc(DisasContext *ctx)
3604 {
3605     uint32_t lev;
3606
3607     lev = (ctx->opcode >> 5) & 0x7F;
3608     gen_exception_err(ctx, POWERPC_SYSCALL, lev);
3609 }
3610
3611 /***                                Trap                                   ***/
3612
3613 /* Check for unconditional traps (always or never) */
3614 static bool check_unconditional_trap(DisasContext *ctx)
3615 {
3616     /* Trap never */
3617     if (TO(ctx->opcode) == 0) {
3618         return true;
3619     }
3620     /* Trap always */
3621     if (TO(ctx->opcode) == 31) {
3622         gen_exception_err(ctx, POWERPC_EXCP_PROGRAM, POWERPC_EXCP_TRAP);
3623         return true;
3624     }
3625     return false;
3626 }
3627
3628 /* tw */
3629 static void gen_tw(DisasContext *ctx)
3630 {
3631     TCGv_i32 t0;
3632
3633     if (check_unconditional_trap(ctx)) {
3634         return;
3635     }
3636     t0 = tcg_const_i32(TO(ctx->opcode));
3637     gen_helper_tw(cpu_env, cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
3638                   t0);
3639     tcg_temp_free_i32(t0);
3640 }
3641
3642 /* twi */
3643 static void gen_twi(DisasContext *ctx)
3644 {
3645     TCGv t0;
3646     TCGv_i32 t1;
3647
3648     if (check_unconditional_trap(ctx)) {
3649         return;
3650     }
3651     t0 = tcg_const_tl(SIMM(ctx->opcode));
3652     t1 = tcg_const_i32(TO(ctx->opcode));
3653     gen_helper_tw(cpu_env, cpu_gpr[rA(ctx->opcode)], t0, t1);
3654     tcg_temp_free(t0);
3655     tcg_temp_free_i32(t1);
3656 }
3657
3658 #if defined(TARGET_PPC64)
3659 /* td */
3660 static void gen_td(DisasContext *ctx)
3661 {
3662     TCGv_i32 t0;
3663
3664     if (check_unconditional_trap(ctx)) {
3665         return;
3666     }
3667     t0 = tcg_const_i32(TO(ctx->opcode));
3668     gen_helper_td(cpu_env, cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
3669                   t0);
3670     tcg_temp_free_i32(t0);
3671 }
3672
3673 /* tdi */
3674 static void gen_tdi(DisasContext *ctx)
3675 {
3676     TCGv t0;
3677     TCGv_i32 t1;
3678
3679     if (check_unconditional_trap(ctx)) {
3680         return;
3681     }
3682     t0 = tcg_const_tl(SIMM(ctx->opcode));
3683     t1 = tcg_const_i32(TO(ctx->opcode));
3684     gen_helper_td(cpu_env, cpu_gpr[rA(ctx->opcode)], t0, t1);
3685     tcg_temp_free(t0);
3686     tcg_temp_free_i32(t1);
3687 }
3688 #endif
3689
3690 /***                          Processor control                            ***/
3691
3692 static void gen_read_xer(TCGv dst)
3693 {
3694     TCGv t0 = tcg_temp_new();
3695     TCGv t1 = tcg_temp_new();
3696     TCGv t2 = tcg_temp_new();
3697     tcg_gen_mov_tl(dst, cpu_xer);
3698     tcg_gen_shli_tl(t0, cpu_so, XER_SO);
3699     tcg_gen_shli_tl(t1, cpu_ov, XER_OV);
3700     tcg_gen_shli_tl(t2, cpu_ca, XER_CA);
3701     tcg_gen_or_tl(t0, t0, t1);
3702     tcg_gen_or_tl(dst, dst, t2);
3703     tcg_gen_or_tl(dst, dst, t0);
3704     tcg_temp_free(t0);
3705     tcg_temp_free(t1);
3706     tcg_temp_free(t2);
3707 }
3708
3709 static void gen_write_xer(TCGv src)
3710 {
3711     tcg_gen_andi_tl(cpu_xer, src,
3712                     ~((1u << XER_SO) | (1u << XER_OV) | (1u << XER_CA)));
3713     tcg_gen_shri_tl(cpu_so, src, XER_SO);
3714     tcg_gen_shri_tl(cpu_ov, src, XER_OV);
3715     tcg_gen_shri_tl(cpu_ca, src, XER_CA);
3716     tcg_gen_andi_tl(cpu_so, cpu_so, 1);
3717     tcg_gen_andi_tl(cpu_ov, cpu_ov, 1);
3718     tcg_gen_andi_tl(cpu_ca, cpu_ca, 1);
3719 }
3720
3721 /* mcrxr */
3722 static void gen_mcrxr(DisasContext *ctx)
3723 {
3724     TCGv_i32 t0 = tcg_temp_new_i32();
3725     TCGv_i32 t1 = tcg_temp_new_i32();
3726     TCGv_i32 dst = cpu_crf[crfD(ctx->opcode)];
3727
3728     tcg_gen_trunc_tl_i32(t0, cpu_so);
3729     tcg_gen_trunc_tl_i32(t1, cpu_ov);
3730     tcg_gen_trunc_tl_i32(dst, cpu_ca);
3731     tcg_gen_shli_i32(t0, t0, 3);
3732     tcg_gen_shli_i32(t1, t1, 2);
3733     tcg_gen_shli_i32(dst, dst, 1);
3734     tcg_gen_or_i32(dst, dst, t0);
3735     tcg_gen_or_i32(dst, dst, t1);
3736     tcg_temp_free_i32(t0);
3737     tcg_temp_free_i32(t1);
3738
3739     tcg_gen_movi_tl(cpu_so, 0);
3740     tcg_gen_movi_tl(cpu_ov, 0);
3741     tcg_gen_movi_tl(cpu_ca, 0);
3742 }
3743
3744 /* mfcr mfocrf */
3745 static void gen_mfcr(DisasContext *ctx)
3746 {
3747     uint32_t crm, crn;
3748
3749     if (likely(ctx->opcode & 0x00100000)) {
3750         crm = CRM(ctx->opcode);
3751         if (likely(crm && ((crm & (crm - 1)) == 0))) {
3752             crn = ctz32 (crm);
3753             tcg_gen_extu_i32_tl(cpu_gpr[rD(ctx->opcode)], cpu_crf[7 - crn]);
3754             tcg_gen_shli_tl(cpu_gpr[rD(ctx->opcode)],
3755                             cpu_gpr[rD(ctx->opcode)], crn * 4);
3756         }
3757     } else {
3758         TCGv_i32 t0 = tcg_temp_new_i32();
3759         tcg_gen_mov_i32(t0, cpu_crf[0]);
3760         tcg_gen_shli_i32(t0, t0, 4);
3761         tcg_gen_or_i32(t0, t0, cpu_crf[1]);
3762         tcg_gen_shli_i32(t0, t0, 4);
3763         tcg_gen_or_i32(t0, t0, cpu_crf[2]);
3764         tcg_gen_shli_i32(t0, t0, 4);
3765         tcg_gen_or_i32(t0, t0, cpu_crf[3]);
3766         tcg_gen_shli_i32(t0, t0, 4);
3767         tcg_gen_or_i32(t0, t0, cpu_crf[4]);
3768         tcg_gen_shli_i32(t0, t0, 4);
3769         tcg_gen_or_i32(t0, t0, cpu_crf[5]);
3770         tcg_gen_shli_i32(t0, t0, 4);
3771         tcg_gen_or_i32(t0, t0, cpu_crf[6]);
3772         tcg_gen_shli_i32(t0, t0, 4);
3773         tcg_gen_or_i32(t0, t0, cpu_crf[7]);
3774         tcg_gen_extu_i32_tl(cpu_gpr[rD(ctx->opcode)], t0);
3775         tcg_temp_free_i32(t0);
3776     }
3777 }
3778
3779 /* mfmsr */
3780 static void gen_mfmsr(DisasContext *ctx)
3781 {
3782     CHK_SV;
3783     tcg_gen_mov_tl(cpu_gpr[rD(ctx->opcode)], cpu_msr);
3784 }
3785
3786 static void spr_noaccess(DisasContext *ctx, int gprn, int sprn)
3787 {
3788 #if 0
3789     sprn = ((sprn >> 5) & 0x1F) | ((sprn & 0x1F) << 5);
3790     printf("ERROR: try to access SPR %d !\n", sprn);
3791 #endif
3792 }
3793 #define SPR_NOACCESS (&spr_noaccess)
3794
3795 /* mfspr */
3796 static inline void gen_op_mfspr(DisasContext *ctx)
3797 {
3798     void (*read_cb)(DisasContext *ctx, int gprn, int sprn);
3799     uint32_t sprn = SPR(ctx->opcode);
3800
3801 #if defined(CONFIG_USER_ONLY)
3802     read_cb = ctx->spr_cb[sprn].uea_read;
3803 #else
3804     if (ctx->pr) {
3805         read_cb = ctx->spr_cb[sprn].uea_read;
3806     } else if (ctx->hv) {
3807         read_cb = ctx->spr_cb[sprn].hea_read;
3808     } else {
3809         read_cb = ctx->spr_cb[sprn].oea_read;
3810     }
3811 #endif
3812     if (likely(read_cb != NULL)) {
3813         if (likely(read_cb != SPR_NOACCESS)) {
3814             (*read_cb)(ctx, rD(ctx->opcode), sprn);
3815         } else {
3816             /* Privilege exception */
3817             /* This is a hack to avoid warnings when running Linux:
3818              * this OS breaks the PowerPC virtualisation model,
3819              * allowing userland application to read the PVR
3820              */
3821             if (sprn != SPR_PVR) {
3822                 fprintf(stderr, "Trying to read privileged spr %d (0x%03x) at "
3823                         TARGET_FMT_lx "\n", sprn, sprn, ctx->nip - 4);
3824                 if (qemu_log_separate()) {
3825                     qemu_log("Trying to read privileged spr %d (0x%03x) at "
3826                              TARGET_FMT_lx "\n", sprn, sprn, ctx->nip - 4);
3827                 }
3828             }
3829             gen_priv_exception(ctx, POWERPC_EXCP_PRIV_REG);
3830         }
3831     } else {
3832         /* ISA 2.07 defines these as no-ops */
3833         if ((ctx->insns_flags2 & PPC2_ISA207S) &&
3834             (sprn >= 808 && sprn <= 811)) {
3835             /* This is a nop */
3836             return;
3837         }
3838         /* Not defined */
3839         fprintf(stderr, "Trying to read invalid spr %d (0x%03x) at "
3840                 TARGET_FMT_lx "\n", sprn, sprn, ctx->nip - 4);
3841         if (qemu_log_separate()) {
3842             qemu_log("Trying to read invalid spr %d (0x%03x) at "
3843                      TARGET_FMT_lx "\n", sprn, sprn, ctx->nip - 4);
3844         }
3845
3846         /* The behaviour depends on MSR:PR and SPR# bit 0x10,
3847          * it can generate a priv, a hv emu or a no-op
3848          */
3849         if (sprn & 0x10) {
3850             if (ctx->pr) {
3851                 gen_priv_exception(ctx, POWERPC_EXCP_INVAL_SPR);
3852             }
3853         } else {
3854             if (ctx->pr || sprn == 0 || sprn == 4 || sprn == 5 || sprn == 6) {
3855                 gen_hvpriv_exception(ctx, POWERPC_EXCP_INVAL_SPR);
3856             }
3857         }
3858     }
3859 }
3860
3861 static void gen_mfspr(DisasContext *ctx)
3862 {
3863     gen_op_mfspr(ctx);
3864 }
3865
3866 /* mftb */
3867 static void gen_mftb(DisasContext *ctx)
3868 {
3869     gen_op_mfspr(ctx);
3870 }
3871
3872 /* mtcrf mtocrf*/
3873 static void gen_mtcrf(DisasContext *ctx)
3874 {
3875     uint32_t crm, crn;
3876
3877     crm = CRM(ctx->opcode);
3878     if (likely((ctx->opcode & 0x00100000))) {
3879         if (crm && ((crm & (crm - 1)) == 0)) {
3880             TCGv_i32 temp = tcg_temp_new_i32();
3881             crn = ctz32 (crm);
3882             tcg_gen_trunc_tl_i32(temp, cpu_gpr[rS(ctx->opcode)]);
3883             tcg_gen_shri_i32(temp, temp, crn * 4);
3884             tcg_gen_andi_i32(cpu_crf[7 - crn], temp, 0xf);
3885             tcg_temp_free_i32(temp);
3886         }
3887     } else {
3888         TCGv_i32 temp = tcg_temp_new_i32();
3889         tcg_gen_trunc_tl_i32(temp, cpu_gpr[rS(ctx->opcode)]);
3890         for (crn = 0 ; crn < 8 ; crn++) {
3891             if (crm & (1 << crn)) {
3892                     tcg_gen_shri_i32(cpu_crf[7 - crn], temp, crn * 4);
3893                     tcg_gen_andi_i32(cpu_crf[7 - crn], cpu_crf[7 - crn], 0xf);
3894             }
3895         }
3896         tcg_temp_free_i32(temp);
3897     }
3898 }
3899
3900 /* mtmsr */
3901 #if defined(TARGET_PPC64)
3902 static void gen_mtmsrd(DisasContext *ctx)
3903 {
3904     CHK_SV;
3905
3906 #if !defined(CONFIG_USER_ONLY)
3907     if (ctx->opcode & 0x00010000) {
3908         /* Special form that does not need any synchronisation */
3909         TCGv t0 = tcg_temp_new();
3910         tcg_gen_andi_tl(t0, cpu_gpr[rS(ctx->opcode)], (1 << MSR_RI) | (1 << MSR_EE));
3911         tcg_gen_andi_tl(cpu_msr, cpu_msr, ~(target_ulong)((1 << MSR_RI) | (1 << MSR_EE)));
3912         tcg_gen_or_tl(cpu_msr, cpu_msr, t0);
3913         tcg_temp_free(t0);
3914     } else {
3915         /* XXX: we need to update nip before the store
3916          *      if we enter power saving mode, we will exit the loop
3917          *      directly from ppc_store_msr
3918          */
3919         gen_update_nip(ctx, ctx->nip);
3920         gen_helper_store_msr(cpu_env, cpu_gpr[rS(ctx->opcode)]);
3921         /* Must stop the translation as machine state (may have) changed */
3922         /* Note that mtmsr is not always defined as context-synchronizing */
3923         gen_stop_exception(ctx);
3924     }
3925 #endif /* !defined(CONFIG_USER_ONLY) */
3926 }
3927 #endif /* defined(TARGET_PPC64) */
3928
3929 static void gen_mtmsr(DisasContext *ctx)
3930 {
3931     CHK_SV;
3932
3933 #if !defined(CONFIG_USER_ONLY)
3934    if (ctx->opcode & 0x00010000) {
3935         /* Special form that does not need any synchronisation */
3936         TCGv t0 = tcg_temp_new();
3937         tcg_gen_andi_tl(t0, cpu_gpr[rS(ctx->opcode)], (1 << MSR_RI) | (1 << MSR_EE));
3938         tcg_gen_andi_tl(cpu_msr, cpu_msr, ~(target_ulong)((1 << MSR_RI) | (1 << MSR_EE)));
3939         tcg_gen_or_tl(cpu_msr, cpu_msr, t0);
3940         tcg_temp_free(t0);
3941     } else {
3942         TCGv msr = tcg_temp_new();
3943
3944         /* XXX: we need to update nip before the store
3945          *      if we enter power saving mode, we will exit the loop
3946          *      directly from ppc_store_msr
3947          */
3948         gen_update_nip(ctx, ctx->nip);
3949 #if defined(TARGET_PPC64)
3950         tcg_gen_deposit_tl(msr, cpu_msr, cpu_gpr[rS(ctx->opcode)], 0, 32);
3951 #else
3952         tcg_gen_mov_tl(msr, cpu_gpr[rS(ctx->opcode)]);
3953 #endif
3954         gen_helper_store_msr(cpu_env, msr);
3955         tcg_temp_free(msr);
3956         /* Must stop the translation as machine state (may have) changed */
3957         /* Note that mtmsr is not always defined as context-synchronizing */
3958         gen_stop_exception(ctx);
3959     }
3960 #endif
3961 }
3962
3963 /* mtspr */
3964 static void gen_mtspr(DisasContext *ctx)
3965 {
3966     void (*write_cb)(DisasContext *ctx, int sprn, int gprn);
3967     uint32_t sprn = SPR(ctx->opcode);
3968
3969 #if defined(CONFIG_USER_ONLY)
3970     write_cb = ctx->spr_cb[sprn].uea_write;
3971 #else
3972     if (ctx->pr) {
3973         write_cb = ctx->spr_cb[sprn].uea_write;
3974     } else if (ctx->hv) {
3975         write_cb = ctx->spr_cb[sprn].hea_write;
3976     } else {
3977         write_cb = ctx->spr_cb[sprn].oea_write;
3978     }
3979 #endif
3980     if (likely(write_cb != NULL)) {
3981         if (likely(write_cb != SPR_NOACCESS)) {
3982             (*write_cb)(ctx, sprn, rS(ctx->opcode));
3983         } else {
3984             /* Privilege exception */
3985             fprintf(stderr, "Trying to write privileged spr %d (0x%03x) at "
3986                     TARGET_FMT_lx "\n", sprn, sprn, ctx->nip - 4);
3987             if (qemu_log_separate()) {
3988                 qemu_log("Trying to write privileged spr %d (0x%03x) at "
3989                          TARGET_FMT_lx "\n", sprn, sprn, ctx->nip - 4);
3990             }
3991             gen_priv_exception(ctx, POWERPC_EXCP_PRIV_REG);
3992         }
3993     } else {
3994         /* ISA 2.07 defines these as no-ops */
3995         if ((ctx->insns_flags2 & PPC2_ISA207S) &&
3996             (sprn >= 808 && sprn <= 811)) {
3997             /* This is a nop */
3998             return;
3999         }
4000
4001         /* Not defined */
4002         if (qemu_log_separate()) {
4003             qemu_log("Trying to write invalid spr %d (0x%03x) at "
4004                      TARGET_FMT_lx "\n", sprn, sprn, ctx->nip - 4);
4005         }
4006         fprintf(stderr, "Trying to write invalid spr %d (0x%03x) at "
4007                 TARGET_FMT_lx "\n", sprn, sprn, ctx->nip - 4);
4008
4009
4010         /* The behaviour depends on MSR:PR and SPR# bit 0x10,
4011          * it can generate a priv, a hv emu or a no-op
4012          */
4013         if (sprn & 0x10) {
4014             if (ctx->pr) {
4015                 gen_priv_exception(ctx, POWERPC_EXCP_INVAL_SPR);
4016             }
4017         } else {
4018             if (ctx->pr || sprn == 0) {
4019                 gen_hvpriv_exception(ctx, POWERPC_EXCP_INVAL_SPR);
4020             }
4021         }
4022     }
4023 }
4024
4025 #if defined(TARGET_PPC64)
4026 /* setb */
4027 static void gen_setb(DisasContext *ctx)
4028 {
4029     TCGv_i32 t0 = tcg_temp_new_i32();
4030     TCGv_i32 t8 = tcg_temp_new_i32();
4031     TCGv_i32 tm1 = tcg_temp_new_i32();
4032     int crf = crfS(ctx->opcode);
4033
4034     tcg_gen_setcondi_i32(TCG_COND_GEU, t0, cpu_crf[crf], 4);
4035     tcg_gen_movi_i32(t8, 8);
4036     tcg_gen_movi_i32(tm1, -1);
4037     tcg_gen_movcond_i32(TCG_COND_GEU, t0, cpu_crf[crf], t8, tm1, t0);
4038     tcg_gen_ext_i32_tl(cpu_gpr[rD(ctx->opcode)], t0);
4039
4040     tcg_temp_free_i32(t0);
4041     tcg_temp_free_i32(t8);
4042     tcg_temp_free_i32(tm1);
4043 }
4044 #endif
4045
4046 /***                         Cache management                              ***/
4047
4048 /* dcbf */
4049 static void gen_dcbf(DisasContext *ctx)
4050 {
4051     /* XXX: specification says this is treated as a load by the MMU */
4052     TCGv t0;
4053     gen_set_access_type(ctx, ACCESS_CACHE);
4054     t0 = tcg_temp_new();
4055     gen_addr_reg_index(ctx, t0);
4056     gen_qemu_ld8u(ctx, t0, t0);
4057     tcg_temp_free(t0);
4058 }
4059
4060 /* dcbi (Supervisor only) */
4061 static void gen_dcbi(DisasContext *ctx)
4062 {
4063 #if defined(CONFIG_USER_ONLY)
4064     GEN_PRIV;
4065 #else
4066     TCGv EA, val;
4067
4068     CHK_SV;
4069     EA = tcg_temp_new();
4070     gen_set_access_type(ctx, ACCESS_CACHE);
4071     gen_addr_reg_index(ctx, EA);
4072     val = tcg_temp_new();
4073     /* XXX: specification says this should be treated as a store by the MMU */
4074     gen_qemu_ld8u(ctx, val, EA);
4075     gen_qemu_st8(ctx, val, EA);
4076     tcg_temp_free(val);
4077     tcg_temp_free(EA);
4078 #endif /* defined(CONFIG_USER_ONLY) */
4079 }
4080
4081 /* dcdst */
4082 static void gen_dcbst(DisasContext *ctx)
4083 {
4084     /* XXX: specification say this is treated as a load by the MMU */
4085     TCGv t0;
4086     gen_set_access_type(ctx, ACCESS_CACHE);
4087     t0 = tcg_temp_new();
4088     gen_addr_reg_index(ctx, t0);
4089     gen_qemu_ld8u(ctx, t0, t0);
4090     tcg_temp_free(t0);
4091 }
4092
4093 /* dcbt */
4094 static void gen_dcbt(DisasContext *ctx)
4095 {
4096     /* interpreted as no-op */
4097     /* XXX: specification say this is treated as a load by the MMU
4098      *      but does not generate any exception
4099      */
4100 }
4101
4102 /* dcbtst */
4103 static void gen_dcbtst(DisasContext *ctx)
4104 {
4105     /* interpreted as no-op */
4106     /* XXX: specification say this is treated as a load by the MMU
4107      *      but does not generate any exception
4108      */
4109 }
4110
4111 /* dcbtls */
4112 static void gen_dcbtls(DisasContext *ctx)
4113 {
4114     /* Always fails locking the cache */
4115     TCGv t0 = tcg_temp_new();
4116     gen_load_spr(t0, SPR_Exxx_L1CSR0);
4117     tcg_gen_ori_tl(t0, t0, L1CSR0_CUL);
4118     gen_store_spr(SPR_Exxx_L1CSR0, t0);
4119     tcg_temp_free(t0);
4120 }
4121
4122 /* dcbz */
4123 static void gen_dcbz(DisasContext *ctx)
4124 {
4125     TCGv tcgv_addr;
4126     TCGv_i32 tcgv_op;
4127
4128     gen_set_access_type(ctx, ACCESS_CACHE);
4129     tcgv_addr = tcg_temp_new();
4130     tcgv_op = tcg_const_i32(ctx->opcode & 0x03FF000);
4131     gen_addr_reg_index(ctx, tcgv_addr);
4132     gen_helper_dcbz(cpu_env, tcgv_addr, tcgv_op);
4133     tcg_temp_free(tcgv_addr);
4134     tcg_temp_free_i32(tcgv_op);
4135 }
4136
4137 /* dst / dstt */
4138 static void gen_dst(DisasContext *ctx)
4139 {
4140     if (rA(ctx->opcode) == 0) {
4141         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
4142     } else {
4143         /* interpreted as no-op */
4144     }
4145 }
4146
4147 /* dstst /dststt */
4148 static void gen_dstst(DisasContext *ctx)
4149 {
4150     if (rA(ctx->opcode) == 0) {
4151         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
4152     } else {
4153         /* interpreted as no-op */
4154     }
4155
4156 }
4157
4158 /* dss / dssall */
4159 static void gen_dss(DisasContext *ctx)
4160 {
4161     /* interpreted as no-op */
4162 }
4163
4164 /* icbi */
4165 static void gen_icbi(DisasContext *ctx)
4166 {
4167     TCGv t0;
4168     gen_set_access_type(ctx, ACCESS_CACHE);
4169     t0 = tcg_temp_new();
4170     gen_addr_reg_index(ctx, t0);
4171     gen_helper_icbi(cpu_env, t0);
4172     tcg_temp_free(t0);
4173 }
4174
4175 /* Optional: */
4176 /* dcba */
4177 static void gen_dcba(DisasContext *ctx)
4178 {
4179     /* interpreted as no-op */
4180     /* XXX: specification say this is treated as a store by the MMU
4181      *      but does not generate any exception
4182      */
4183 }
4184
4185 /***                    Segment register manipulation                      ***/
4186 /* Supervisor only: */
4187
4188 /* mfsr */
4189 static void gen_mfsr(DisasContext *ctx)
4190 {
4191 #if defined(CONFIG_USER_ONLY)
4192     GEN_PRIV;
4193 #else
4194     TCGv t0;
4195
4196     CHK_SV;
4197     t0 = tcg_const_tl(SR(ctx->opcode));
4198     gen_helper_load_sr(cpu_gpr[rD(ctx->opcode)], cpu_env, t0);
4199     tcg_temp_free(t0);
4200 #endif /* defined(CONFIG_USER_ONLY) */
4201 }
4202
4203 /* mfsrin */
4204 static void gen_mfsrin(DisasContext *ctx)
4205 {
4206 #if defined(CONFIG_USER_ONLY)
4207     GEN_PRIV;
4208 #else
4209     TCGv t0;
4210
4211     CHK_SV;
4212     t0 = tcg_temp_new();
4213     tcg_gen_shri_tl(t0, cpu_gpr[rB(ctx->opcode)], 28);
4214     tcg_gen_andi_tl(t0, t0, 0xF);
4215     gen_helper_load_sr(cpu_gpr[rD(ctx->opcode)], cpu_env, t0);
4216     tcg_temp_free(t0);
4217 #endif /* defined(CONFIG_USER_ONLY) */
4218 }
4219
4220 /* mtsr */
4221 static void gen_mtsr(DisasContext *ctx)
4222 {
4223 #if defined(CONFIG_USER_ONLY)
4224     GEN_PRIV;
4225 #else
4226     TCGv t0;
4227
4228     CHK_SV;
4229     t0 = tcg_const_tl(SR(ctx->opcode));
4230     gen_helper_store_sr(cpu_env, t0, cpu_gpr[rS(ctx->opcode)]);
4231     tcg_temp_free(t0);
4232 #endif /* defined(CONFIG_USER_ONLY) */
4233 }
4234
4235 /* mtsrin */
4236 static void gen_mtsrin(DisasContext *ctx)
4237 {
4238 #if defined(CONFIG_USER_ONLY)
4239     GEN_PRIV;
4240 #else
4241     TCGv t0;
4242     CHK_SV;
4243
4244     t0 = tcg_temp_new();
4245     tcg_gen_shri_tl(t0, cpu_gpr[rB(ctx->opcode)], 28);
4246     tcg_gen_andi_tl(t0, t0, 0xF);
4247     gen_helper_store_sr(cpu_env, t0, cpu_gpr[rD(ctx->opcode)]);
4248     tcg_temp_free(t0);
4249 #endif /* defined(CONFIG_USER_ONLY) */
4250 }
4251
4252 #if defined(TARGET_PPC64)
4253 /* Specific implementation for PowerPC 64 "bridge" emulation using SLB */
4254
4255 /* mfsr */
4256 static void gen_mfsr_64b(DisasContext *ctx)
4257 {
4258 #if defined(CONFIG_USER_ONLY)
4259     GEN_PRIV;
4260 #else
4261     TCGv t0;
4262
4263     CHK_SV;
4264     t0 = tcg_const_tl(SR(ctx->opcode));
4265     gen_helper_load_sr(cpu_gpr[rD(ctx->opcode)], cpu_env, t0);
4266     tcg_temp_free(t0);
4267 #endif /* defined(CONFIG_USER_ONLY) */
4268 }
4269
4270 /* mfsrin */
4271 static void gen_mfsrin_64b(DisasContext *ctx)
4272 {
4273 #if defined(CONFIG_USER_ONLY)
4274     GEN_PRIV;
4275 #else
4276     TCGv t0;
4277
4278     CHK_SV;
4279     t0 = tcg_temp_new();
4280     tcg_gen_shri_tl(t0, cpu_gpr[rB(ctx->opcode)], 28);
4281     tcg_gen_andi_tl(t0, t0, 0xF);
4282     gen_helper_load_sr(cpu_gpr[rD(ctx->opcode)], cpu_env, t0);
4283     tcg_temp_free(t0);
4284 #endif /* defined(CONFIG_USER_ONLY) */
4285 }
4286
4287 /* mtsr */
4288 static void gen_mtsr_64b(DisasContext *ctx)
4289 {
4290 #if defined(CONFIG_USER_ONLY)
4291     GEN_PRIV;
4292 #else
4293     TCGv t0;
4294
4295     CHK_SV;
4296     t0 = tcg_const_tl(SR(ctx->opcode));
4297     gen_helper_store_sr(cpu_env, t0, cpu_gpr[rS(ctx->opcode)]);
4298     tcg_temp_free(t0);
4299 #endif /* defined(CONFIG_USER_ONLY) */
4300 }
4301
4302 /* mtsrin */
4303 static void gen_mtsrin_64b(DisasContext *ctx)
4304 {
4305 #if defined(CONFIG_USER_ONLY)
4306     GEN_PRIV;
4307 #else
4308     TCGv t0;
4309
4310     CHK_SV;
4311     t0 = tcg_temp_new();
4312     tcg_gen_shri_tl(t0, cpu_gpr[rB(ctx->opcode)], 28);
4313     tcg_gen_andi_tl(t0, t0, 0xF);
4314     gen_helper_store_sr(cpu_env, t0, cpu_gpr[rS(ctx->opcode)]);
4315     tcg_temp_free(t0);
4316 #endif /* defined(CONFIG_USER_ONLY) */
4317 }
4318
4319 /* slbmte */
4320 static void gen_slbmte(DisasContext *ctx)
4321 {
4322 #if defined(CONFIG_USER_ONLY)
4323     GEN_PRIV;
4324 #else
4325     CHK_SV;
4326
4327     gen_helper_store_slb(cpu_env, cpu_gpr[rB(ctx->opcode)],
4328                          cpu_gpr[rS(ctx->opcode)]);
4329 #endif /* defined(CONFIG_USER_ONLY) */
4330 }
4331
4332 static void gen_slbmfee(DisasContext *ctx)
4333 {
4334 #if defined(CONFIG_USER_ONLY)
4335     GEN_PRIV;
4336 #else
4337     CHK_SV;
4338
4339     gen_helper_load_slb_esid(cpu_gpr[rS(ctx->opcode)], cpu_env,
4340                              cpu_gpr[rB(ctx->opcode)]);
4341 #endif /* defined(CONFIG_USER_ONLY) */
4342 }
4343
4344 static void gen_slbmfev(DisasContext *ctx)
4345 {
4346 #if defined(CONFIG_USER_ONLY)
4347     GEN_PRIV;
4348 #else
4349     CHK_SV;
4350
4351     gen_helper_load_slb_vsid(cpu_gpr[rS(ctx->opcode)], cpu_env,
4352                              cpu_gpr[rB(ctx->opcode)]);
4353 #endif /* defined(CONFIG_USER_ONLY) */
4354 }
4355
4356 static void gen_slbfee_(DisasContext *ctx)
4357 {
4358 #if defined(CONFIG_USER_ONLY)
4359     gen_inval_exception(ctx, POWERPC_EXCP_PRIV_REG);
4360 #else
4361     TCGLabel *l1, *l2;
4362
4363     if (unlikely(ctx->pr)) {
4364         gen_inval_exception(ctx, POWERPC_EXCP_PRIV_REG);
4365         return;
4366     }
4367     gen_helper_find_slb_vsid(cpu_gpr[rS(ctx->opcode)], cpu_env,
4368                              cpu_gpr[rB(ctx->opcode)]);
4369     l1 = gen_new_label();
4370     l2 = gen_new_label();
4371     tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_so);
4372     tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[rS(ctx->opcode)], -1, l1);
4373     tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 1 << CRF_EQ);
4374     tcg_gen_br(l2);
4375     gen_set_label(l1);
4376     tcg_gen_movi_tl(cpu_gpr[rS(ctx->opcode)], 0);
4377     gen_set_label(l2);
4378 #endif
4379 }
4380 #endif /* defined(TARGET_PPC64) */
4381
4382 /***                      Lookaside buffer management                      ***/
4383 /* Optional & supervisor only: */
4384
4385 /* tlbia */
4386 static void gen_tlbia(DisasContext *ctx)
4387 {
4388 #if defined(CONFIG_USER_ONLY)
4389     GEN_PRIV;
4390 #else
4391     CHK_HV;
4392
4393     gen_helper_tlbia(cpu_env);
4394 #endif  /* defined(CONFIG_USER_ONLY) */
4395 }
4396
4397 /* tlbiel */
4398 static void gen_tlbiel(DisasContext *ctx)
4399 {
4400 #if defined(CONFIG_USER_ONLY)
4401     GEN_PRIV;
4402 #else
4403     CHK_SV;
4404
4405     gen_helper_tlbie(cpu_env, cpu_gpr[rB(ctx->opcode)]);
4406 #endif /* defined(CONFIG_USER_ONLY) */
4407 }
4408
4409 /* tlbie */
4410 static void gen_tlbie(DisasContext *ctx)
4411 {
4412 #if defined(CONFIG_USER_ONLY)
4413     GEN_PRIV;
4414 #else
4415     CHK_HV;
4416
4417     if (NARROW_MODE(ctx)) {
4418         TCGv t0 = tcg_temp_new();
4419         tcg_gen_ext32u_tl(t0, cpu_gpr[rB(ctx->opcode)]);
4420         gen_helper_tlbie(cpu_env, t0);
4421         tcg_temp_free(t0);
4422     } else {
4423         gen_helper_tlbie(cpu_env, cpu_gpr[rB(ctx->opcode)]);
4424     }
4425 #endif /* defined(CONFIG_USER_ONLY) */
4426 }
4427
4428 /* tlbsync */
4429 static void gen_tlbsync(DisasContext *ctx)
4430 {
4431 #if defined(CONFIG_USER_ONLY)
4432     GEN_PRIV;
4433 #else
4434     CHK_HV;
4435
4436     /* tlbsync is a nop for server, ptesync handles delayed tlb flush,
4437      * embedded however needs to deal with tlbsync. We don't try to be
4438      * fancy and swallow the overhead of checking for both.
4439      */
4440     gen_check_tlb_flush(ctx);
4441 #endif /* defined(CONFIG_USER_ONLY) */
4442 }
4443
4444 #if defined(TARGET_PPC64)
4445 /* slbia */
4446 static void gen_slbia(DisasContext *ctx)
4447 {
4448 #if defined(CONFIG_USER_ONLY)
4449     GEN_PRIV;
4450 #else
4451     CHK_SV;
4452
4453     gen_helper_slbia(cpu_env);
4454 #endif /* defined(CONFIG_USER_ONLY) */
4455 }
4456
4457 /* slbie */
4458 static void gen_slbie(DisasContext *ctx)
4459 {
4460 #if defined(CONFIG_USER_ONLY)
4461     GEN_PRIV;
4462 #else
4463     CHK_SV;
4464
4465     gen_helper_slbie(cpu_env, cpu_gpr[rB(ctx->opcode)]);
4466 #endif /* defined(CONFIG_USER_ONLY) */
4467 }
4468 #endif  /* defined(TARGET_PPC64) */
4469
4470 /***                              External control                         ***/
4471 /* Optional: */
4472
4473 /* eciwx */
4474 static void gen_eciwx(DisasContext *ctx)
4475 {
4476     TCGv t0;
4477     /* Should check EAR[E] ! */
4478     gen_set_access_type(ctx, ACCESS_EXT);
4479     t0 = tcg_temp_new();
4480     gen_addr_reg_index(ctx, t0);
4481     gen_check_align(ctx, t0, 0x03);
4482     gen_qemu_ld32u(ctx, cpu_gpr[rD(ctx->opcode)], t0);
4483     tcg_temp_free(t0);
4484 }
4485
4486 /* ecowx */
4487 static void gen_ecowx(DisasContext *ctx)
4488 {
4489     TCGv t0;
4490     /* Should check EAR[E] ! */
4491     gen_set_access_type(ctx, ACCESS_EXT);
4492     t0 = tcg_temp_new();
4493     gen_addr_reg_index(ctx, t0);
4494     gen_check_align(ctx, t0, 0x03);
4495     gen_qemu_st32(ctx, cpu_gpr[rD(ctx->opcode)], t0);
4496     tcg_temp_free(t0);
4497 }
4498
4499 /* PowerPC 601 specific instructions */
4500
4501 /* abs - abs. */
4502 static void gen_abs(DisasContext *ctx)
4503 {
4504     TCGLabel *l1 = gen_new_label();
4505     TCGLabel *l2 = gen_new_label();
4506     tcg_gen_brcondi_tl(TCG_COND_GE, cpu_gpr[rA(ctx->opcode)], 0, l1);
4507     tcg_gen_neg_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4508     tcg_gen_br(l2);
4509     gen_set_label(l1);
4510     tcg_gen_mov_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4511     gen_set_label(l2);
4512     if (unlikely(Rc(ctx->opcode) != 0))
4513         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4514 }
4515
4516 /* abso - abso. */
4517 static void gen_abso(DisasContext *ctx)
4518 {
4519     TCGLabel *l1 = gen_new_label();
4520     TCGLabel *l2 = gen_new_label();
4521     TCGLabel *l3 = gen_new_label();
4522     /* Start with XER OV disabled, the most likely case */
4523     tcg_gen_movi_tl(cpu_ov, 0);
4524     tcg_gen_brcondi_tl(TCG_COND_GE, cpu_gpr[rA(ctx->opcode)], 0, l2);
4525     tcg_gen_brcondi_tl(TCG_COND_NE, cpu_gpr[rA(ctx->opcode)], 0x80000000, l1);
4526     tcg_gen_movi_tl(cpu_ov, 1);
4527     tcg_gen_movi_tl(cpu_so, 1);
4528     tcg_gen_br(l2);
4529     gen_set_label(l1);
4530     tcg_gen_neg_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4531     tcg_gen_br(l3);
4532     gen_set_label(l2);
4533     tcg_gen_mov_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4534     gen_set_label(l3);
4535     if (unlikely(Rc(ctx->opcode) != 0))
4536         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4537 }
4538
4539 /* clcs */
4540 static void gen_clcs(DisasContext *ctx)
4541 {
4542     TCGv_i32 t0 = tcg_const_i32(rA(ctx->opcode));
4543     gen_helper_clcs(cpu_gpr[rD(ctx->opcode)], cpu_env, t0);
4544     tcg_temp_free_i32(t0);
4545     /* Rc=1 sets CR0 to an undefined state */
4546 }
4547
4548 /* div - div. */
4549 static void gen_div(DisasContext *ctx)
4550 {
4551     gen_helper_div(cpu_gpr[rD(ctx->opcode)], cpu_env, cpu_gpr[rA(ctx->opcode)],
4552                    cpu_gpr[rB(ctx->opcode)]);
4553     if (unlikely(Rc(ctx->opcode) != 0))
4554         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4555 }
4556
4557 /* divo - divo. */
4558 static void gen_divo(DisasContext *ctx)
4559 {
4560     gen_helper_divo(cpu_gpr[rD(ctx->opcode)], cpu_env, cpu_gpr[rA(ctx->opcode)],
4561                     cpu_gpr[rB(ctx->opcode)]);
4562     if (unlikely(Rc(ctx->opcode) != 0))
4563         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4564 }
4565
4566 /* divs - divs. */
4567 static void gen_divs(DisasContext *ctx)
4568 {
4569     gen_helper_divs(cpu_gpr[rD(ctx->opcode)], cpu_env, cpu_gpr[rA(ctx->opcode)],
4570                     cpu_gpr[rB(ctx->opcode)]);
4571     if (unlikely(Rc(ctx->opcode) != 0))
4572         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4573 }
4574
4575 /* divso - divso. */
4576 static void gen_divso(DisasContext *ctx)
4577 {
4578     gen_helper_divso(cpu_gpr[rD(ctx->opcode)], cpu_env,
4579                      cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
4580     if (unlikely(Rc(ctx->opcode) != 0))
4581         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4582 }
4583
4584 /* doz - doz. */
4585 static void gen_doz(DisasContext *ctx)
4586 {
4587     TCGLabel *l1 = gen_new_label();
4588     TCGLabel *l2 = gen_new_label();
4589     tcg_gen_brcond_tl(TCG_COND_GE, cpu_gpr[rB(ctx->opcode)], cpu_gpr[rA(ctx->opcode)], l1);
4590     tcg_gen_sub_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rB(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4591     tcg_gen_br(l2);
4592     gen_set_label(l1);
4593     tcg_gen_movi_tl(cpu_gpr[rD(ctx->opcode)], 0);
4594     gen_set_label(l2);
4595     if (unlikely(Rc(ctx->opcode) != 0))
4596         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4597 }
4598
4599 /* dozo - dozo. */
4600 static void gen_dozo(DisasContext *ctx)
4601 {
4602     TCGLabel *l1 = gen_new_label();
4603     TCGLabel *l2 = gen_new_label();
4604     TCGv t0 = tcg_temp_new();
4605     TCGv t1 = tcg_temp_new();
4606     TCGv t2 = tcg_temp_new();
4607     /* Start with XER OV disabled, the most likely case */
4608     tcg_gen_movi_tl(cpu_ov, 0);
4609     tcg_gen_brcond_tl(TCG_COND_GE, cpu_gpr[rB(ctx->opcode)], cpu_gpr[rA(ctx->opcode)], l1);
4610     tcg_gen_sub_tl(t0, cpu_gpr[rB(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4611     tcg_gen_xor_tl(t1, cpu_gpr[rB(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4612     tcg_gen_xor_tl(t2, cpu_gpr[rA(ctx->opcode)], t0);
4613     tcg_gen_andc_tl(t1, t1, t2);
4614     tcg_gen_mov_tl(cpu_gpr[rD(ctx->opcode)], t0);
4615     tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l2);
4616     tcg_gen_movi_tl(cpu_ov, 1);
4617     tcg_gen_movi_tl(cpu_so, 1);
4618     tcg_gen_br(l2);
4619     gen_set_label(l1);
4620     tcg_gen_movi_tl(cpu_gpr[rD(ctx->opcode)], 0);
4621     gen_set_label(l2);
4622     tcg_temp_free(t0);
4623     tcg_temp_free(t1);
4624     tcg_temp_free(t2);
4625     if (unlikely(Rc(ctx->opcode) != 0))
4626         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4627 }
4628
4629 /* dozi */
4630 static void gen_dozi(DisasContext *ctx)
4631 {
4632     target_long simm = SIMM(ctx->opcode);
4633     TCGLabel *l1 = gen_new_label();
4634     TCGLabel *l2 = gen_new_label();
4635     tcg_gen_brcondi_tl(TCG_COND_LT, cpu_gpr[rA(ctx->opcode)], simm, l1);
4636     tcg_gen_subfi_tl(cpu_gpr[rD(ctx->opcode)], simm, cpu_gpr[rA(ctx->opcode)]);
4637     tcg_gen_br(l2);
4638     gen_set_label(l1);
4639     tcg_gen_movi_tl(cpu_gpr[rD(ctx->opcode)], 0);
4640     gen_set_label(l2);
4641     if (unlikely(Rc(ctx->opcode) != 0))
4642         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4643 }
4644
4645 /* lscbx - lscbx. */
4646 static void gen_lscbx(DisasContext *ctx)
4647 {
4648     TCGv t0 = tcg_temp_new();
4649     TCGv_i32 t1 = tcg_const_i32(rD(ctx->opcode));
4650     TCGv_i32 t2 = tcg_const_i32(rA(ctx->opcode));
4651     TCGv_i32 t3 = tcg_const_i32(rB(ctx->opcode));
4652
4653     gen_addr_reg_index(ctx, t0);
4654     gen_helper_lscbx(t0, cpu_env, t0, t1, t2, t3);
4655     tcg_temp_free_i32(t1);
4656     tcg_temp_free_i32(t2);
4657     tcg_temp_free_i32(t3);
4658     tcg_gen_andi_tl(cpu_xer, cpu_xer, ~0x7F);
4659     tcg_gen_or_tl(cpu_xer, cpu_xer, t0);
4660     if (unlikely(Rc(ctx->opcode) != 0))
4661         gen_set_Rc0(ctx, t0);
4662     tcg_temp_free(t0);
4663 }
4664
4665 /* maskg - maskg. */
4666 static void gen_maskg(DisasContext *ctx)
4667 {
4668     TCGLabel *l1 = gen_new_label();
4669     TCGv t0 = tcg_temp_new();
4670     TCGv t1 = tcg_temp_new();
4671     TCGv t2 = tcg_temp_new();
4672     TCGv t3 = tcg_temp_new();
4673     tcg_gen_movi_tl(t3, 0xFFFFFFFF);
4674     tcg_gen_andi_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x1F);
4675     tcg_gen_andi_tl(t1, cpu_gpr[rS(ctx->opcode)], 0x1F);
4676     tcg_gen_addi_tl(t2, t0, 1);
4677     tcg_gen_shr_tl(t2, t3, t2);
4678     tcg_gen_shr_tl(t3, t3, t1);
4679     tcg_gen_xor_tl(cpu_gpr[rA(ctx->opcode)], t2, t3);
4680     tcg_gen_brcond_tl(TCG_COND_GE, t0, t1, l1);
4681     tcg_gen_neg_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4682     gen_set_label(l1);
4683     tcg_temp_free(t0);
4684     tcg_temp_free(t1);
4685     tcg_temp_free(t2);
4686     tcg_temp_free(t3);
4687     if (unlikely(Rc(ctx->opcode) != 0))
4688         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4689 }
4690
4691 /* maskir - maskir. */
4692 static void gen_maskir(DisasContext *ctx)
4693 {
4694     TCGv t0 = tcg_temp_new();
4695     TCGv t1 = tcg_temp_new();
4696     tcg_gen_and_tl(t0, cpu_gpr[rS(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
4697     tcg_gen_andc_tl(t1, cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
4698     tcg_gen_or_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
4699     tcg_temp_free(t0);
4700     tcg_temp_free(t1);
4701     if (unlikely(Rc(ctx->opcode) != 0))
4702         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4703 }
4704
4705 /* mul - mul. */
4706 static void gen_mul(DisasContext *ctx)
4707 {
4708     TCGv_i64 t0 = tcg_temp_new_i64();
4709     TCGv_i64 t1 = tcg_temp_new_i64();
4710     TCGv t2 = tcg_temp_new();
4711     tcg_gen_extu_tl_i64(t0, cpu_gpr[rA(ctx->opcode)]);
4712     tcg_gen_extu_tl_i64(t1, cpu_gpr[rB(ctx->opcode)]);
4713     tcg_gen_mul_i64(t0, t0, t1);
4714     tcg_gen_trunc_i64_tl(t2, t0);
4715     gen_store_spr(SPR_MQ, t2);
4716     tcg_gen_shri_i64(t1, t0, 32);
4717     tcg_gen_trunc_i64_tl(cpu_gpr[rD(ctx->opcode)], t1);
4718     tcg_temp_free_i64(t0);
4719     tcg_temp_free_i64(t1);
4720     tcg_temp_free(t2);
4721     if (unlikely(Rc(ctx->opcode) != 0))
4722         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4723 }
4724
4725 /* mulo - mulo. */
4726 static void gen_mulo(DisasContext *ctx)
4727 {
4728     TCGLabel *l1 = gen_new_label();
4729     TCGv_i64 t0 = tcg_temp_new_i64();
4730     TCGv_i64 t1 = tcg_temp_new_i64();
4731     TCGv t2 = tcg_temp_new();
4732     /* Start with XER OV disabled, the most likely case */
4733     tcg_gen_movi_tl(cpu_ov, 0);
4734     tcg_gen_extu_tl_i64(t0, cpu_gpr[rA(ctx->opcode)]);
4735     tcg_gen_extu_tl_i64(t1, cpu_gpr[rB(ctx->opcode)]);
4736     tcg_gen_mul_i64(t0, t0, t1);
4737     tcg_gen_trunc_i64_tl(t2, t0);
4738     gen_store_spr(SPR_MQ, t2);
4739     tcg_gen_shri_i64(t1, t0, 32);
4740     tcg_gen_trunc_i64_tl(cpu_gpr[rD(ctx->opcode)], t1);
4741     tcg_gen_ext32s_i64(t1, t0);
4742     tcg_gen_brcond_i64(TCG_COND_EQ, t0, t1, l1);
4743     tcg_gen_movi_tl(cpu_ov, 1);
4744     tcg_gen_movi_tl(cpu_so, 1);
4745     gen_set_label(l1);
4746     tcg_temp_free_i64(t0);
4747     tcg_temp_free_i64(t1);
4748     tcg_temp_free(t2);
4749     if (unlikely(Rc(ctx->opcode) != 0))
4750         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4751 }
4752
4753 /* nabs - nabs. */
4754 static void gen_nabs(DisasContext *ctx)
4755 {
4756     TCGLabel *l1 = gen_new_label();
4757     TCGLabel *l2 = gen_new_label();
4758     tcg_gen_brcondi_tl(TCG_COND_GT, cpu_gpr[rA(ctx->opcode)], 0, l1);
4759     tcg_gen_mov_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4760     tcg_gen_br(l2);
4761     gen_set_label(l1);
4762     tcg_gen_neg_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4763     gen_set_label(l2);
4764     if (unlikely(Rc(ctx->opcode) != 0))
4765         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4766 }
4767
4768 /* nabso - nabso. */
4769 static void gen_nabso(DisasContext *ctx)
4770 {
4771     TCGLabel *l1 = gen_new_label();
4772     TCGLabel *l2 = gen_new_label();
4773     tcg_gen_brcondi_tl(TCG_COND_GT, cpu_gpr[rA(ctx->opcode)], 0, l1);
4774     tcg_gen_mov_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4775     tcg_gen_br(l2);
4776     gen_set_label(l1);
4777     tcg_gen_neg_tl(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
4778     gen_set_label(l2);
4779     /* nabs never overflows */
4780     tcg_gen_movi_tl(cpu_ov, 0);
4781     if (unlikely(Rc(ctx->opcode) != 0))
4782         gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);
4783 }
4784
4785 /* rlmi - rlmi. */
4786 static void gen_rlmi(DisasContext *ctx)
4787 {
4788     uint32_t mb = MB(ctx->opcode);
4789     uint32_t me = ME(ctx->opcode);
4790     TCGv t0 = tcg_temp_new();
4791     tcg_gen_andi_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x1F);
4792     tcg_gen_rotl_tl(t0, cpu_gpr[rS(ctx->opcode)], t0);
4793     tcg_gen_andi_tl(t0, t0, MASK(mb, me));
4794     tcg_gen_andi_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rA(ctx->opcode)], ~MASK(mb, me));
4795     tcg_gen_or_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rA(ctx->opcode)], t0);
4796     tcg_temp_free(t0);
4797     if (unlikely(Rc(ctx->opcode) != 0))
4798         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4799 }
4800
4801 /* rrib - rrib. */
4802 static void gen_rrib(DisasContext *ctx)
4803 {
4804     TCGv t0 = tcg_temp_new();
4805     TCGv t1 = tcg_temp_new();
4806     tcg_gen_andi_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x1F);
4807     tcg_gen_movi_tl(t1, 0x80000000);
4808     tcg_gen_shr_tl(t1, t1, t0);
4809     tcg_gen_shr_tl(t0, cpu_gpr[rS(ctx->opcode)], t0);
4810     tcg_gen_and_tl(t0, t0, t1);
4811     tcg_gen_andc_tl(t1, cpu_gpr[rA(ctx->opcode)], t1);
4812     tcg_gen_or_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
4813     tcg_temp_free(t0);
4814     tcg_temp_free(t1);
4815     if (unlikely(Rc(ctx->opcode) != 0))
4816         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4817 }
4818
4819 /* sle - sle. */
4820 static void gen_sle(DisasContext *ctx)
4821 {
4822     TCGv t0 = tcg_temp_new();
4823     TCGv t1 = tcg_temp_new();
4824     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x1F);
4825     tcg_gen_shl_tl(t0, cpu_gpr[rS(ctx->opcode)], t1);
4826     tcg_gen_subfi_tl(t1, 32, t1);
4827     tcg_gen_shr_tl(t1, cpu_gpr[rS(ctx->opcode)], t1);
4828     tcg_gen_or_tl(t1, t0, t1);
4829     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], t0);
4830     gen_store_spr(SPR_MQ, t1);
4831     tcg_temp_free(t0);
4832     tcg_temp_free(t1);
4833     if (unlikely(Rc(ctx->opcode) != 0))
4834         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4835 }
4836
4837 /* sleq - sleq. */
4838 static void gen_sleq(DisasContext *ctx)
4839 {
4840     TCGv t0 = tcg_temp_new();
4841     TCGv t1 = tcg_temp_new();
4842     TCGv t2 = tcg_temp_new();
4843     tcg_gen_andi_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x1F);
4844     tcg_gen_movi_tl(t2, 0xFFFFFFFF);
4845     tcg_gen_shl_tl(t2, t2, t0);
4846     tcg_gen_rotl_tl(t0, cpu_gpr[rS(ctx->opcode)], t0);
4847     gen_load_spr(t1, SPR_MQ);
4848     gen_store_spr(SPR_MQ, t0);
4849     tcg_gen_and_tl(t0, t0, t2);
4850     tcg_gen_andc_tl(t1, t1, t2);
4851     tcg_gen_or_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
4852     tcg_temp_free(t0);
4853     tcg_temp_free(t1);
4854     tcg_temp_free(t2);
4855     if (unlikely(Rc(ctx->opcode) != 0))
4856         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4857 }
4858
4859 /* sliq - sliq. */
4860 static void gen_sliq(DisasContext *ctx)
4861 {
4862     int sh = SH(ctx->opcode);
4863     TCGv t0 = tcg_temp_new();
4864     TCGv t1 = tcg_temp_new();
4865     tcg_gen_shli_tl(t0, cpu_gpr[rS(ctx->opcode)], sh);
4866     tcg_gen_shri_tl(t1, cpu_gpr[rS(ctx->opcode)], 32 - sh);
4867     tcg_gen_or_tl(t1, t0, t1);
4868     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], t0);
4869     gen_store_spr(SPR_MQ, t1);
4870     tcg_temp_free(t0);
4871     tcg_temp_free(t1);
4872     if (unlikely(Rc(ctx->opcode) != 0))
4873         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4874 }
4875
4876 /* slliq - slliq. */
4877 static void gen_slliq(DisasContext *ctx)
4878 {
4879     int sh = SH(ctx->opcode);
4880     TCGv t0 = tcg_temp_new();
4881     TCGv t1 = tcg_temp_new();
4882     tcg_gen_rotli_tl(t0, cpu_gpr[rS(ctx->opcode)], sh);
4883     gen_load_spr(t1, SPR_MQ);
4884     gen_store_spr(SPR_MQ, t0);
4885     tcg_gen_andi_tl(t0, t0,  (0xFFFFFFFFU << sh));
4886     tcg_gen_andi_tl(t1, t1, ~(0xFFFFFFFFU << sh));
4887     tcg_gen_or_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
4888     tcg_temp_free(t0);
4889     tcg_temp_free(t1);
4890     if (unlikely(Rc(ctx->opcode) != 0))
4891         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4892 }
4893
4894 /* sllq - sllq. */
4895 static void gen_sllq(DisasContext *ctx)
4896 {
4897     TCGLabel *l1 = gen_new_label();
4898     TCGLabel *l2 = gen_new_label();
4899     TCGv t0 = tcg_temp_local_new();
4900     TCGv t1 = tcg_temp_local_new();
4901     TCGv t2 = tcg_temp_local_new();
4902     tcg_gen_andi_tl(t2, cpu_gpr[rB(ctx->opcode)], 0x1F);
4903     tcg_gen_movi_tl(t1, 0xFFFFFFFF);
4904     tcg_gen_shl_tl(t1, t1, t2);
4905     tcg_gen_andi_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x20);
4906     tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);
4907     gen_load_spr(t0, SPR_MQ);
4908     tcg_gen_and_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
4909     tcg_gen_br(l2);
4910     gen_set_label(l1);
4911     tcg_gen_shl_tl(t0, cpu_gpr[rS(ctx->opcode)], t2);
4912     gen_load_spr(t2, SPR_MQ);
4913     tcg_gen_andc_tl(t1, t2, t1);
4914     tcg_gen_or_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
4915     gen_set_label(l2);
4916     tcg_temp_free(t0);
4917     tcg_temp_free(t1);
4918     tcg_temp_free(t2);
4919     if (unlikely(Rc(ctx->opcode) != 0))
4920         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4921 }
4922
4923 /* slq - slq. */
4924 static void gen_slq(DisasContext *ctx)
4925 {
4926     TCGLabel *l1 = gen_new_label();
4927     TCGv t0 = tcg_temp_new();
4928     TCGv t1 = tcg_temp_new();
4929     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x1F);
4930     tcg_gen_shl_tl(t0, cpu_gpr[rS(ctx->opcode)], t1);
4931     tcg_gen_subfi_tl(t1, 32, t1);
4932     tcg_gen_shr_tl(t1, cpu_gpr[rS(ctx->opcode)], t1);
4933     tcg_gen_or_tl(t1, t0, t1);
4934     gen_store_spr(SPR_MQ, t1);
4935     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x20);
4936     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], t0);
4937     tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
4938     tcg_gen_movi_tl(cpu_gpr[rA(ctx->opcode)], 0);
4939     gen_set_label(l1);
4940     tcg_temp_free(t0);
4941     tcg_temp_free(t1);
4942     if (unlikely(Rc(ctx->opcode) != 0))
4943         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4944 }
4945
4946 /* sraiq - sraiq. */
4947 static void gen_sraiq(DisasContext *ctx)
4948 {
4949     int sh = SH(ctx->opcode);
4950     TCGLabel *l1 = gen_new_label();
4951     TCGv t0 = tcg_temp_new();
4952     TCGv t1 = tcg_temp_new();
4953     tcg_gen_shri_tl(t0, cpu_gpr[rS(ctx->opcode)], sh);
4954     tcg_gen_shli_tl(t1, cpu_gpr[rS(ctx->opcode)], 32 - sh);
4955     tcg_gen_or_tl(t0, t0, t1);
4956     gen_store_spr(SPR_MQ, t0);
4957     tcg_gen_movi_tl(cpu_ca, 0);
4958     tcg_gen_brcondi_tl(TCG_COND_EQ, t1, 0, l1);
4959     tcg_gen_brcondi_tl(TCG_COND_GE, cpu_gpr[rS(ctx->opcode)], 0, l1);
4960     tcg_gen_movi_tl(cpu_ca, 1);
4961     gen_set_label(l1);
4962     tcg_gen_sari_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)], sh);
4963     tcg_temp_free(t0);
4964     tcg_temp_free(t1);
4965     if (unlikely(Rc(ctx->opcode) != 0))
4966         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
4967 }
4968
4969 /* sraq - sraq. */
4970 static void gen_sraq(DisasContext *ctx)
4971 {
4972     TCGLabel *l1 = gen_new_label();
4973     TCGLabel *l2 = gen_new_label();
4974     TCGv t0 = tcg_temp_new();
4975     TCGv t1 = tcg_temp_local_new();
4976     TCGv t2 = tcg_temp_local_new();
4977     tcg_gen_andi_tl(t2, cpu_gpr[rB(ctx->opcode)], 0x1F);
4978     tcg_gen_shr_tl(t0, cpu_gpr[rS(ctx->opcode)], t2);
4979     tcg_gen_sar_tl(t1, cpu_gpr[rS(ctx->opcode)], t2);
4980     tcg_gen_subfi_tl(t2, 32, t2);
4981     tcg_gen_shl_tl(t2, cpu_gpr[rS(ctx->opcode)], t2);
4982     tcg_gen_or_tl(t0, t0, t2);
4983     gen_store_spr(SPR_MQ, t0);
4984     tcg_gen_andi_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x20);
4985     tcg_gen_brcondi_tl(TCG_COND_EQ, t2, 0, l1);
4986     tcg_gen_mov_tl(t2, cpu_gpr[rS(ctx->opcode)]);
4987     tcg_gen_sari_tl(t1, cpu_gpr[rS(ctx->opcode)], 31);
4988     gen_set_label(l1);
4989     tcg_temp_free(t0);
4990     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], t1);
4991     tcg_gen_movi_tl(cpu_ca, 0);
4992     tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l2);
4993     tcg_gen_brcondi_tl(TCG_COND_EQ, t2, 0, l2);
4994     tcg_gen_movi_tl(cpu_ca, 1);
4995     gen_set_label(l2);
4996     tcg_temp_free(t1);
4997     tcg_temp_free(t2);
4998     if (unlikely(Rc(ctx->opcode) != 0))
4999         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
5000 }
5001
5002 /* sre - sre. */
5003 static void gen_sre(DisasContext *ctx)
5004 {
5005     TCGv t0 = tcg_temp_new();
5006     TCGv t1 = tcg_temp_new();
5007     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x1F);
5008     tcg_gen_shr_tl(t0, cpu_gpr[rS(ctx->opcode)], t1);
5009     tcg_gen_subfi_tl(t1, 32, t1);
5010     tcg_gen_shl_tl(t1, cpu_gpr[rS(ctx->opcode)], t1);
5011     tcg_gen_or_tl(t1, t0, t1);
5012     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], t0);
5013     gen_store_spr(SPR_MQ, t1);
5014     tcg_temp_free(t0);
5015     tcg_temp_free(t1);
5016     if (unlikely(Rc(ctx->opcode) != 0))
5017         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
5018 }
5019
5020 /* srea - srea. */
5021 static void gen_srea(DisasContext *ctx)
5022 {
5023     TCGv t0 = tcg_temp_new();
5024     TCGv t1 = tcg_temp_new();
5025     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x1F);
5026     tcg_gen_rotr_tl(t0, cpu_gpr[rS(ctx->opcode)], t1);
5027     gen_store_spr(SPR_MQ, t0);
5028     tcg_gen_sar_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)], t1);
5029     tcg_temp_free(t0);
5030     tcg_temp_free(t1);
5031     if (unlikely(Rc(ctx->opcode) != 0))
5032         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
5033 }
5034
5035 /* sreq */
5036 static void gen_sreq(DisasContext *ctx)
5037 {
5038     TCGv t0 = tcg_temp_new();
5039     TCGv t1 = tcg_temp_new();
5040     TCGv t2 = tcg_temp_new();
5041     tcg_gen_andi_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x1F);
5042     tcg_gen_movi_tl(t1, 0xFFFFFFFF);
5043     tcg_gen_shr_tl(t1, t1, t0);
5044     tcg_gen_rotr_tl(t0, cpu_gpr[rS(ctx->opcode)], t0);
5045     gen_load_spr(t2, SPR_MQ);
5046     gen_store_spr(SPR_MQ, t0);
5047     tcg_gen_and_tl(t0, t0, t1);
5048     tcg_gen_andc_tl(t2, t2, t1);
5049     tcg_gen_or_tl(cpu_gpr[rA(ctx->opcode)], t0, t2);
5050     tcg_temp_free(t0);
5051     tcg_temp_free(t1);
5052     tcg_temp_free(t2);
5053     if (unlikely(Rc(ctx->opcode) != 0))
5054         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
5055 }
5056
5057 /* sriq */
5058 static void gen_sriq(DisasContext *ctx)
5059 {
5060     int sh = SH(ctx->opcode);
5061     TCGv t0 = tcg_temp_new();
5062     TCGv t1 = tcg_temp_new();
5063     tcg_gen_shri_tl(t0, cpu_gpr[rS(ctx->opcode)], sh);
5064     tcg_gen_shli_tl(t1, cpu_gpr[rS(ctx->opcode)], 32 - sh);
5065     tcg_gen_or_tl(t1, t0, t1);
5066     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], t0);
5067     gen_store_spr(SPR_MQ, t1);
5068     tcg_temp_free(t0);
5069     tcg_temp_free(t1);
5070     if (unlikely(Rc(ctx->opcode) != 0))
5071         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
5072 }
5073
5074 /* srliq */
5075 static void gen_srliq(DisasContext *ctx)
5076 {
5077     int sh = SH(ctx->opcode);
5078     TCGv t0 = tcg_temp_new();
5079     TCGv t1 = tcg_temp_new();
5080     tcg_gen_rotri_tl(t0, cpu_gpr[rS(ctx->opcode)], sh);
5081     gen_load_spr(t1, SPR_MQ);
5082     gen_store_spr(SPR_MQ, t0);
5083     tcg_gen_andi_tl(t0, t0,  (0xFFFFFFFFU >> sh));
5084     tcg_gen_andi_tl(t1, t1, ~(0xFFFFFFFFU >> sh));
5085     tcg_gen_or_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
5086     tcg_temp_free(t0);
5087     tcg_temp_free(t1);
5088     if (unlikely(Rc(ctx->opcode) != 0))
5089         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
5090 }
5091
5092 /* srlq */
5093 static void gen_srlq(DisasContext *ctx)
5094 {
5095     TCGLabel *l1 = gen_new_label();
5096     TCGLabel *l2 = gen_new_label();
5097     TCGv t0 = tcg_temp_local_new();
5098     TCGv t1 = tcg_temp_local_new();
5099     TCGv t2 = tcg_temp_local_new();
5100     tcg_gen_andi_tl(t2, cpu_gpr[rB(ctx->opcode)], 0x1F);
5101     tcg_gen_movi_tl(t1, 0xFFFFFFFF);
5102     tcg_gen_shr_tl(t2, t1, t2);
5103     tcg_gen_andi_tl(t0, cpu_gpr[rB(ctx->opcode)], 0x20);
5104     tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);
5105     gen_load_spr(t0, SPR_MQ);
5106     tcg_gen_and_tl(cpu_gpr[rA(ctx->opcode)], t0, t2);
5107     tcg_gen_br(l2);
5108     gen_set_label(l1);
5109     tcg_gen_shr_tl(t0, cpu_gpr[rS(ctx->opcode)], t2);
5110     tcg_gen_and_tl(t0, t0, t2);
5111     gen_load_spr(t1, SPR_MQ);
5112     tcg_gen_andc_tl(t1, t1, t2);
5113     tcg_gen_or_tl(cpu_gpr[rA(ctx->opcode)], t0, t1);
5114     gen_set_label(l2);
5115     tcg_temp_free(t0);
5116     tcg_temp_free(t1);
5117     tcg_temp_free(t2);
5118     if (unlikely(Rc(ctx->opcode) != 0))
5119         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
5120 }
5121
5122 /* srq */
5123 static void gen_srq(DisasContext *ctx)
5124 {
5125     TCGLabel *l1 = gen_new_label();
5126     TCGv t0 = tcg_temp_new();
5127     TCGv t1 = tcg_temp_new();
5128     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x1F);
5129     tcg_gen_shr_tl(t0, cpu_gpr[rS(ctx->opcode)], t1);
5130     tcg_gen_subfi_tl(t1, 32, t1);
5131     tcg_gen_shl_tl(t1, cpu_gpr[rS(ctx->opcode)], t1);
5132     tcg_gen_or_tl(t1, t0, t1);
5133     gen_store_spr(SPR_MQ, t1);
5134     tcg_gen_andi_tl(t1, cpu_gpr[rB(ctx->opcode)], 0x20);
5135     tcg_gen_mov_tl(cpu_gpr[rA(ctx->opcode)], t0);
5136     tcg_gen_brcondi_tl(TCG_COND_EQ, t0, 0, l1);
5137     tcg_gen_movi_tl(cpu_gpr[rA(ctx->opcode)], 0);
5138     gen_set_label(l1);
5139     tcg_temp_free(t0);
5140     tcg_temp_free(t1);
5141     if (unlikely(Rc(ctx->opcode) != 0))
5142         gen_set_Rc0(ctx, cpu_gpr[rA(ctx->opcode)]);
5143 }
5144
5145 /* PowerPC 602 specific instructions */
5146
5147 /* dsa  */
5148 static void gen_dsa(DisasContext *ctx)
5149 {
5150     /* XXX: TODO */
5151     gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
5152 }
5153
5154 /* esa */
5155 static void gen_esa(DisasContext *ctx)
5156 {
5157     /* XXX: TODO */
5158     gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
5159 }
5160
5161 /* mfrom */
5162 static void gen_mfrom(DisasContext *ctx)
5163 {
5164 #if defined(CONFIG_USER_ONLY)
5165     GEN_PRIV;
5166 #else
5167     CHK_SV;
5168     gen_helper_602_mfrom(cpu_gpr[rD(ctx->opcode)], cpu_gpr[rA(ctx->opcode)]);
5169 #endif /* defined(CONFIG_USER_ONLY) */
5170 }
5171
5172 /* 602 - 603 - G2 TLB management */
5173
5174 /* tlbld */
5175 static void gen_tlbld_6xx(DisasContext *ctx)
5176 {
5177 #if defined(CONFIG_USER_ONLY)
5178     GEN_PRIV;
5179 #else
5180     CHK_SV;
5181     gen_helper_6xx_tlbd(cpu_env, cpu_gpr[rB(ctx->opcode)]);
5182 #endif /* defined(CONFIG_USER_ONLY) */
5183 }
5184
5185 /* tlbli */
5186 static void gen_tlbli_6xx(DisasContext *ctx)
5187 {
5188 #if defined(CONFIG_USER_ONLY)
5189     GEN_PRIV;
5190 #else
5191     CHK_SV;
5192     gen_helper_6xx_tlbi(cpu_env, cpu_gpr[rB(ctx->opcode)]);
5193 #endif /* defined(CONFIG_USER_ONLY) */
5194 }
5195
5196 /* 74xx TLB management */
5197
5198 /* tlbld */
5199 static void gen_tlbld_74xx(DisasContext *ctx)
5200 {
5201 #if defined(CONFIG_USER_ONLY)
5202     GEN_PRIV;
5203 #else
5204     CHK_SV;
5205     gen_helper_74xx_tlbd(cpu_env, cpu_gpr[rB(ctx->opcode)]);
5206 #endif /* defined(CONFIG_USER_ONLY) */
5207 }
5208
5209 /* tlbli */
5210 static void gen_tlbli_74xx(DisasContext *ctx)
5211 {
5212 #if defined(CONFIG_USER_ONLY)
5213     GEN_PRIV;
5214 #else
5215     CHK_SV;
5216     gen_helper_74xx_tlbi(cpu_env, cpu_gpr[rB(ctx->opcode)]);
5217 #endif /* defined(CONFIG_USER_ONLY) */
5218 }
5219
5220 /* POWER instructions not in PowerPC 601 */
5221
5222 /* clf */
5223 static void gen_clf(DisasContext *ctx)
5224 {
5225     /* Cache line flush: implemented as no-op */
5226 }
5227
5228 /* cli */
5229 static void gen_cli(DisasContext *ctx)
5230 {
5231 #if defined(CONFIG_USER_ONLY)
5232     GEN_PRIV;
5233 #else
5234     /* Cache line invalidate: privileged and treated as no-op */
5235     CHK_SV;
5236 #endif /* defined(CONFIG_USER_ONLY) */
5237 }
5238
5239 /* dclst */
5240 static void gen_dclst(DisasContext *ctx)
5241 {
5242     /* Data cache line store: treated as no-op */
5243 }
5244
5245 static void gen_mfsri(DisasContext *ctx)
5246 {
5247 #if defined(CONFIG_USER_ONLY)
5248     GEN_PRIV;
5249 #else
5250     int ra = rA(ctx->opcode);
5251     int rd = rD(ctx->opcode);
5252     TCGv t0;
5253
5254     CHK_SV;
5255     t0 = tcg_temp_new();
5256     gen_addr_reg_index(ctx, t0);
5257     tcg_gen_shri_tl(t0, t0, 28);
5258     tcg_gen_andi_tl(t0, t0, 0xF);
5259     gen_helper_load_sr(cpu_gpr[rd], cpu_env, t0);
5260     tcg_temp_free(t0);
5261     if (ra != 0 && ra != rd)
5262         tcg_gen_mov_tl(cpu_gpr[ra], cpu_gpr[rd]);
5263 #endif /* defined(CONFIG_USER_ONLY) */
5264 }
5265
5266 static void gen_rac(DisasContext *ctx)
5267 {
5268 #if defined(CONFIG_USER_ONLY)
5269     GEN_PRIV;
5270 #else
5271     TCGv t0;
5272
5273     CHK_SV;
5274     t0 = tcg_temp_new();
5275     gen_addr_reg_index(ctx, t0);
5276     gen_helper_rac(cpu_gpr[rD(ctx->opcode)], cpu_env, t0);
5277     tcg_temp_free(t0);
5278 #endif /* defined(CONFIG_USER_ONLY) */
5279 }
5280
5281 static void gen_rfsvc(DisasContext *ctx)
5282 {
5283 #if defined(CONFIG_USER_ONLY)
5284     GEN_PRIV;
5285 #else
5286     CHK_SV;
5287
5288     gen_helper_rfsvc(cpu_env);
5289     gen_sync_exception(ctx);
5290 #endif /* defined(CONFIG_USER_ONLY) */
5291 }
5292
5293 /* svc is not implemented for now */
5294
5295 /* BookE specific instructions */
5296
5297 /* XXX: not implemented on 440 ? */
5298 static void gen_mfapidi(DisasContext *ctx)
5299 {
5300     /* XXX: TODO */
5301     gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
5302 }
5303
5304 /* XXX: not implemented on 440 ? */
5305 static void gen_tlbiva(DisasContext *ctx)
5306 {
5307 #if defined(CONFIG_USER_ONLY)
5308     GEN_PRIV;
5309 #else
5310     TCGv t0;
5311
5312     CHK_SV;
5313     t0 = tcg_temp_new();
5314     gen_addr_reg_index(ctx, t0);
5315     gen_helper_tlbiva(cpu_env, cpu_gpr[rB(ctx->opcode)]);
5316     tcg_temp_free(t0);
5317 #endif /* defined(CONFIG_USER_ONLY) */
5318 }
5319
5320 /* All 405 MAC instructions are translated here */
5321 static inline void gen_405_mulladd_insn(DisasContext *ctx, int opc2, int opc3,
5322                                         int ra, int rb, int rt, int Rc)
5323 {
5324     TCGv t0, t1;
5325
5326     t0 = tcg_temp_local_new();
5327     t1 = tcg_temp_local_new();
5328
5329     switch (opc3 & 0x0D) {
5330     case 0x05:
5331         /* macchw    - macchw.    - macchwo   - macchwo.   */
5332         /* macchws   - macchws.   - macchwso  - macchwso.  */
5333         /* nmacchw   - nmacchw.   - nmacchwo  - nmacchwo.  */
5334         /* nmacchws  - nmacchws.  - nmacchwso - nmacchwso. */
5335         /* mulchw - mulchw. */
5336         tcg_gen_ext16s_tl(t0, cpu_gpr[ra]);
5337         tcg_gen_sari_tl(t1, cpu_gpr[rb], 16);
5338         tcg_gen_ext16s_tl(t1, t1);
5339         break;
5340     case 0x04:
5341         /* macchwu   - macchwu.   - macchwuo  - macchwuo.  */
5342         /* macchwsu  - macchwsu.  - macchwsuo - macchwsuo. */
5343         /* mulchwu - mulchwu. */
5344         tcg_gen_ext16u_tl(t0, cpu_gpr[ra]);
5345         tcg_gen_shri_tl(t1, cpu_gpr[rb], 16);
5346         tcg_gen_ext16u_tl(t1, t1);
5347         break;
5348     case 0x01:
5349         /* machhw    - machhw.    - machhwo   - machhwo.   */
5350         /* machhws   - machhws.   - machhwso  - machhwso.  */
5351         /* nmachhw   - nmachhw.   - nmachhwo  - nmachhwo.  */
5352         /* nmachhws  - nmachhws.  - nmachhwso - nmachhwso. */
5353         /* mulhhw - mulhhw. */
5354         tcg_gen_sari_tl(t0, cpu_gpr[ra], 16);
5355         tcg_gen_ext16s_tl(t0, t0);
5356         tcg_gen_sari_tl(t1, cpu_gpr[rb], 16);
5357         tcg_gen_ext16s_tl(t1, t1);
5358         break;
5359     case 0x00:
5360         /* machhwu   - machhwu.   - machhwuo  - machhwuo.  */
5361         /* machhwsu  - machhwsu.  - machhwsuo - machhwsuo. */
5362         /* mulhhwu - mulhhwu. */
5363         tcg_gen_shri_tl(t0, cpu_gpr[ra], 16);
5364         tcg_gen_ext16u_tl(t0, t0);
5365         tcg_gen_shri_tl(t1, cpu_gpr[rb], 16);
5366         tcg_gen_ext16u_tl(t1, t1);
5367         break;
5368     case 0x0D:
5369         /* maclhw    - maclhw.    - maclhwo   - maclhwo.   */
5370         /* maclhws   - maclhws.   - maclhwso  - maclhwso.  */
5371         /* nmaclhw   - nmaclhw.   - nmaclhwo  - nmaclhwo.  */
5372         /* nmaclhws  - nmaclhws.  - nmaclhwso - nmaclhwso. */
5373         /* mullhw - mullhw. */
5374         tcg_gen_ext16s_tl(t0, cpu_gpr[ra]);
5375         tcg_gen_ext16s_tl(t1, cpu_gpr[rb]);
5376         break;
5377     case 0x0C:
5378         /* maclhwu   - maclhwu.   - maclhwuo  - maclhwuo.  */
5379         /* maclhwsu  - maclhwsu.  - maclhwsuo - maclhwsuo. */
5380         /* mullhwu - mullhwu. */
5381         tcg_gen_ext16u_tl(t0, cpu_gpr[ra]);
5382         tcg_gen_ext16u_tl(t1, cpu_gpr[rb]);
5383         break;
5384     }
5385     if (opc2 & 0x04) {
5386         /* (n)multiply-and-accumulate (0x0C / 0x0E) */
5387         tcg_gen_mul_tl(t1, t0, t1);
5388         if (opc2 & 0x02) {
5389             /* nmultiply-and-accumulate (0x0E) */
5390             tcg_gen_sub_tl(t0, cpu_gpr[rt], t1);
5391         } else {
5392             /* multiply-and-accumulate (0x0C) */
5393             tcg_gen_add_tl(t0, cpu_gpr[rt], t1);
5394         }
5395
5396         if (opc3 & 0x12) {
5397             /* Check overflow and/or saturate */
5398             TCGLabel *l1 = gen_new_label();
5399
5400             if (opc3 & 0x10) {
5401                 /* Start with XER OV disabled, the most likely case */
5402                 tcg_gen_movi_tl(cpu_ov, 0);
5403             }
5404             if (opc3 & 0x01) {
5405                 /* Signed */
5406                 tcg_gen_xor_tl(t1, cpu_gpr[rt], t1);
5407                 tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
5408                 tcg_gen_xor_tl(t1, cpu_gpr[rt], t0);
5409                 tcg_gen_brcondi_tl(TCG_COND_LT, t1, 0, l1);
5410                 if (opc3 & 0x02) {
5411                     /* Saturate */
5412                     tcg_gen_sari_tl(t0, cpu_gpr[rt], 31);
5413                     tcg_gen_xori_tl(t0, t0, 0x7fffffff);
5414                 }
5415             } else {
5416                 /* Unsigned */
5417                 tcg_gen_brcond_tl(TCG_COND_GEU, t0, t1, l1);
5418                 if (opc3 & 0x02) {
5419                     /* Saturate */
5420                     tcg_gen_movi_tl(t0, UINT32_MAX);
5421                 }
5422             }
5423             if (opc3 & 0x10) {
5424                 /* Check overflow */
5425                 tcg_gen_movi_tl(cpu_ov, 1);
5426                 tcg_gen_movi_tl(cpu_so, 1);
5427             }
5428             gen_set_label(l1);
5429             tcg_gen_mov_tl(cpu_gpr[rt], t0);
5430         }
5431     } else {
5432         tcg_gen_mul_tl(cpu_gpr[rt], t0, t1);
5433     }
5434     tcg_temp_free(t0);
5435     tcg_temp_free(t1);
5436     if (unlikely(Rc) != 0) {
5437         /* Update Rc0 */
5438         gen_set_Rc0(ctx, cpu_gpr[rt]);
5439     }
5440 }
5441
5442 #define GEN_MAC_HANDLER(name, opc2, opc3)                                     \
5443 static void glue(gen_, name)(DisasContext *ctx)                               \
5444 {                                                                             \
5445     gen_405_mulladd_insn(ctx, opc2, opc3, rA(ctx->opcode), rB(ctx->opcode),   \
5446                          rD(ctx->opcode), Rc(ctx->opcode));                   \
5447 }
5448
5449 /* macchw    - macchw.    */
5450 GEN_MAC_HANDLER(macchw, 0x0C, 0x05);
5451 /* macchwo   - macchwo.   */
5452 GEN_MAC_HANDLER(macchwo, 0x0C, 0x15);
5453 /* macchws   - macchws.   */
5454 GEN_MAC_HANDLER(macchws, 0x0C, 0x07);
5455 /* macchwso  - macchwso.  */
5456 GEN_MAC_HANDLER(macchwso, 0x0C, 0x17);
5457 /* macchwsu  - macchwsu.  */
5458 GEN_MAC_HANDLER(macchwsu, 0x0C, 0x06);
5459 /* macchwsuo - macchwsuo. */
5460 GEN_MAC_HANDLER(macchwsuo, 0x0C, 0x16);
5461 /* macchwu   - macchwu.   */
5462 GEN_MAC_HANDLER(macchwu, 0x0C, 0x04);
5463 /* macchwuo  - macchwuo.  */
5464 GEN_MAC_HANDLER(macchwuo, 0x0C, 0x14);
5465 /* machhw    - machhw.    */
5466 GEN_MAC_HANDLER(machhw, 0x0C, 0x01);
5467 /* machhwo   - machhwo.   */
5468 GEN_MAC_HANDLER(machhwo, 0x0C, 0x11);
5469 /* machhws   - machhws.   */
5470 GEN_MAC_HANDLER(machhws, 0x0C, 0x03);
5471 /* machhwso  - machhwso.  */
5472 GEN_MAC_HANDLER(machhwso, 0x0C, 0x13);
5473 /* machhwsu  - machhwsu.  */
5474 GEN_MAC_HANDLER(machhwsu, 0x0C, 0x02);
5475 /* machhwsuo - machhwsuo. */
5476 GEN_MAC_HANDLER(machhwsuo, 0x0C, 0x12);
5477 /* machhwu   - machhwu.   */
5478 GEN_MAC_HANDLER(machhwu, 0x0C, 0x00);
5479 /* machhwuo  - machhwuo.  */
5480 GEN_MAC_HANDLER(machhwuo, 0x0C, 0x10);
5481 /* maclhw    - maclhw.    */
5482 GEN_MAC_HANDLER(maclhw, 0x0C, 0x0D);
5483 /* maclhwo   - maclhwo.   */
5484 GEN_MAC_HANDLER(maclhwo, 0x0C, 0x1D);
5485 /* maclhws   - maclhws.   */
5486 GEN_MAC_HANDLER(maclhws, 0x0C, 0x0F);
5487 /* maclhwso  - maclhwso.  */
5488 GEN_MAC_HANDLER(maclhwso, 0x0C, 0x1F);
5489 /* maclhwu   - maclhwu.   */
5490 GEN_MAC_HANDLER(maclhwu, 0x0C, 0x0C);
5491 /* maclhwuo  - maclhwuo.  */
5492 GEN_MAC_HANDLER(maclhwuo, 0x0C, 0x1C);
5493 /* maclhwsu  - maclhwsu.  */
5494 GEN_MAC_HANDLER(maclhwsu, 0x0C, 0x0E);
5495 /* maclhwsuo - maclhwsuo. */
5496 GEN_MAC_HANDLER(maclhwsuo, 0x0C, 0x1E);
5497 /* nmacchw   - nmacchw.   */
5498 GEN_MAC_HANDLER(nmacchw, 0x0E, 0x05);
5499 /* nmacchwo  - nmacchwo.  */
5500 GEN_MAC_HANDLER(nmacchwo, 0x0E, 0x15);
5501 /* nmacchws  - nmacchws.  */
5502 GEN_MAC_HANDLER(nmacchws, 0x0E, 0x07);
5503 /* nmacchwso - nmacchwso. */
5504 GEN_MAC_HANDLER(nmacchwso, 0x0E, 0x17);
5505 /* nmachhw   - nmachhw.   */
5506 GEN_MAC_HANDLER(nmachhw, 0x0E, 0x01);
5507 /* nmachhwo  - nmachhwo.  */
5508 GEN_MAC_HANDLER(nmachhwo, 0x0E, 0x11);
5509 /* nmachhws  - nmachhws.  */
5510 GEN_MAC_HANDLER(nmachhws, 0x0E, 0x03);
5511 /* nmachhwso - nmachhwso. */
5512 GEN_MAC_HANDLER(nmachhwso, 0x0E, 0x13);
5513 /* nmaclhw   - nmaclhw.   */
5514 GEN_MAC_HANDLER(nmaclhw, 0x0E, 0x0D);
5515 /* nmaclhwo  - nmaclhwo.  */
5516 GEN_MAC_HANDLER(nmaclhwo, 0x0E, 0x1D);
5517 /* nmaclhws  - nmaclhws.  */
5518 GEN_MAC_HANDLER(nmaclhws, 0x0E, 0x0F);
5519 /* nmaclhwso - nmaclhwso. */
5520 GEN_MAC_HANDLER(nmaclhwso, 0x0E, 0x1F);
5521
5522 /* mulchw  - mulchw.  */
5523 GEN_MAC_HANDLER(mulchw, 0x08, 0x05);
5524 /* mulchwu - mulchwu. */
5525 GEN_MAC_HANDLER(mulchwu, 0x08, 0x04);
5526 /* mulhhw  - mulhhw.  */
5527 GEN_MAC_HANDLER(mulhhw, 0x08, 0x01);
5528 /* mulhhwu - mulhhwu. */
5529 GEN_MAC_HANDLER(mulhhwu, 0x08, 0x00);
5530 /* mullhw  - mullhw.  */
5531 GEN_MAC_HANDLER(mullhw, 0x08, 0x0D);
5532 /* mullhwu - mullhwu. */
5533 GEN_MAC_HANDLER(mullhwu, 0x08, 0x0C);
5534
5535 /* mfdcr */
5536 static void gen_mfdcr(DisasContext *ctx)
5537 {
5538 #if defined(CONFIG_USER_ONLY)
5539     GEN_PRIV;
5540 #else
5541     TCGv dcrn;
5542
5543     CHK_SV;
5544     dcrn = tcg_const_tl(SPR(ctx->opcode));
5545     gen_helper_load_dcr(cpu_gpr[rD(ctx->opcode)], cpu_env, dcrn);
5546     tcg_temp_free(dcrn);
5547 #endif /* defined(CONFIG_USER_ONLY) */
5548 }
5549
5550 /* mtdcr */
5551 static void gen_mtdcr(DisasContext *ctx)
5552 {
5553 #if defined(CONFIG_USER_ONLY)
5554     GEN_PRIV;
5555 #else
5556     TCGv dcrn;
5557
5558     CHK_SV;
5559     dcrn = tcg_const_tl(SPR(ctx->opcode));
5560     gen_helper_store_dcr(cpu_env, dcrn, cpu_gpr[rS(ctx->opcode)]);
5561     tcg_temp_free(dcrn);
5562 #endif /* defined(CONFIG_USER_ONLY) */
5563 }
5564
5565 /* mfdcrx */
5566 /* XXX: not implemented on 440 ? */
5567 static void gen_mfdcrx(DisasContext *ctx)
5568 {
5569 #if defined(CONFIG_USER_ONLY)
5570     GEN_PRIV;
5571 #else
5572     CHK_SV;
5573     gen_helper_load_dcr(cpu_gpr[rD(ctx->opcode)], cpu_env,
5574                         cpu_gpr[rA(ctx->opcode)]);
5575     /* Note: Rc update flag set leads to undefined state of Rc0 */
5576 #endif /* defined(CONFIG_USER_ONLY) */
5577 }
5578
5579 /* mtdcrx */
5580 /* XXX: not implemented on 440 ? */
5581 static void gen_mtdcrx(DisasContext *ctx)
5582 {
5583 #if defined(CONFIG_USER_ONLY)
5584     GEN_PRIV;
5585 #else
5586     CHK_SV;
5587     gen_helper_store_dcr(cpu_env, cpu_gpr[rA(ctx->opcode)],
5588                          cpu_gpr[rS(ctx->opcode)]);
5589     /* Note: Rc update flag set leads to undefined state of Rc0 */
5590 #endif /* defined(CONFIG_USER_ONLY) */
5591 }
5592
5593 /* mfdcrux (PPC 460) : user-mode access to DCR */
5594 static void gen_mfdcrux(DisasContext *ctx)
5595 {
5596     gen_helper_load_dcr(cpu_gpr[rD(ctx->opcode)], cpu_env,
5597                         cpu_gpr[rA(ctx->opcode)]);
5598     /* Note: Rc update flag set leads to undefined state of Rc0 */
5599 }
5600
5601 /* mtdcrux (PPC 460) : user-mode access to DCR */
5602 static void gen_mtdcrux(DisasContext *ctx)
5603 {
5604     gen_helper_store_dcr(cpu_env, cpu_gpr[rA(ctx->opcode)],
5605                          cpu_gpr[rS(ctx->opcode)]);
5606     /* Note: Rc update flag set leads to undefined state of Rc0 */
5607 }
5608
5609 /* dccci */
5610 static void gen_dccci(DisasContext *ctx)
5611 {
5612     CHK_SV;
5613     /* interpreted as no-op */
5614 }
5615
5616 /* dcread */
5617 static void gen_dcread(DisasContext *ctx)
5618 {
5619 #if defined(CONFIG_USER_ONLY)
5620     GEN_PRIV;
5621 #else
5622     TCGv EA, val;
5623
5624     CHK_SV;
5625     gen_set_access_type(ctx, ACCESS_CACHE);
5626     EA = tcg_temp_new();
5627     gen_addr_reg_index(ctx, EA);
5628     val = tcg_temp_new();
5629     gen_qemu_ld32u(ctx, val, EA);
5630     tcg_temp_free(val);
5631     tcg_gen_mov_tl(cpu_gpr[rD(ctx->opcode)], EA);
5632     tcg_temp_free(EA);
5633 #endif /* defined(CONFIG_USER_ONLY) */
5634 }
5635
5636 /* icbt */
5637 static void gen_icbt_40x(DisasContext *ctx)
5638 {
5639     /* interpreted as no-op */
5640     /* XXX: specification say this is treated as a load by the MMU
5641      *      but does not generate any exception
5642      */
5643 }
5644
5645 /* iccci */
5646 static void gen_iccci(DisasContext *ctx)
5647 {
5648     CHK_SV;
5649     /* interpreted as no-op */
5650 }
5651
5652 /* icread */
5653 static void gen_icread(DisasContext *ctx)
5654 {
5655     CHK_SV;
5656     /* interpreted as no-op */
5657 }
5658
5659 /* rfci (supervisor only) */
5660 static void gen_rfci_40x(DisasContext *ctx)
5661 {
5662 #if defined(CONFIG_USER_ONLY)
5663     GEN_PRIV;
5664 #else
5665     CHK_SV;
5666     /* Restore CPU state */
5667     gen_helper_40x_rfci(cpu_env);
5668     gen_sync_exception(ctx);
5669 #endif /* defined(CONFIG_USER_ONLY) */
5670 }
5671
5672 static void gen_rfci(DisasContext *ctx)
5673 {
5674 #if defined(CONFIG_USER_ONLY)
5675     GEN_PRIV;
5676 #else
5677     CHK_SV;
5678     /* Restore CPU state */
5679     gen_helper_rfci(cpu_env);
5680     gen_sync_exception(ctx);
5681 #endif /* defined(CONFIG_USER_ONLY) */
5682 }
5683
5684 /* BookE specific */
5685
5686 /* XXX: not implemented on 440 ? */
5687 static void gen_rfdi(DisasContext *ctx)
5688 {
5689 #if defined(CONFIG_USER_ONLY)
5690     GEN_PRIV;
5691 #else
5692     CHK_SV;
5693     /* Restore CPU state */
5694     gen_helper_rfdi(cpu_env);
5695     gen_sync_exception(ctx);
5696 #endif /* defined(CONFIG_USER_ONLY) */
5697 }
5698
5699 /* XXX: not implemented on 440 ? */
5700 static void gen_rfmci(DisasContext *ctx)
5701 {
5702 #if defined(CONFIG_USER_ONLY)
5703     GEN_PRIV;
5704 #else
5705     CHK_SV;
5706     /* Restore CPU state */
5707     gen_helper_rfmci(cpu_env);
5708     gen_sync_exception(ctx);
5709 #endif /* defined(CONFIG_USER_ONLY) */
5710 }
5711
5712 /* TLB management - PowerPC 405 implementation */
5713
5714 /* tlbre */
5715 static void gen_tlbre_40x(DisasContext *ctx)
5716 {
5717 #if defined(CONFIG_USER_ONLY)
5718     GEN_PRIV;
5719 #else
5720     CHK_SV;
5721     switch (rB(ctx->opcode)) {
5722     case 0:
5723         gen_helper_4xx_tlbre_hi(cpu_gpr[rD(ctx->opcode)], cpu_env,
5724                                 cpu_gpr[rA(ctx->opcode)]);
5725         break;
5726     case 1:
5727         gen_helper_4xx_tlbre_lo(cpu_gpr[rD(ctx->opcode)], cpu_env,
5728                                 cpu_gpr[rA(ctx->opcode)]);
5729         break;
5730     default:
5731         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
5732         break;
5733     }
5734 #endif /* defined(CONFIG_USER_ONLY) */
5735 }
5736
5737 /* tlbsx - tlbsx. */
5738 static void gen_tlbsx_40x(DisasContext *ctx)
5739 {
5740 #if defined(CONFIG_USER_ONLY)
5741     GEN_PRIV;
5742 #else
5743     TCGv t0;
5744
5745     CHK_SV;
5746     t0 = tcg_temp_new();
5747     gen_addr_reg_index(ctx, t0);
5748     gen_helper_4xx_tlbsx(cpu_gpr[rD(ctx->opcode)], cpu_env, t0);
5749     tcg_temp_free(t0);
5750     if (Rc(ctx->opcode)) {
5751         TCGLabel *l1 = gen_new_label();
5752         tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_so);
5753         tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[rD(ctx->opcode)], -1, l1);
5754         tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 0x02);
5755         gen_set_label(l1);
5756     }
5757 #endif /* defined(CONFIG_USER_ONLY) */
5758 }
5759
5760 /* tlbwe */
5761 static void gen_tlbwe_40x(DisasContext *ctx)
5762 {
5763 #if defined(CONFIG_USER_ONLY)
5764     GEN_PRIV;
5765 #else
5766     CHK_SV;
5767
5768     switch (rB(ctx->opcode)) {
5769     case 0:
5770         gen_helper_4xx_tlbwe_hi(cpu_env, cpu_gpr[rA(ctx->opcode)],
5771                                 cpu_gpr[rS(ctx->opcode)]);
5772         break;
5773     case 1:
5774         gen_helper_4xx_tlbwe_lo(cpu_env, cpu_gpr[rA(ctx->opcode)],
5775                                 cpu_gpr[rS(ctx->opcode)]);
5776         break;
5777     default:
5778         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
5779         break;
5780     }
5781 #endif /* defined(CONFIG_USER_ONLY) */
5782 }
5783
5784 /* TLB management - PowerPC 440 implementation */
5785
5786 /* tlbre */
5787 static void gen_tlbre_440(DisasContext *ctx)
5788 {
5789 #if defined(CONFIG_USER_ONLY)
5790     GEN_PRIV;
5791 #else
5792     CHK_SV;
5793
5794     switch (rB(ctx->opcode)) {
5795     case 0:
5796     case 1:
5797     case 2:
5798         {
5799             TCGv_i32 t0 = tcg_const_i32(rB(ctx->opcode));
5800             gen_helper_440_tlbre(cpu_gpr[rD(ctx->opcode)], cpu_env,
5801                                  t0, cpu_gpr[rA(ctx->opcode)]);
5802             tcg_temp_free_i32(t0);
5803         }
5804         break;
5805     default:
5806         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
5807         break;
5808     }
5809 #endif /* defined(CONFIG_USER_ONLY) */
5810 }
5811
5812 /* tlbsx - tlbsx. */
5813 static void gen_tlbsx_440(DisasContext *ctx)
5814 {
5815 #if defined(CONFIG_USER_ONLY)
5816     GEN_PRIV;
5817 #else
5818     TCGv t0;
5819
5820     CHK_SV;
5821     t0 = tcg_temp_new();
5822     gen_addr_reg_index(ctx, t0);
5823     gen_helper_440_tlbsx(cpu_gpr[rD(ctx->opcode)], cpu_env, t0);
5824     tcg_temp_free(t0);
5825     if (Rc(ctx->opcode)) {
5826         TCGLabel *l1 = gen_new_label();
5827         tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_so);
5828         tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_gpr[rD(ctx->opcode)], -1, l1);
5829         tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 0x02);
5830         gen_set_label(l1);
5831     }
5832 #endif /* defined(CONFIG_USER_ONLY) */
5833 }
5834
5835 /* tlbwe */
5836 static void gen_tlbwe_440(DisasContext *ctx)
5837 {
5838 #if defined(CONFIG_USER_ONLY)
5839     GEN_PRIV;
5840 #else
5841     CHK_SV;
5842     switch (rB(ctx->opcode)) {
5843     case 0:
5844     case 1:
5845     case 2:
5846         {
5847             TCGv_i32 t0 = tcg_const_i32(rB(ctx->opcode));
5848             gen_helper_440_tlbwe(cpu_env, t0, cpu_gpr[rA(ctx->opcode)],
5849                                  cpu_gpr[rS(ctx->opcode)]);
5850             tcg_temp_free_i32(t0);
5851         }
5852         break;
5853     default:
5854         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
5855         break;
5856     }
5857 #endif /* defined(CONFIG_USER_ONLY) */
5858 }
5859
5860 /* TLB management - PowerPC BookE 2.06 implementation */
5861
5862 /* tlbre */
5863 static void gen_tlbre_booke206(DisasContext *ctx)
5864 {
5865  #if defined(CONFIG_USER_ONLY)
5866     GEN_PRIV;
5867 #else
5868    CHK_SV;
5869     gen_helper_booke206_tlbre(cpu_env);
5870 #endif /* defined(CONFIG_USER_ONLY) */
5871 }
5872
5873 /* tlbsx - tlbsx. */
5874 static void gen_tlbsx_booke206(DisasContext *ctx)
5875 {
5876 #if defined(CONFIG_USER_ONLY)
5877     GEN_PRIV;
5878 #else
5879     TCGv t0;
5880
5881     CHK_SV;
5882     if (rA(ctx->opcode)) {
5883         t0 = tcg_temp_new();
5884         tcg_gen_mov_tl(t0, cpu_gpr[rD(ctx->opcode)]);
5885     } else {
5886         t0 = tcg_const_tl(0);
5887     }
5888
5889     tcg_gen_add_tl(t0, t0, cpu_gpr[rB(ctx->opcode)]);
5890     gen_helper_booke206_tlbsx(cpu_env, t0);
5891     tcg_temp_free(t0);
5892 #endif /* defined(CONFIG_USER_ONLY) */
5893 }
5894
5895 /* tlbwe */
5896 static void gen_tlbwe_booke206(DisasContext *ctx)
5897 {
5898 #if defined(CONFIG_USER_ONLY)
5899     GEN_PRIV;
5900 #else
5901     CHK_SV;
5902     gen_helper_booke206_tlbwe(cpu_env);
5903 #endif /* defined(CONFIG_USER_ONLY) */
5904 }
5905
5906 static void gen_tlbivax_booke206(DisasContext *ctx)
5907 {
5908 #if defined(CONFIG_USER_ONLY)
5909     GEN_PRIV;
5910 #else
5911     TCGv t0;
5912
5913     CHK_SV;
5914     t0 = tcg_temp_new();
5915     gen_addr_reg_index(ctx, t0);
5916     gen_helper_booke206_tlbivax(cpu_env, t0);
5917     tcg_temp_free(t0);
5918 #endif /* defined(CONFIG_USER_ONLY) */
5919 }
5920
5921 static void gen_tlbilx_booke206(DisasContext *ctx)
5922 {
5923 #if defined(CONFIG_USER_ONLY)
5924     GEN_PRIV;
5925 #else
5926     TCGv t0;
5927
5928     CHK_SV;
5929     t0 = tcg_temp_new();
5930     gen_addr_reg_index(ctx, t0);
5931
5932     switch((ctx->opcode >> 21) & 0x3) {
5933     case 0:
5934         gen_helper_booke206_tlbilx0(cpu_env, t0);
5935         break;
5936     case 1:
5937         gen_helper_booke206_tlbilx1(cpu_env, t0);
5938         break;
5939     case 3:
5940         gen_helper_booke206_tlbilx3(cpu_env, t0);
5941         break;
5942     default:
5943         gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
5944         break;
5945     }
5946
5947     tcg_temp_free(t0);
5948 #endif /* defined(CONFIG_USER_ONLY) */
5949 }
5950
5951
5952 /* wrtee */
5953 static void gen_wrtee(DisasContext *ctx)
5954 {
5955 #if defined(CONFIG_USER_ONLY)
5956     GEN_PRIV;
5957 #else
5958     TCGv t0;
5959
5960     CHK_SV;
5961     t0 = tcg_temp_new();
5962     tcg_gen_andi_tl(t0, cpu_gpr[rD(ctx->opcode)], (1 << MSR_EE));
5963     tcg_gen_andi_tl(cpu_msr, cpu_msr, ~(1 << MSR_EE));
5964     tcg_gen_or_tl(cpu_msr, cpu_msr, t0);
5965     tcg_temp_free(t0);
5966     /* Stop translation to have a chance to raise an exception
5967      * if we just set msr_ee to 1
5968      */
5969     gen_stop_exception(ctx);
5970 #endif /* defined(CONFIG_USER_ONLY) */
5971 }
5972
5973 /* wrteei */
5974 static void gen_wrteei(DisasContext *ctx)
5975 {
5976 #if defined(CONFIG_USER_ONLY)
5977     GEN_PRIV;
5978 #else
5979     CHK_SV;
5980     if (ctx->opcode & 0x00008000) {
5981         tcg_gen_ori_tl(cpu_msr, cpu_msr, (1 << MSR_EE));
5982         /* Stop translation to have a chance to raise an exception */
5983         gen_stop_exception(ctx);
5984     } else {
5985         tcg_gen_andi_tl(cpu_msr, cpu_msr, ~(1 << MSR_EE));
5986     }
5987 #endif /* defined(CONFIG_USER_ONLY) */
5988 }
5989
5990 /* PowerPC 440 specific instructions */
5991
5992 /* dlmzb */
5993 static void gen_dlmzb(DisasContext *ctx)
5994 {
5995     TCGv_i32 t0 = tcg_const_i32(Rc(ctx->opcode));
5996     gen_helper_dlmzb(cpu_gpr[rA(ctx->opcode)], cpu_env,
5997                      cpu_gpr[rS(ctx->opcode)], cpu_gpr[rB(ctx->opcode)], t0);
5998     tcg_temp_free_i32(t0);
5999 }
6000
6001 /* mbar replaces eieio on 440 */
6002 static void gen_mbar(DisasContext *ctx)
6003 {
6004     /* interpreted as no-op */
6005 }
6006
6007 /* msync replaces sync on 440 */
6008 static void gen_msync_4xx(DisasContext *ctx)
6009 {
6010     /* interpreted as no-op */
6011 }
6012
6013 /* icbt */
6014 static void gen_icbt_440(DisasContext *ctx)
6015 {
6016     /* interpreted as no-op */
6017     /* XXX: specification say this is treated as a load by the MMU
6018      *      but does not generate any exception
6019      */
6020 }
6021
6022 /* Embedded.Processor Control */
6023
6024 static void gen_msgclr(DisasContext *ctx)
6025 {
6026 #if defined(CONFIG_USER_ONLY)
6027     GEN_PRIV;
6028 #else
6029     CHK_SV;
6030     gen_helper_msgclr(cpu_env, cpu_gpr[rB(ctx->opcode)]);
6031 #endif /* defined(CONFIG_USER_ONLY) */
6032 }
6033
6034 static void gen_msgsnd(DisasContext *ctx)
6035 {
6036 #if defined(CONFIG_USER_ONLY)
6037     GEN_PRIV;
6038 #else
6039     CHK_SV;
6040     gen_helper_msgsnd(cpu_gpr[rB(ctx->opcode)]);
6041 #endif /* defined(CONFIG_USER_ONLY) */
6042 }
6043
6044
6045 #if defined(TARGET_PPC64)
6046 static void gen_maddld(DisasContext *ctx)
6047 {
6048     TCGv_i64 t1 = tcg_temp_new_i64();
6049
6050     tcg_gen_mul_i64(t1, cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
6051     tcg_gen_add_i64(cpu_gpr[rD(ctx->opcode)], t1, cpu_gpr[rC(ctx->opcode)]);
6052     tcg_temp_free_i64(t1);
6053 }
6054
6055 /* maddhd maddhdu */
6056 static void gen_maddhd_maddhdu(DisasContext *ctx)
6057 {
6058     TCGv_i64 lo = tcg_temp_new_i64();
6059     TCGv_i64 hi = tcg_temp_new_i64();
6060     TCGv_i64 t1 = tcg_temp_new_i64();
6061
6062     if (Rc(ctx->opcode)) {
6063         tcg_gen_mulu2_i64(lo, hi, cpu_gpr[rA(ctx->opcode)],
6064                           cpu_gpr[rB(ctx->opcode)]);
6065         tcg_gen_movi_i64(t1, 0);
6066     } else {
6067         tcg_gen_muls2_i64(lo, hi, cpu_gpr[rA(ctx->opcode)],
6068                           cpu_gpr[rB(ctx->opcode)]);
6069         tcg_gen_sari_i64(t1, cpu_gpr[rC(ctx->opcode)], 63);
6070     }
6071     tcg_gen_add2_i64(t1, cpu_gpr[rD(ctx->opcode)], lo, hi,
6072                      cpu_gpr[rC(ctx->opcode)], t1);
6073     tcg_temp_free_i64(lo);
6074     tcg_temp_free_i64(hi);
6075     tcg_temp_free_i64(t1);
6076 }
6077 #endif /* defined(TARGET_PPC64) */
6078
6079 static void gen_tbegin(DisasContext *ctx)
6080 {
6081     if (unlikely(!ctx->tm_enabled)) {
6082         gen_exception_err(ctx, POWERPC_EXCP_FU, FSCR_IC_TM);
6083         return;
6084     }
6085     gen_helper_tbegin(cpu_env);
6086 }
6087
6088 #define GEN_TM_NOOP(name)                                      \
6089 static inline void gen_##name(DisasContext *ctx)               \
6090 {                                                              \
6091     if (unlikely(!ctx->tm_enabled)) {                          \
6092         gen_exception_err(ctx, POWERPC_EXCP_FU, FSCR_IC_TM);   \
6093         return;                                                \
6094     }                                                          \
6095     /* Because tbegin always fails in QEMU, these user         \
6096      * space instructions all have a simple implementation:    \
6097      *                                                         \
6098      *     CR[0] = 0b0 || MSR[TS] || 0b0                       \
6099      *           = 0b0 || 0b00    || 0b0                       \
6100      */                                                        \
6101     tcg_gen_movi_i32(cpu_crf[0], 0);                           \
6102 }
6103
6104 GEN_TM_NOOP(tend);
6105 GEN_TM_NOOP(tabort);
6106 GEN_TM_NOOP(tabortwc);
6107 GEN_TM_NOOP(tabortwci);
6108 GEN_TM_NOOP(tabortdc);
6109 GEN_TM_NOOP(tabortdci);
6110 GEN_TM_NOOP(tsr);
6111
6112 static void gen_tcheck(DisasContext *ctx)
6113 {
6114     if (unlikely(!ctx->tm_enabled)) {
6115         gen_exception_err(ctx, POWERPC_EXCP_FU, FSCR_IC_TM);
6116         return;
6117     }
6118     /* Because tbegin always fails, the tcheck implementation
6119      * is simple:
6120      *
6121      * CR[CRF] = TDOOMED || MSR[TS] || 0b0
6122      *         = 0b1 || 0b00 || 0b0
6123      */
6124     tcg_gen_movi_i32(cpu_crf[crfD(ctx->opcode)], 0x8);
6125 }
6126
6127 #if defined(CONFIG_USER_ONLY)
6128 #define GEN_TM_PRIV_NOOP(name)                                 \
6129 static inline void gen_##name(DisasContext *ctx)               \
6130 {                                                              \
6131     gen_priv_exception(ctx, POWERPC_EXCP_PRIV_OPC);           \
6132 }
6133
6134 #else
6135
6136 #define GEN_TM_PRIV_NOOP(name)                                 \
6137 static inline void gen_##name(DisasContext *ctx)               \
6138 {                                                              \
6139     CHK_SV;                                                    \
6140     if (unlikely(!ctx->tm_enabled)) {                          \
6141         gen_exception_err(ctx, POWERPC_EXCP_FU, FSCR_IC_TM);   \
6142         return;                                                \
6143     }                                                          \
6144     /* Because tbegin always fails, the implementation is      \
6145      * simple:                                                 \
6146      *                                                         \
6147      *   CR[0] = 0b0 || MSR[TS] || 0b0                         \
6148      *         = 0b0 || 0b00 | 0b0                             \
6149      */                                                        \
6150     tcg_gen_movi_i32(cpu_crf[0], 0);                           \
6151 }
6152
6153 #endif
6154
6155 GEN_TM_PRIV_NOOP(treclaim);
6156 GEN_TM_PRIV_NOOP(trechkpt);
6157
6158 #include "translate/fp-impl.inc.c"
6159
6160 #include "translate/vmx-impl.inc.c"
6161
6162 #include "translate/vsx-impl.inc.c"
6163
6164 #include "translate/dfp-impl.inc.c"
6165
6166 #include "translate/spe-impl.inc.c"
6167
6168 static opcode_t opcodes[] = {
6169 GEN_HANDLER(invalid, 0x00, 0x00, 0x00, 0xFFFFFFFF, PPC_NONE),
6170 GEN_HANDLER(cmp, 0x1F, 0x00, 0x00, 0x00400000, PPC_INTEGER),
6171 GEN_HANDLER(cmpi, 0x0B, 0xFF, 0xFF, 0x00400000, PPC_INTEGER),
6172 GEN_HANDLER(cmpl, 0x1F, 0x00, 0x01, 0x00400000, PPC_INTEGER),
6173 GEN_HANDLER(cmpli, 0x0A, 0xFF, 0xFF, 0x00400000, PPC_INTEGER),
6174 #if defined(TARGET_PPC64)
6175 GEN_HANDLER_E(cmpeqb, 0x1F, 0x00, 0x07, 0x00600000, PPC_NONE, PPC2_ISA300),
6176 #endif
6177 GEN_HANDLER_E(cmpb, 0x1F, 0x1C, 0x0F, 0x00000001, PPC_NONE, PPC2_ISA205),
6178 GEN_HANDLER_E(cmprb, 0x1F, 0x00, 0x06, 0x00400001, PPC_NONE, PPC2_ISA300),
6179 GEN_HANDLER(isel, 0x1F, 0x0F, 0xFF, 0x00000001, PPC_ISEL),
6180 GEN_HANDLER(addi, 0x0E, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6181 GEN_HANDLER(addic, 0x0C, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6182 GEN_HANDLER2(addic_, "addic.", 0x0D, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6183 GEN_HANDLER(addis, 0x0F, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6184 GEN_HANDLER_E(addpcis, 0x13, 0x2, 0xFF, 0x00000000, PPC_NONE, PPC2_ISA300),
6185 GEN_HANDLER(mulhw, 0x1F, 0x0B, 0x02, 0x00000400, PPC_INTEGER),
6186 GEN_HANDLER(mulhwu, 0x1F, 0x0B, 0x00, 0x00000400, PPC_INTEGER),
6187 GEN_HANDLER(mullw, 0x1F, 0x0B, 0x07, 0x00000000, PPC_INTEGER),
6188 GEN_HANDLER(mullwo, 0x1F, 0x0B, 0x17, 0x00000000, PPC_INTEGER),
6189 GEN_HANDLER(mulli, 0x07, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6190 #if defined(TARGET_PPC64)
6191 GEN_HANDLER(mulld, 0x1F, 0x09, 0x07, 0x00000000, PPC_64B),
6192 #endif
6193 GEN_HANDLER(neg, 0x1F, 0x08, 0x03, 0x0000F800, PPC_INTEGER),
6194 GEN_HANDLER(nego, 0x1F, 0x08, 0x13, 0x0000F800, PPC_INTEGER),
6195 GEN_HANDLER(subfic, 0x08, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6196 GEN_HANDLER2(andi_, "andi.", 0x1C, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6197 GEN_HANDLER2(andis_, "andis.", 0x1D, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6198 GEN_HANDLER(cntlzw, 0x1F, 0x1A, 0x00, 0x00000000, PPC_INTEGER),
6199 GEN_HANDLER_E(cnttzw, 0x1F, 0x1A, 0x10, 0x00000000, PPC_NONE, PPC2_ISA300),
6200 GEN_HANDLER(or, 0x1F, 0x1C, 0x0D, 0x00000000, PPC_INTEGER),
6201 GEN_HANDLER(xor, 0x1F, 0x1C, 0x09, 0x00000000, PPC_INTEGER),
6202 GEN_HANDLER(ori, 0x18, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6203 GEN_HANDLER(oris, 0x19, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6204 GEN_HANDLER(xori, 0x1A, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6205 GEN_HANDLER(xoris, 0x1B, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6206 GEN_HANDLER(popcntb, 0x1F, 0x1A, 0x03, 0x0000F801, PPC_POPCNTB),
6207 GEN_HANDLER(popcntw, 0x1F, 0x1A, 0x0b, 0x0000F801, PPC_POPCNTWD),
6208 GEN_HANDLER_E(prtyw, 0x1F, 0x1A, 0x04, 0x0000F801, PPC_NONE, PPC2_ISA205),
6209 #if defined(TARGET_PPC64)
6210 GEN_HANDLER(popcntd, 0x1F, 0x1A, 0x0F, 0x0000F801, PPC_POPCNTWD),
6211 GEN_HANDLER(cntlzd, 0x1F, 0x1A, 0x01, 0x00000000, PPC_64B),
6212 GEN_HANDLER_E(cnttzd, 0x1F, 0x1A, 0x11, 0x00000000, PPC_NONE, PPC2_ISA300),
6213 GEN_HANDLER_E(prtyd, 0x1F, 0x1A, 0x05, 0x0000F801, PPC_NONE, PPC2_ISA205),
6214 GEN_HANDLER_E(bpermd, 0x1F, 0x1C, 0x07, 0x00000001, PPC_NONE, PPC2_PERM_ISA206),
6215 #endif
6216 GEN_HANDLER(rlwimi, 0x14, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6217 GEN_HANDLER(rlwinm, 0x15, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6218 GEN_HANDLER(rlwnm, 0x17, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6219 GEN_HANDLER(slw, 0x1F, 0x18, 0x00, 0x00000000, PPC_INTEGER),
6220 GEN_HANDLER(sraw, 0x1F, 0x18, 0x18, 0x00000000, PPC_INTEGER),
6221 GEN_HANDLER(srawi, 0x1F, 0x18, 0x19, 0x00000000, PPC_INTEGER),
6222 GEN_HANDLER(srw, 0x1F, 0x18, 0x10, 0x00000000, PPC_INTEGER),
6223 #if defined(TARGET_PPC64)
6224 GEN_HANDLER(sld, 0x1F, 0x1B, 0x00, 0x00000000, PPC_64B),
6225 GEN_HANDLER(srad, 0x1F, 0x1A, 0x18, 0x00000000, PPC_64B),
6226 GEN_HANDLER2(sradi0, "sradi", 0x1F, 0x1A, 0x19, 0x00000000, PPC_64B),
6227 GEN_HANDLER2(sradi1, "sradi", 0x1F, 0x1B, 0x19, 0x00000000, PPC_64B),
6228 GEN_HANDLER(srd, 0x1F, 0x1B, 0x10, 0x00000000, PPC_64B),
6229 GEN_HANDLER2_E(extswsli0, "extswsli", 0x1F, 0x1A, 0x1B, 0x00000000,
6230                PPC_NONE, PPC2_ISA300),
6231 GEN_HANDLER2_E(extswsli1, "extswsli", 0x1F, 0x1B, 0x1B, 0x00000000,
6232                PPC_NONE, PPC2_ISA300),
6233 #endif
6234 #if defined(TARGET_PPC64)
6235 GEN_HANDLER(ld, 0x3A, 0xFF, 0xFF, 0x00000000, PPC_64B),
6236 GEN_HANDLER(lq, 0x38, 0xFF, 0xFF, 0x00000000, PPC_64BX),
6237 GEN_HANDLER(std, 0x3E, 0xFF, 0xFF, 0x00000000, PPC_64B),
6238 #endif
6239 GEN_HANDLER(lmw, 0x2E, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6240 GEN_HANDLER(stmw, 0x2F, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
6241 GEN_HANDLER(lswi, 0x1F, 0x15, 0x12, 0x00000001, PPC_STRING),
6242 GEN_HANDLER(lswx, 0x1F, 0x15, 0x10, 0x00000001, PPC_STRING),
6243 GEN_HANDLER(stswi, 0x1F, 0x15, 0x16, 0x00000001, PPC_STRING),
6244 GEN_HANDLER(stswx, 0x1F, 0x15, 0x14, 0x00000001, PPC_STRING),
6245 GEN_HANDLER(eieio, 0x1F, 0x16, 0x1A, 0x03FFF801, PPC_MEM_EIEIO),
6246 GEN_HANDLER(isync, 0x13, 0x16, 0x04, 0x03FFF801, PPC_MEM),
6247 GEN_HANDLER_E(lbarx, 0x1F, 0x14, 0x01, 0, PPC_NONE, PPC2_ATOMIC_ISA206),
6248 GEN_HANDLER_E(lharx, 0x1F, 0x14, 0x03, 0, PPC_NONE, PPC2_ATOMIC_ISA206),
6249 GEN_HANDLER(lwarx, 0x1F, 0x14, 0x00, 0x00000000, PPC_RES),
6250 GEN_HANDLER_E(stbcx_, 0x1F, 0x16, 0x15, 0, PPC_NONE, PPC2_ATOMIC_ISA206),
6251 GEN_HANDLER_E(sthcx_, 0x1F, 0x16, 0x16, 0, PPC_NONE, PPC2_ATOMIC_ISA206),
6252 GEN_HANDLER2(stwcx_, "stwcx.", 0x1F, 0x16, 0x04, 0x00000000, PPC_RES),
6253 #if defined(TARGET_PPC64)
6254 GEN_HANDLER(ldarx, 0x1F, 0x14, 0x02, 0x00000000, PPC_64B),
6255 GEN_HANDLER_E(lqarx, 0x1F, 0x14, 0x08, 0, PPC_NONE, PPC2_LSQ_ISA207),
6256 GEN_HANDLER2(stdcx_, "stdcx.", 0x1F, 0x16, 0x06, 0x00000000, PPC_64B),
6257 GEN_HANDLER_E(stqcx_, 0x1F, 0x16, 0x05, 0, PPC_NONE, PPC2_LSQ_ISA207),
6258 #endif
6259 GEN_HANDLER(sync, 0x1F, 0x16, 0x12, 0x039FF801, PPC_MEM_SYNC),
6260 GEN_HANDLER(wait, 0x1F, 0x1E, 0x01, 0x03FFF801, PPC_WAIT),
6261 GEN_HANDLER(b, 0x12, 0xFF, 0xFF, 0x00000000, PPC_FLOW),
6262 GEN_HANDLER(bc, 0x10, 0xFF, 0xFF, 0x00000000, PPC_FLOW),
6263 GEN_HANDLER(bcctr, 0x13, 0x10, 0x10, 0x00000000, PPC_FLOW),
6264 GEN_HANDLER(bclr, 0x13, 0x10, 0x00, 0x00000000, PPC_FLOW),
6265 GEN_HANDLER_E(bctar, 0x13, 0x10, 0x11, 0, PPC_NONE, PPC2_BCTAR_ISA207),
6266 GEN_HANDLER(mcrf, 0x13, 0x00, 0xFF, 0x00000001, PPC_INTEGER),
6267 GEN_HANDLER(rfi, 0x13, 0x12, 0x01, 0x03FF8001, PPC_FLOW),
6268 #if defined(TARGET_PPC64)
6269 GEN_HANDLER(rfid, 0x13, 0x12, 0x00, 0x03FF8001, PPC_64B),
6270 GEN_HANDLER_E(doze, 0x13, 0x12, 0x0c, 0x03FFF801, PPC_NONE, PPC2_PM_ISA206),
6271 GEN_HANDLER_E(nap, 0x13, 0x12, 0x0d, 0x03FFF801, PPC_NONE, PPC2_PM_ISA206),
6272 GEN_HANDLER_E(sleep, 0x13, 0x12, 0x0e, 0x03FFF801, PPC_NONE, PPC2_PM_ISA206),
6273 GEN_HANDLER_E(rvwinkle, 0x13, 0x12, 0x0f, 0x03FFF801, PPC_NONE, PPC2_PM_ISA206),
6274 GEN_HANDLER(hrfid, 0x13, 0x12, 0x08, 0x03FF8001, PPC_64H),
6275 #endif
6276 GEN_HANDLER(sc, 0x11, 0xFF, 0xFF, 0x03FFF01D, PPC_FLOW),
6277 GEN_HANDLER(tw, 0x1F, 0x04, 0x00, 0x00000001, PPC_FLOW),
6278 GEN_HANDLER(twi, 0x03, 0xFF, 0xFF, 0x00000000, PPC_FLOW),
6279 #if defined(TARGET_PPC64)
6280 GEN_HANDLER(td, 0x1F, 0x04, 0x02, 0x00000001, PPC_64B),
6281 GEN_HANDLER(tdi, 0x02, 0xFF, 0xFF, 0x00000000, PPC_64B),
6282 #endif
6283 GEN_HANDLER(mcrxr, 0x1F, 0x00, 0x10, 0x007FF801, PPC_MISC),
6284 GEN_HANDLER(mfcr, 0x1F, 0x13, 0x00, 0x00000801, PPC_MISC),
6285 GEN_HANDLER(mfmsr, 0x1F, 0x13, 0x02, 0x001FF801, PPC_MISC),
6286 GEN_HANDLER(mfspr, 0x1F, 0x13, 0x0A, 0x00000001, PPC_MISC),
6287 GEN_HANDLER(mftb, 0x1F, 0x13, 0x0B, 0x00000001, PPC_MFTB),
6288 GEN_HANDLER(mtcrf, 0x1F, 0x10, 0x04, 0x00000801, PPC_MISC),
6289 #if defined(TARGET_PPC64)
6290 GEN_HANDLER(mtmsrd, 0x1F, 0x12, 0x05, 0x001EF801, PPC_64B),
6291 GEN_HANDLER_E(setb, 0x1F, 0x00, 0x04, 0x0003F801, PPC_NONE, PPC2_ISA300),
6292 #endif
6293 GEN_HANDLER(mtmsr, 0x1F, 0x12, 0x04, 0x001EF801, PPC_MISC),
6294 GEN_HANDLER(mtspr, 0x1F, 0x13, 0x0E, 0x00000000, PPC_MISC),
6295 GEN_HANDLER(dcbf, 0x1F, 0x16, 0x02, 0x03C00001, PPC_CACHE),
6296 GEN_HANDLER(dcbi, 0x1F, 0x16, 0x0E, 0x03E00001, PPC_CACHE),
6297 GEN_HANDLER(dcbst, 0x1F, 0x16, 0x01, 0x03E00001, PPC_CACHE),
6298 GEN_HANDLER(dcbt, 0x1F, 0x16, 0x08, 0x00000001, PPC_CACHE),
6299 GEN_HANDLER(dcbtst, 0x1F, 0x16, 0x07, 0x00000001, PPC_CACHE),
6300 GEN_HANDLER_E(dcbtls, 0x1F, 0x06, 0x05, 0x02000001, PPC_BOOKE, PPC2_BOOKE206),
6301 GEN_HANDLER(dcbz, 0x1F, 0x16, 0x1F, 0x03C00001, PPC_CACHE_DCBZ),
6302 GEN_HANDLER(dst, 0x1F, 0x16, 0x0A, 0x01800001, PPC_ALTIVEC),
6303 GEN_HANDLER(dstst, 0x1F, 0x16, 0x0B, 0x02000001, PPC_ALTIVEC),
6304 GEN_HANDLER(dss, 0x1F, 0x16, 0x19, 0x019FF801, PPC_ALTIVEC),
6305 GEN_HANDLER(icbi, 0x1F, 0x16, 0x1E, 0x03E00001, PPC_CACHE_ICBI),
6306 GEN_HANDLER(dcba, 0x1F, 0x16, 0x17, 0x03E00001, PPC_CACHE_DCBA),
6307 GEN_HANDLER(mfsr, 0x1F, 0x13, 0x12, 0x0010F801, PPC_SEGMENT),
6308 GEN_HANDLER(mfsrin, 0x1F, 0x13, 0x14, 0x001F0001, PPC_SEGMENT),
6309 GEN_HANDLER(mtsr, 0x1F, 0x12, 0x06, 0x0010F801, PPC_SEGMENT),
6310 GEN_HANDLER(mtsrin, 0x1F, 0x12, 0x07, 0x001F0001, PPC_SEGMENT),
6311 #if defined(TARGET_PPC64)
6312 GEN_HANDLER2(mfsr_64b, "mfsr", 0x1F, 0x13, 0x12, 0x0010F801, PPC_SEGMENT_64B),
6313 GEN_HANDLER2(mfsrin_64b, "mfsrin", 0x1F, 0x13, 0x14, 0x001F0001,
6314              PPC_SEGMENT_64B),
6315 GEN_HANDLER2(mtsr_64b, "mtsr", 0x1F, 0x12, 0x06, 0x0010F801, PPC_SEGMENT_64B),
6316 GEN_HANDLER2(mtsrin_64b, "mtsrin", 0x1F, 0x12, 0x07, 0x001F0001,
6317              PPC_SEGMENT_64B),
6318 GEN_HANDLER2(slbmte, "slbmte", 0x1F, 0x12, 0x0C, 0x001F0001, PPC_SEGMENT_64B),
6319 GEN_HANDLER2(slbmfee, "slbmfee", 0x1F, 0x13, 0x1C, 0x001F0001, PPC_SEGMENT_64B),
6320 GEN_HANDLER2(slbmfev, "slbmfev", 0x1F, 0x13, 0x1A, 0x001F0001, PPC_SEGMENT_64B),
6321 GEN_HANDLER2(slbfee_, "slbfee.", 0x1F, 0x13, 0x1E, 0x001F0000, PPC_SEGMENT_64B),
6322 #endif
6323 GEN_HANDLER(tlbia, 0x1F, 0x12, 0x0B, 0x03FFFC01, PPC_MEM_TLBIA),
6324 /* XXX Those instructions will need to be handled differently for
6325  * different ISA versions */
6326 GEN_HANDLER(tlbiel, 0x1F, 0x12, 0x08, 0x001F0001, PPC_MEM_TLBIE),
6327 GEN_HANDLER(tlbie, 0x1F, 0x12, 0x09, 0x001F0001, PPC_MEM_TLBIE),
6328 GEN_HANDLER(tlbsync, 0x1F, 0x16, 0x11, 0x03FFF801, PPC_MEM_TLBSYNC),
6329 #if defined(TARGET_PPC64)
6330 GEN_HANDLER(slbia, 0x1F, 0x12, 0x0F, 0x031FFC01, PPC_SLBI),
6331 GEN_HANDLER(slbie, 0x1F, 0x12, 0x0D, 0x03FF0001, PPC_SLBI),
6332 #endif
6333 GEN_HANDLER(eciwx, 0x1F, 0x16, 0x0D, 0x00000001, PPC_EXTERN),
6334 GEN_HANDLER(ecowx, 0x1F, 0x16, 0x09, 0x00000001, PPC_EXTERN),
6335 GEN_HANDLER(abs, 0x1F, 0x08, 0x0B, 0x0000F800, PPC_POWER_BR),
6336 GEN_HANDLER(abso, 0x1F, 0x08, 0x1B, 0x0000F800, PPC_POWER_BR),
6337 GEN_HANDLER(clcs, 0x1F, 0x10, 0x13, 0x0000F800, PPC_POWER_BR),
6338 GEN_HANDLER(div, 0x1F, 0x0B, 0x0A, 0x00000000, PPC_POWER_BR),
6339 GEN_HANDLER(divo, 0x1F, 0x0B, 0x1A, 0x00000000, PPC_POWER_BR),
6340 GEN_HANDLER(divs, 0x1F, 0x0B, 0x0B, 0x00000000, PPC_POWER_BR),
6341 GEN_HANDLER(divso, 0x1F, 0x0B, 0x1B, 0x00000000, PPC_POWER_BR),
6342 GEN_HANDLER(doz, 0x1F, 0x08, 0x08, 0x00000000, PPC_POWER_BR),
6343 GEN_HANDLER(dozo, 0x1F, 0x08, 0x18, 0x00000000, PPC_POWER_BR),
6344 GEN_HANDLER(dozi, 0x09, 0xFF, 0xFF, 0x00000000, PPC_POWER_BR),
6345 GEN_HANDLER(lscbx, 0x1F, 0x15, 0x08, 0x00000000, PPC_POWER_BR),
6346 GEN_HANDLER(maskg, 0x1F, 0x1D, 0x00, 0x00000000, PPC_POWER_BR),
6347 GEN_HANDLER(maskir, 0x1F, 0x1D, 0x10, 0x00000000, PPC_POWER_BR),
6348 GEN_HANDLER(mul, 0x1F, 0x0B, 0x03, 0x00000000, PPC_POWER_BR),
6349 GEN_HANDLER(mulo, 0x1F, 0x0B, 0x13, 0x00000000, PPC_POWER_BR),
6350 GEN_HANDLER(nabs, 0x1F, 0x08, 0x0F, 0x00000000, PPC_POWER_BR),
6351 GEN_HANDLER(nabso, 0x1F, 0x08, 0x1F, 0x00000000, PPC_POWER_BR),
6352 GEN_HANDLER(rlmi, 0x16, 0xFF, 0xFF, 0x00000000, PPC_POWER_BR),
6353 GEN_HANDLER(rrib, 0x1F, 0x19, 0x10, 0x00000000, PPC_POWER_BR),
6354 GEN_HANDLER(sle, 0x1F, 0x19, 0x04, 0x00000000, PPC_POWER_BR),
6355 GEN_HANDLER(sleq, 0x1F, 0x19, 0x06, 0x00000000, PPC_POWER_BR),
6356 GEN_HANDLER(sliq, 0x1F, 0x18, 0x05, 0x00000000, PPC_POWER_BR),
6357 GEN_HANDLER(slliq, 0x1F, 0x18, 0x07, 0x00000000, PPC_POWER_BR),
6358 GEN_HANDLER(sllq, 0x1F, 0x18, 0x06, 0x00000000, PPC_POWER_BR),
6359 GEN_HANDLER(slq, 0x1F, 0x18, 0x04, 0x00000000, PPC_POWER_BR),
6360 GEN_HANDLER(sraiq, 0x1F, 0x18, 0x1D, 0x00000000, PPC_POWER_BR),
6361 GEN_HANDLER(sraq, 0x1F, 0x18, 0x1C, 0x00000000, PPC_POWER_BR),
6362 GEN_HANDLER(sre, 0x1F, 0x19, 0x14, 0x00000000, PPC_POWER_BR),
6363 GEN_HANDLER(srea, 0x1F, 0x19, 0x1C, 0x00000000, PPC_POWER_BR),
6364 GEN_HANDLER(sreq, 0x1F, 0x19, 0x16, 0x00000000, PPC_POWER_BR),
6365 GEN_HANDLER(sriq, 0x1F, 0x18, 0x15, 0x00000000, PPC_POWER_BR),
6366 GEN_HANDLER(srliq, 0x1F, 0x18, 0x17, 0x00000000, PPC_POWER_BR),
6367 GEN_HANDLER(srlq, 0x1F, 0x18, 0x16, 0x00000000, PPC_POWER_BR),
6368 GEN_HANDLER(srq, 0x1F, 0x18, 0x14, 0x00000000, PPC_POWER_BR),
6369 GEN_HANDLER(dsa, 0x1F, 0x14, 0x13, 0x03FFF801, PPC_602_SPEC),
6370 GEN_HANDLER(esa, 0x1F, 0x14, 0x12, 0x03FFF801, PPC_602_SPEC),
6371 GEN_HANDLER(mfrom, 0x1F, 0x09, 0x08, 0x03E0F801, PPC_602_SPEC),
6372 GEN_HANDLER2(tlbld_6xx, "tlbld", 0x1F, 0x12, 0x1E, 0x03FF0001, PPC_6xx_TLB),
6373 GEN_HANDLER2(tlbli_6xx, "tlbli", 0x1F, 0x12, 0x1F, 0x03FF0001, PPC_6xx_TLB),
6374 GEN_HANDLER2(tlbld_74xx, "tlbld", 0x1F, 0x12, 0x1E, 0x03FF0001, PPC_74xx_TLB),
6375 GEN_HANDLER2(tlbli_74xx, "tlbli", 0x1F, 0x12, 0x1F, 0x03FF0001, PPC_74xx_TLB),
6376 GEN_HANDLER(clf, 0x1F, 0x16, 0x03, 0x03E00000, PPC_POWER),
6377 GEN_HANDLER(cli, 0x1F, 0x16, 0x0F, 0x03E00000, PPC_POWER),
6378 GEN_HANDLER(dclst, 0x1F, 0x16, 0x13, 0x03E00000, PPC_POWER),
6379 GEN_HANDLER(mfsri, 0x1F, 0x13, 0x13, 0x00000001, PPC_POWER),
6380 GEN_HANDLER(rac, 0x1F, 0x12, 0x19, 0x00000001, PPC_POWER),
6381 GEN_HANDLER(rfsvc, 0x13, 0x12, 0x02, 0x03FFF0001, PPC_POWER),
6382 GEN_HANDLER(lfq, 0x38, 0xFF, 0xFF, 0x00000003, PPC_POWER2),
6383 GEN_HANDLER(lfqu, 0x39, 0xFF, 0xFF, 0x00000003, PPC_POWER2),
6384 GEN_HANDLER(lfqux, 0x1F, 0x17, 0x19, 0x00000001, PPC_POWER2),
6385 GEN_HANDLER(lfqx, 0x1F, 0x17, 0x18, 0x00000001, PPC_POWER2),
6386 GEN_HANDLER(stfq, 0x3C, 0xFF, 0xFF, 0x00000003, PPC_POWER2),
6387 GEN_HANDLER(stfqu, 0x3D, 0xFF, 0xFF, 0x00000003, PPC_POWER2),
6388 GEN_HANDLER(stfqux, 0x1F, 0x17, 0x1D, 0x00000001, PPC_POWER2),
6389 GEN_HANDLER(stfqx, 0x1F, 0x17, 0x1C, 0x00000001, PPC_POWER2),
6390 GEN_HANDLER(mfapidi, 0x1F, 0x13, 0x08, 0x0000F801, PPC_MFAPIDI),
6391 GEN_HANDLER(tlbiva, 0x1F, 0x12, 0x18, 0x03FFF801, PPC_TLBIVA),
6392 GEN_HANDLER(mfdcr, 0x1F, 0x03, 0x0A, 0x00000001, PPC_DCR),
6393 GEN_HANDLER(mtdcr, 0x1F, 0x03, 0x0E, 0x00000001, PPC_DCR),
6394 GEN_HANDLER(mfdcrx, 0x1F, 0x03, 0x08, 0x00000000, PPC_DCRX),
6395 GEN_HANDLER(mtdcrx, 0x1F, 0x03, 0x0C, 0x00000000, PPC_DCRX),
6396 GEN_HANDLER(mfdcrux, 0x1F, 0x03, 0x09, 0x00000000, PPC_DCRUX),
6397 GEN_HANDLER(mtdcrux, 0x1F, 0x03, 0x0D, 0x00000000, PPC_DCRUX),
6398 GEN_HANDLER(dccci, 0x1F, 0x06, 0x0E, 0x03E00001, PPC_4xx_COMMON),
6399 GEN_HANDLER(dcread, 0x1F, 0x06, 0x0F, 0x00000001, PPC_4xx_COMMON),
6400 GEN_HANDLER2(icbt_40x, "icbt", 0x1F, 0x06, 0x08, 0x03E00001, PPC_40x_ICBT),
6401 GEN_HANDLER(iccci, 0x1F, 0x06, 0x1E, 0x00000001, PPC_4xx_COMMON),
6402 GEN_HANDLER(icread, 0x1F, 0x06, 0x1F, 0x03E00001, PPC_4xx_COMMON),
6403 GEN_HANDLER2(rfci_40x, "rfci", 0x13, 0x13, 0x01, 0x03FF8001, PPC_40x_EXCP),
6404 GEN_HANDLER_E(rfci, 0x13, 0x13, 0x01, 0x03FF8001, PPC_BOOKE, PPC2_BOOKE206),
6405 GEN_HANDLER(rfdi, 0x13, 0x07, 0x01, 0x03FF8001, PPC_RFDI),
6406 GEN_HANDLER(rfmci, 0x13, 0x06, 0x01, 0x03FF8001, PPC_RFMCI),
6407 GEN_HANDLER2(tlbre_40x, "tlbre", 0x1F, 0x12, 0x1D, 0x00000001, PPC_40x_TLB),
6408 GEN_HANDLER2(tlbsx_40x, "tlbsx", 0x1F, 0x12, 0x1C, 0x00000000, PPC_40x_TLB),
6409 GEN_HANDLER2(tlbwe_40x, "tlbwe", 0x1F, 0x12, 0x1E, 0x00000001, PPC_40x_TLB),
6410 GEN_HANDLER2(tlbre_440, "tlbre", 0x1F, 0x12, 0x1D, 0x00000001, PPC_BOOKE),
6411 GEN_HANDLER2(tlbsx_440, "tlbsx", 0x1F, 0x12, 0x1C, 0x00000000, PPC_BOOKE),
6412 GEN_HANDLER2(tlbwe_440, "tlbwe", 0x1F, 0x12, 0x1E, 0x00000001, PPC_BOOKE),
6413 GEN_HANDLER2_E(tlbre_booke206, "tlbre", 0x1F, 0x12, 0x1D, 0x00000001,
6414                PPC_NONE, PPC2_BOOKE206),
6415 GEN_HANDLER2_E(tlbsx_booke206, "tlbsx", 0x1F, 0x12, 0x1C, 0x00000000,
6416                PPC_NONE, PPC2_BOOKE206),
6417 GEN_HANDLER2_E(tlbwe_booke206, "tlbwe", 0x1F, 0x12, 0x1E, 0x00000001,
6418                PPC_NONE, PPC2_BOOKE206),
6419 GEN_HANDLER2_E(tlbivax_booke206, "tlbivax", 0x1F, 0x12, 0x18, 0x00000001,
6420                PPC_NONE, PPC2_BOOKE206),
6421 GEN_HANDLER2_E(tlbilx_booke206, "tlbilx", 0x1F, 0x12, 0x00, 0x03800001,
6422                PPC_NONE, PPC2_BOOKE206),
6423 GEN_HANDLER2_E(msgsnd, "msgsnd", 0x1F, 0x0E, 0x06, 0x03ff0001,
6424                PPC_NONE, PPC2_PRCNTL),
6425 GEN_HANDLER2_E(msgclr, "msgclr", 0x1F, 0x0E, 0x07, 0x03ff0001,
6426                PPC_NONE, PPC2_PRCNTL),
6427 GEN_HANDLER(wrtee, 0x1F, 0x03, 0x04, 0x000FFC01, PPC_WRTEE),
6428 GEN_HANDLER(wrteei, 0x1F, 0x03, 0x05, 0x000E7C01, PPC_WRTEE),
6429 GEN_HANDLER(dlmzb, 0x1F, 0x0E, 0x02, 0x00000000, PPC_440_SPEC),
6430 GEN_HANDLER_E(mbar, 0x1F, 0x16, 0x1a, 0x001FF801,
6431               PPC_BOOKE, PPC2_BOOKE206),
6432 GEN_HANDLER(msync_4xx, 0x1F, 0x16, 0x12, 0x03FFF801, PPC_BOOKE),
6433 GEN_HANDLER2_E(icbt_440, "icbt", 0x1F, 0x16, 0x00, 0x03E00001,
6434                PPC_BOOKE, PPC2_BOOKE206),
6435 GEN_HANDLER(lvsl, 0x1f, 0x06, 0x00, 0x00000001, PPC_ALTIVEC),
6436 GEN_HANDLER(lvsr, 0x1f, 0x06, 0x01, 0x00000001, PPC_ALTIVEC),
6437 GEN_HANDLER(mfvscr, 0x04, 0x2, 0x18, 0x001ff800, PPC_ALTIVEC),
6438 GEN_HANDLER(mtvscr, 0x04, 0x2, 0x19, 0x03ff0000, PPC_ALTIVEC),
6439 GEN_HANDLER(vmladduhm, 0x04, 0x11, 0xFF, 0x00000000, PPC_ALTIVEC),
6440 #if defined(TARGET_PPC64)
6441 GEN_HANDLER_E(maddhd_maddhdu, 0x04, 0x18, 0xFF, 0x00000000, PPC_NONE,
6442               PPC2_ISA300),
6443 GEN_HANDLER_E(maddld, 0x04, 0x19, 0xFF, 0x00000000, PPC_NONE, PPC2_ISA300),
6444 #endif
6445
6446 #undef GEN_INT_ARITH_ADD
6447 #undef GEN_INT_ARITH_ADD_CONST
6448 #define GEN_INT_ARITH_ADD(name, opc3, add_ca, compute_ca, compute_ov)         \
6449 GEN_HANDLER(name, 0x1F, 0x0A, opc3, 0x00000000, PPC_INTEGER),
6450 #define GEN_INT_ARITH_ADD_CONST(name, opc3, const_val,                        \
6451                                 add_ca, compute_ca, compute_ov)               \
6452 GEN_HANDLER(name, 0x1F, 0x0A, opc3, 0x0000F800, PPC_INTEGER),
6453 GEN_INT_ARITH_ADD(add, 0x08, 0, 0, 0)
6454 GEN_INT_ARITH_ADD(addo, 0x18, 0, 0, 1)
6455 GEN_INT_ARITH_ADD(addc, 0x00, 0, 1, 0)
6456 GEN_INT_ARITH_ADD(addco, 0x10, 0, 1, 1)
6457 GEN_INT_ARITH_ADD(adde, 0x04, 1, 1, 0)
6458 GEN_INT_ARITH_ADD(addeo, 0x14, 1, 1, 1)
6459 GEN_INT_ARITH_ADD_CONST(addme, 0x07, -1LL, 1, 1, 0)
6460 GEN_INT_ARITH_ADD_CONST(addmeo, 0x17, -1LL, 1, 1, 1)
6461 GEN_INT_ARITH_ADD_CONST(addze, 0x06, 0, 1, 1, 0)
6462 GEN_INT_ARITH_ADD_CONST(addzeo, 0x16, 0, 1, 1, 1)
6463
6464 #undef GEN_INT_ARITH_DIVW
6465 #define GEN_INT_ARITH_DIVW(name, opc3, sign, compute_ov)                      \
6466 GEN_HANDLER(name, 0x1F, 0x0B, opc3, 0x00000000, PPC_INTEGER)
6467 GEN_INT_ARITH_DIVW(divwu, 0x0E, 0, 0),
6468 GEN_INT_ARITH_DIVW(divwuo, 0x1E, 0, 1),
6469 GEN_INT_ARITH_DIVW(divw, 0x0F, 1, 0),
6470 GEN_INT_ARITH_DIVW(divwo, 0x1F, 1, 1),
6471 GEN_HANDLER_E(divwe, 0x1F, 0x0B, 0x0D, 0, PPC_NONE, PPC2_DIVE_ISA206),
6472 GEN_HANDLER_E(divweo, 0x1F, 0x0B, 0x1D, 0, PPC_NONE, PPC2_DIVE_ISA206),
6473 GEN_HANDLER_E(divweu, 0x1F, 0x0B, 0x0C, 0, PPC_NONE, PPC2_DIVE_ISA206),
6474 GEN_HANDLER_E(divweuo, 0x1F, 0x0B, 0x1C, 0, PPC_NONE, PPC2_DIVE_ISA206),
6475 GEN_HANDLER_E(modsw, 0x1F, 0x0B, 0x18, 0x00000001, PPC_NONE, PPC2_ISA300),
6476 GEN_HANDLER_E(moduw, 0x1F, 0x0B, 0x08, 0x00000001, PPC_NONE, PPC2_ISA300),
6477
6478 #if defined(TARGET_PPC64)
6479 #undef GEN_INT_ARITH_DIVD
6480 #define GEN_INT_ARITH_DIVD(name, opc3, sign, compute_ov)                      \
6481 GEN_HANDLER(name, 0x1F, 0x09, opc3, 0x00000000, PPC_64B)
6482 GEN_INT_ARITH_DIVD(divdu, 0x0E, 0, 0),
6483 GEN_INT_ARITH_DIVD(divduo, 0x1E, 0, 1),
6484 GEN_INT_ARITH_DIVD(divd, 0x0F, 1, 0),
6485 GEN_INT_ARITH_DIVD(divdo, 0x1F, 1, 1),
6486
6487 GEN_HANDLER_E(divdeu, 0x1F, 0x09, 0x0C, 0, PPC_NONE, PPC2_DIVE_ISA206),
6488 GEN_HANDLER_E(divdeuo, 0x1F, 0x09, 0x1C, 0, PPC_NONE, PPC2_DIVE_ISA206),
6489 GEN_HANDLER_E(divde, 0x1F, 0x09, 0x0D, 0, PPC_NONE, PPC2_DIVE_ISA206),
6490 GEN_HANDLER_E(divdeo, 0x1F, 0x09, 0x1D, 0, PPC_NONE, PPC2_DIVE_ISA206),
6491 GEN_HANDLER_E(modsd, 0x1F, 0x09, 0x18, 0x00000001, PPC_NONE, PPC2_ISA300),
6492 GEN_HANDLER_E(modud, 0x1F, 0x09, 0x08, 0x00000001, PPC_NONE, PPC2_ISA300),
6493
6494 #undef GEN_INT_ARITH_MUL_HELPER
6495 #define GEN_INT_ARITH_MUL_HELPER(name, opc3)                                  \
6496 GEN_HANDLER(name, 0x1F, 0x09, opc3, 0x00000000, PPC_64B)
6497 GEN_INT_ARITH_MUL_HELPER(mulhdu, 0x00),
6498 GEN_INT_ARITH_MUL_HELPER(mulhd, 0x02),
6499 GEN_INT_ARITH_MUL_HELPER(mulldo, 0x17),
6500 #endif
6501
6502 #undef GEN_INT_ARITH_SUBF
6503 #undef GEN_INT_ARITH_SUBF_CONST
6504 #define GEN_INT_ARITH_SUBF(name, opc3, add_ca, compute_ca, compute_ov)        \
6505 GEN_HANDLER(name, 0x1F, 0x08, opc3, 0x00000000, PPC_INTEGER),
6506 #define GEN_INT_ARITH_SUBF_CONST(name, opc3, const_val,                       \
6507                                 add_ca, compute_ca, compute_ov)               \
6508 GEN_HANDLER(name, 0x1F, 0x08, opc3, 0x0000F800, PPC_INTEGER),
6509 GEN_INT_ARITH_SUBF(subf, 0x01, 0, 0, 0)
6510 GEN_INT_ARITH_SUBF(subfo, 0x11, 0, 0, 1)
6511 GEN_INT_ARITH_SUBF(subfc, 0x00, 0, 1, 0)
6512 GEN_INT_ARITH_SUBF(subfco, 0x10, 0, 1, 1)
6513 GEN_INT_ARITH_SUBF(subfe, 0x04, 1, 1, 0)
6514 GEN_INT_ARITH_SUBF(subfeo, 0x14, 1, 1, 1)
6515 GEN_INT_ARITH_SUBF_CONST(subfme, 0x07, -1LL, 1, 1, 0)
6516 GEN_INT_ARITH_SUBF_CONST(subfmeo, 0x17, -1LL, 1, 1, 1)
6517 GEN_INT_ARITH_SUBF_CONST(subfze, 0x06, 0, 1, 1, 0)
6518 GEN_INT_ARITH_SUBF_CONST(subfzeo, 0x16, 0, 1, 1, 1)
6519
6520 #undef GEN_LOGICAL1
6521 #undef GEN_LOGICAL2
6522 #define GEN_LOGICAL2(name, tcg_op, opc, type)                                 \
6523 GEN_HANDLER(name, 0x1F, 0x1C, opc, 0x00000000, type)
6524 #define GEN_LOGICAL1(name, tcg_op, opc, type)                                 \
6525 GEN_HANDLER(name, 0x1F, 0x1A, opc, 0x00000000, type)
6526 GEN_LOGICAL2(and, tcg_gen_and_tl, 0x00, PPC_INTEGER),
6527 GEN_LOGICAL2(andc, tcg_gen_andc_tl, 0x01, PPC_INTEGER),
6528 GEN_LOGICAL2(eqv, tcg_gen_eqv_tl, 0x08, PPC_INTEGER),
6529 GEN_LOGICAL1(extsb, tcg_gen_ext8s_tl, 0x1D, PPC_INTEGER),
6530 GEN_LOGICAL1(extsh, tcg_gen_ext16s_tl, 0x1C, PPC_INTEGER),
6531 GEN_LOGICAL2(nand, tcg_gen_nand_tl, 0x0E, PPC_INTEGER),
6532 GEN_LOGICAL2(nor, tcg_gen_nor_tl, 0x03, PPC_INTEGER),
6533 GEN_LOGICAL2(orc, tcg_gen_orc_tl, 0x0C, PPC_INTEGER),
6534 #if defined(TARGET_PPC64)
6535 GEN_LOGICAL1(extsw, tcg_gen_ext32s_tl, 0x1E, PPC_64B),
6536 #endif
6537
6538 #if defined(TARGET_PPC64)
6539 #undef GEN_PPC64_R2
6540 #undef GEN_PPC64_R4
6541 #define GEN_PPC64_R2(name, opc1, opc2)                                        \
6542 GEN_HANDLER2(name##0, stringify(name), opc1, opc2, 0xFF, 0x00000000, PPC_64B),\
6543 GEN_HANDLER2(name##1, stringify(name), opc1, opc2 | 0x10, 0xFF, 0x00000000,   \
6544              PPC_64B)
6545 #define GEN_PPC64_R4(name, opc1, opc2)                                        \
6546 GEN_HANDLER2(name##0, stringify(name), opc1, opc2, 0xFF, 0x00000000, PPC_64B),\
6547 GEN_HANDLER2(name##1, stringify(name), opc1, opc2 | 0x01, 0xFF, 0x00000000,   \
6548              PPC_64B),                                                        \
6549 GEN_HANDLER2(name##2, stringify(name), opc1, opc2 | 0x10, 0xFF, 0x00000000,   \
6550              PPC_64B),                                                        \
6551 GEN_HANDLER2(name##3, stringify(name), opc1, opc2 | 0x11, 0xFF, 0x00000000,   \
6552              PPC_64B)
6553 GEN_PPC64_R4(rldicl, 0x1E, 0x00),
6554 GEN_PPC64_R4(rldicr, 0x1E, 0x02),
6555 GEN_PPC64_R4(rldic, 0x1E, 0x04),
6556 GEN_PPC64_R2(rldcl, 0x1E, 0x08),
6557 GEN_PPC64_R2(rldcr, 0x1E, 0x09),
6558 GEN_PPC64_R4(rldimi, 0x1E, 0x06),
6559 #endif
6560
6561 #undef GEN_LD
6562 #undef GEN_LDU
6563 #undef GEN_LDUX
6564 #undef GEN_LDX_E
6565 #undef GEN_LDS
6566 #define GEN_LD(name, ldop, opc, type)                                         \
6567 GEN_HANDLER(name, opc, 0xFF, 0xFF, 0x00000000, type),
6568 #define GEN_LDU(name, ldop, opc, type)                                        \
6569 GEN_HANDLER(name##u, opc, 0xFF, 0xFF, 0x00000000, type),
6570 #define GEN_LDUX(name, ldop, opc2, opc3, type)                                \
6571 GEN_HANDLER(name##ux, 0x1F, opc2, opc3, 0x00000001, type),
6572 #define GEN_LDX_E(name, ldop, opc2, opc3, type, type2, chk)                   \
6573 GEN_HANDLER_E(name##x, 0x1F, opc2, opc3, 0x00000001, type, type2),
6574 #define GEN_LDS(name, ldop, op, type)                                         \
6575 GEN_LD(name, ldop, op | 0x20, type)                                           \
6576 GEN_LDU(name, ldop, op | 0x21, type)                                          \
6577 GEN_LDUX(name, ldop, 0x17, op | 0x01, type)                                   \
6578 GEN_LDX(name, ldop, 0x17, op | 0x00, type)
6579
6580 GEN_LDS(lbz, ld8u, 0x02, PPC_INTEGER)
6581 GEN_LDS(lha, ld16s, 0x0A, PPC_INTEGER)
6582 GEN_LDS(lhz, ld16u, 0x08, PPC_INTEGER)
6583 GEN_LDS(lwz, ld32u, 0x00, PPC_INTEGER)
6584 #if defined(TARGET_PPC64)
6585 GEN_LDUX(lwa, ld32s, 0x15, 0x0B, PPC_64B)
6586 GEN_LDX(lwa, ld32s, 0x15, 0x0A, PPC_64B)
6587 GEN_LDUX(ld, ld64_i64, 0x15, 0x01, PPC_64B)
6588 GEN_LDX(ld, ld64_i64, 0x15, 0x00, PPC_64B)
6589 GEN_LDX_E(ldbr, ld64ur_i64, 0x14, 0x10, PPC_NONE, PPC2_DBRX, CHK_NONE)
6590
6591 /* HV/P7 and later only */
6592 GEN_LDX_HVRM(ldcix, ld64_i64, 0x15, 0x1b, PPC_CILDST)
6593 GEN_LDX_HVRM(lwzcix, ld32u, 0x15, 0x18, PPC_CILDST)
6594 GEN_LDX_HVRM(lhzcix, ld16u, 0x15, 0x19, PPC_CILDST)
6595 GEN_LDX_HVRM(lbzcix, ld8u, 0x15, 0x1a, PPC_CILDST)
6596 #endif
6597 GEN_LDX(lhbr, ld16ur, 0x16, 0x18, PPC_INTEGER)
6598 GEN_LDX(lwbr, ld32ur, 0x16, 0x10, PPC_INTEGER)
6599
6600 #undef GEN_ST
6601 #undef GEN_STU
6602 #undef GEN_STUX
6603 #undef GEN_STX_E
6604 #undef GEN_STS
6605 #define GEN_ST(name, stop, opc, type)                                         \
6606 GEN_HANDLER(name, opc, 0xFF, 0xFF, 0x00000000, type),
6607 #define GEN_STU(name, stop, opc, type)                                        \
6608 GEN_HANDLER(stop##u, opc, 0xFF, 0xFF, 0x00000000, type),
6609 #define GEN_STUX(name, stop, opc2, opc3, type)                                \
6610 GEN_HANDLER(name##ux, 0x1F, opc2, opc3, 0x00000001, type),
6611 #define GEN_STX_E(name, stop, opc2, opc3, type, type2, chk)                   \
6612 GEN_HANDLER_E(name##x, 0x1F, opc2, opc3, 0x00000001, type, type2),
6613 #define GEN_STS(name, stop, op, type)                                         \
6614 GEN_ST(name, stop, op | 0x20, type)                                           \
6615 GEN_STU(name, stop, op | 0x21, type)                                          \
6616 GEN_STUX(name, stop, 0x17, op | 0x01, type)                                   \
6617 GEN_STX(name, stop, 0x17, op | 0x00, type)
6618
6619 GEN_STS(stb, st8, 0x06, PPC_INTEGER)
6620 GEN_STS(sth, st16, 0x0C, PPC_INTEGER)
6621 GEN_STS(stw, st32, 0x04, PPC_INTEGER)
6622 #if defined(TARGET_PPC64)
6623 GEN_STUX(std, st64_i64, 0x15, 0x05, PPC_64B)
6624 GEN_STX(std, st64_i64, 0x15, 0x04, PPC_64B)
6625 GEN_STX_E(stdbr, st64r_i64, 0x14, 0x14, PPC_NONE, PPC2_DBRX, CHK_NONE)
6626 GEN_STX_HVRM(stdcix, st64_i64, 0x15, 0x1f, PPC_CILDST)
6627 GEN_STX_HVRM(stwcix, st32, 0x15, 0x1c, PPC_CILDST)
6628 GEN_STX_HVRM(sthcix, st16, 0x15, 0x1d, PPC_CILDST)
6629 GEN_STX_HVRM(stbcix, st8, 0x15, 0x1e, PPC_CILDST)
6630 #endif
6631 GEN_STX(sthbr, st16r, 0x16, 0x1C, PPC_INTEGER)
6632 GEN_STX(stwbr, st32r, 0x16, 0x14, PPC_INTEGER)
6633
6634 #undef GEN_CRLOGIC
6635 #define GEN_CRLOGIC(name, tcg_op, opc)                                        \
6636 GEN_HANDLER(name, 0x13, 0x01, opc, 0x00000001, PPC_INTEGER)
6637 GEN_CRLOGIC(crand, tcg_gen_and_i32, 0x08),
6638 GEN_CRLOGIC(crandc, tcg_gen_andc_i32, 0x04),
6639 GEN_CRLOGIC(creqv, tcg_gen_eqv_i32, 0x09),
6640 GEN_CRLOGIC(crnand, tcg_gen_nand_i32, 0x07),
6641 GEN_CRLOGIC(crnor, tcg_gen_nor_i32, 0x01),
6642 GEN_CRLOGIC(cror, tcg_gen_or_i32, 0x0E),
6643 GEN_CRLOGIC(crorc, tcg_gen_orc_i32, 0x0D),
6644 GEN_CRLOGIC(crxor, tcg_gen_xor_i32, 0x06),
6645
6646 #undef GEN_MAC_HANDLER
6647 #define GEN_MAC_HANDLER(name, opc2, opc3)                                     \
6648 GEN_HANDLER(name, 0x04, opc2, opc3, 0x00000000, PPC_405_MAC)
6649 GEN_MAC_HANDLER(macchw, 0x0C, 0x05),
6650 GEN_MAC_HANDLER(macchwo, 0x0C, 0x15),
6651 GEN_MAC_HANDLER(macchws, 0x0C, 0x07),
6652 GEN_MAC_HANDLER(macchwso, 0x0C, 0x17),
6653 GEN_MAC_HANDLER(macchwsu, 0x0C, 0x06),
6654 GEN_MAC_HANDLER(macchwsuo, 0x0C, 0x16),
6655 GEN_MAC_HANDLER(macchwu, 0x0C, 0x04),
6656 GEN_MAC_HANDLER(macchwuo, 0x0C, 0x14),
6657 GEN_MAC_HANDLER(machhw, 0x0C, 0x01),
6658 GEN_MAC_HANDLER(machhwo, 0x0C, 0x11),
6659 GEN_MAC_HANDLER(machhws, 0x0C, 0x03),
6660 GEN_MAC_HANDLER(machhwso, 0x0C, 0x13),
6661 GEN_MAC_HANDLER(machhwsu, 0x0C, 0x02),
6662 GEN_MAC_HANDLER(machhwsuo, 0x0C, 0x12),
6663 GEN_MAC_HANDLER(machhwu, 0x0C, 0x00),
6664 GEN_MAC_HANDLER(machhwuo, 0x0C, 0x10),
6665 GEN_MAC_HANDLER(maclhw, 0x0C, 0x0D),
6666 GEN_MAC_HANDLER(maclhwo, 0x0C, 0x1D),
6667 GEN_MAC_HANDLER(maclhws, 0x0C, 0x0F),
6668 GEN_MAC_HANDLER(maclhwso, 0x0C, 0x1F),
6669 GEN_MAC_HANDLER(maclhwu, 0x0C, 0x0C),
6670 GEN_MAC_HANDLER(maclhwuo, 0x0C, 0x1C),
6671 GEN_MAC_HANDLER(maclhwsu, 0x0C, 0x0E),
6672 GEN_MAC_HANDLER(maclhwsuo, 0x0C, 0x1E),
6673 GEN_MAC_HANDLER(nmacchw, 0x0E, 0x05),
6674 GEN_MAC_HANDLER(nmacchwo, 0x0E, 0x15),
6675 GEN_MAC_HANDLER(nmacchws, 0x0E, 0x07),
6676 GEN_MAC_HANDLER(nmacchwso, 0x0E, 0x17),
6677 GEN_MAC_HANDLER(nmachhw, 0x0E, 0x01),
6678 GEN_MAC_HANDLER(nmachhwo, 0x0E, 0x11),
6679 GEN_MAC_HANDLER(nmachhws, 0x0E, 0x03),
6680 GEN_MAC_HANDLER(nmachhwso, 0x0E, 0x13),
6681 GEN_MAC_HANDLER(nmaclhw, 0x0E, 0x0D),
6682 GEN_MAC_HANDLER(nmaclhwo, 0x0E, 0x1D),
6683 GEN_MAC_HANDLER(nmaclhws, 0x0E, 0x0F),
6684 GEN_MAC_HANDLER(nmaclhwso, 0x0E, 0x1F),
6685 GEN_MAC_HANDLER(mulchw, 0x08, 0x05),
6686 GEN_MAC_HANDLER(mulchwu, 0x08, 0x04),
6687 GEN_MAC_HANDLER(mulhhw, 0x08, 0x01),
6688 GEN_MAC_HANDLER(mulhhwu, 0x08, 0x00),
6689 GEN_MAC_HANDLER(mullhw, 0x08, 0x0D),
6690 GEN_MAC_HANDLER(mullhwu, 0x08, 0x0C),
6691
6692 GEN_HANDLER2_E(tbegin, "tbegin", 0x1F, 0x0E, 0x14, 0x01DFF800, \
6693                PPC_NONE, PPC2_TM),
6694 GEN_HANDLER2_E(tend,   "tend",   0x1F, 0x0E, 0x15, 0x01FFF800, \
6695                PPC_NONE, PPC2_TM),
6696 GEN_HANDLER2_E(tabort, "tabort", 0x1F, 0x0E, 0x1C, 0x03E0F800, \
6697                PPC_NONE, PPC2_TM),
6698 GEN_HANDLER2_E(tabortwc, "tabortwc", 0x1F, 0x0E, 0x18, 0x00000000, \
6699                PPC_NONE, PPC2_TM),
6700 GEN_HANDLER2_E(tabortwci, "tabortwci", 0x1F, 0x0E, 0x1A, 0x00000000, \
6701                PPC_NONE, PPC2_TM),
6702 GEN_HANDLER2_E(tabortdc, "tabortdc", 0x1F, 0x0E, 0x19, 0x00000000, \
6703                PPC_NONE, PPC2_TM),
6704 GEN_HANDLER2_E(tabortdci, "tabortdci", 0x1F, 0x0E, 0x1B, 0x00000000, \
6705                PPC_NONE, PPC2_TM),
6706 GEN_HANDLER2_E(tsr, "tsr", 0x1F, 0x0E, 0x17, 0x03DFF800, \
6707                PPC_NONE, PPC2_TM),
6708 GEN_HANDLER2_E(tcheck, "tcheck", 0x1F, 0x0E, 0x16, 0x007FF800, \
6709                PPC_NONE, PPC2_TM),
6710 GEN_HANDLER2_E(treclaim, "treclaim", 0x1F, 0x0E, 0x1D, 0x03E0F800, \
6711                PPC_NONE, PPC2_TM),
6712 GEN_HANDLER2_E(trechkpt, "trechkpt", 0x1F, 0x0E, 0x1F, 0x03FFF800, \
6713                PPC_NONE, PPC2_TM),
6714
6715 #include "translate/fp-ops.inc.c"
6716
6717 #include "translate/vmx-ops.inc.c"
6718
6719 #include "translate/vsx-ops.inc.c"
6720
6721 #include "translate/dfp-ops.inc.c"
6722
6723 #include "translate/spe-ops.inc.c"
6724 };
6725
6726 #include "helper_regs.h"
6727 #include "translate_init.c"
6728
6729 /*****************************************************************************/
6730 /* Misc PowerPC helpers */
6731 void ppc_cpu_dump_state(CPUState *cs, FILE *f, fprintf_function cpu_fprintf,
6732                         int flags)
6733 {
6734 #define RGPL  4
6735 #define RFPL  4
6736
6737     PowerPCCPU *cpu = POWERPC_CPU(cs);
6738     CPUPPCState *env = &cpu->env;
6739     int i;
6740
6741     cpu_fprintf(f, "NIP " TARGET_FMT_lx "   LR " TARGET_FMT_lx " CTR "
6742                 TARGET_FMT_lx " XER " TARGET_FMT_lx " CPU#%d\n",
6743                 env->nip, env->lr, env->ctr, cpu_read_xer(env),
6744                 cs->cpu_index);
6745     cpu_fprintf(f, "MSR " TARGET_FMT_lx " HID0 " TARGET_FMT_lx "  HF "
6746                 TARGET_FMT_lx " iidx %d didx %d\n",
6747                 env->msr, env->spr[SPR_HID0],
6748                 env->hflags, env->immu_idx, env->dmmu_idx);
6749 #if !defined(NO_TIMER_DUMP)
6750     cpu_fprintf(f, "TB %08" PRIu32 " %08" PRIu64
6751 #if !defined(CONFIG_USER_ONLY)
6752                 " DECR %08" PRIu32
6753 #endif
6754                 "\n",
6755                 cpu_ppc_load_tbu(env), cpu_ppc_load_tbl(env)
6756 #if !defined(CONFIG_USER_ONLY)
6757                 , cpu_ppc_load_decr(env)
6758 #endif
6759                 );
6760 #endif
6761     for (i = 0; i < 32; i++) {
6762         if ((i & (RGPL - 1)) == 0)
6763             cpu_fprintf(f, "GPR%02d", i);
6764         cpu_fprintf(f, " %016" PRIx64, ppc_dump_gpr(env, i));
6765         if ((i & (RGPL - 1)) == (RGPL - 1))
6766             cpu_fprintf(f, "\n");
6767     }
6768     cpu_fprintf(f, "CR ");
6769     for (i = 0; i < 8; i++)
6770         cpu_fprintf(f, "%01x", env->crf[i]);
6771     cpu_fprintf(f, "  [");
6772     for (i = 0; i < 8; i++) {
6773         char a = '-';
6774         if (env->crf[i] & 0x08)
6775             a = 'L';
6776         else if (env->crf[i] & 0x04)
6777             a = 'G';
6778         else if (env->crf[i] & 0x02)
6779             a = 'E';
6780         cpu_fprintf(f, " %c%c", a, env->crf[i] & 0x01 ? 'O' : ' ');
6781     }
6782     cpu_fprintf(f, " ]             RES " TARGET_FMT_lx "\n",
6783                 env->reserve_addr);
6784     for (i = 0; i < 32; i++) {
6785         if ((i & (RFPL - 1)) == 0)
6786             cpu_fprintf(f, "FPR%02d", i);
6787         cpu_fprintf(f, " %016" PRIx64, *((uint64_t *)&env->fpr[i]));
6788         if ((i & (RFPL - 1)) == (RFPL - 1))
6789             cpu_fprintf(f, "\n");
6790     }
6791     cpu_fprintf(f, "FPSCR " TARGET_FMT_lx "\n", env->fpscr);
6792 #if !defined(CONFIG_USER_ONLY)
6793     cpu_fprintf(f, " SRR0 " TARGET_FMT_lx "  SRR1 " TARGET_FMT_lx
6794                    "    PVR " TARGET_FMT_lx " VRSAVE " TARGET_FMT_lx "\n",
6795                 env->spr[SPR_SRR0], env->spr[SPR_SRR1],
6796                 env->spr[SPR_PVR], env->spr[SPR_VRSAVE]);
6797
6798     cpu_fprintf(f, "SPRG0 " TARGET_FMT_lx " SPRG1 " TARGET_FMT_lx
6799                    "  SPRG2 " TARGET_FMT_lx "  SPRG3 " TARGET_FMT_lx "\n",
6800                 env->spr[SPR_SPRG0], env->spr[SPR_SPRG1],
6801                 env->spr[SPR_SPRG2], env->spr[SPR_SPRG3]);
6802
6803     cpu_fprintf(f, "SPRG4 " TARGET_FMT_lx " SPRG5 " TARGET_FMT_lx
6804                    "  SPRG6 " TARGET_FMT_lx "  SPRG7 " TARGET_FMT_lx "\n",
6805                 env->spr[SPR_SPRG4], env->spr[SPR_SPRG5],
6806                 env->spr[SPR_SPRG6], env->spr[SPR_SPRG7]);
6807
6808 #if defined(TARGET_PPC64)
6809     if (env->excp_model == POWERPC_EXCP_POWER7 ||
6810         env->excp_model == POWERPC_EXCP_POWER8) {
6811         cpu_fprintf(f, "HSRR0 " TARGET_FMT_lx " HSRR1 " TARGET_FMT_lx "\n",
6812                     env->spr[SPR_HSRR0], env->spr[SPR_HSRR1]);
6813     }
6814 #endif
6815     if (env->excp_model == POWERPC_EXCP_BOOKE) {
6816         cpu_fprintf(f, "CSRR0 " TARGET_FMT_lx " CSRR1 " TARGET_FMT_lx
6817                        " MCSRR0 " TARGET_FMT_lx " MCSRR1 " TARGET_FMT_lx "\n",
6818                     env->spr[SPR_BOOKE_CSRR0], env->spr[SPR_BOOKE_CSRR1],
6819                     env->spr[SPR_BOOKE_MCSRR0], env->spr[SPR_BOOKE_MCSRR1]);
6820
6821         cpu_fprintf(f, "  TCR " TARGET_FMT_lx "   TSR " TARGET_FMT_lx
6822                        "    ESR " TARGET_FMT_lx "   DEAR " TARGET_FMT_lx "\n",
6823                     env->spr[SPR_BOOKE_TCR], env->spr[SPR_BOOKE_TSR],
6824                     env->spr[SPR_BOOKE_ESR], env->spr[SPR_BOOKE_DEAR]);
6825
6826         cpu_fprintf(f, "  PIR " TARGET_FMT_lx " DECAR " TARGET_FMT_lx
6827                        "   IVPR " TARGET_FMT_lx "   EPCR " TARGET_FMT_lx "\n",
6828                     env->spr[SPR_BOOKE_PIR], env->spr[SPR_BOOKE_DECAR],
6829                     env->spr[SPR_BOOKE_IVPR], env->spr[SPR_BOOKE_EPCR]);
6830
6831         cpu_fprintf(f, " MCSR " TARGET_FMT_lx " SPRG8 " TARGET_FMT_lx
6832                        "    EPR " TARGET_FMT_lx "\n",
6833                     env->spr[SPR_BOOKE_MCSR], env->spr[SPR_BOOKE_SPRG8],
6834                     env->spr[SPR_BOOKE_EPR]);
6835
6836         /* FSL-specific */
6837         cpu_fprintf(f, " MCAR " TARGET_FMT_lx "  PID1 " TARGET_FMT_lx
6838                        "   PID2 " TARGET_FMT_lx "    SVR " TARGET_FMT_lx "\n",
6839                     env->spr[SPR_Exxx_MCAR], env->spr[SPR_BOOKE_PID1],
6840                     env->spr[SPR_BOOKE_PID2], env->spr[SPR_E500_SVR]);
6841
6842         /*
6843          * IVORs are left out as they are large and do not change often --
6844          * they can be read with "p $ivor0", "p $ivor1", etc.
6845          */
6846     }
6847
6848 #if defined(TARGET_PPC64)
6849     if (env->flags & POWERPC_FLAG_CFAR) {
6850         cpu_fprintf(f, " CFAR " TARGET_FMT_lx"\n", env->cfar);
6851     }
6852 #endif
6853
6854     switch (env->mmu_model) {
6855     case POWERPC_MMU_32B:
6856     case POWERPC_MMU_601:
6857     case POWERPC_MMU_SOFT_6xx:
6858     case POWERPC_MMU_SOFT_74xx:
6859 #if defined(TARGET_PPC64)
6860     case POWERPC_MMU_64B:
6861     case POWERPC_MMU_2_03:
6862     case POWERPC_MMU_2_06:
6863     case POWERPC_MMU_2_06a:
6864     case POWERPC_MMU_2_07:
6865     case POWERPC_MMU_2_07a:
6866 #endif
6867         cpu_fprintf(f, " SDR1 " TARGET_FMT_lx "   DAR " TARGET_FMT_lx
6868                        "  DSISR " TARGET_FMT_lx "\n", env->spr[SPR_SDR1],
6869                     env->spr[SPR_DAR], env->spr[SPR_DSISR]);
6870         break;
6871     case POWERPC_MMU_BOOKE206:
6872         cpu_fprintf(f, " MAS0 " TARGET_FMT_lx "  MAS1 " TARGET_FMT_lx
6873                        "   MAS2 " TARGET_FMT_lx "   MAS3 " TARGET_FMT_lx "\n",
6874                     env->spr[SPR_BOOKE_MAS0], env->spr[SPR_BOOKE_MAS1],
6875                     env->spr[SPR_BOOKE_MAS2], env->spr[SPR_BOOKE_MAS3]);
6876
6877         cpu_fprintf(f, " MAS4 " TARGET_FMT_lx "  MAS6 " TARGET_FMT_lx
6878                        "   MAS7 " TARGET_FMT_lx "    PID " TARGET_FMT_lx "\n",
6879                     env->spr[SPR_BOOKE_MAS4], env->spr[SPR_BOOKE_MAS6],
6880                     env->spr[SPR_BOOKE_MAS7], env->spr[SPR_BOOKE_PID]);
6881
6882         cpu_fprintf(f, "MMUCFG " TARGET_FMT_lx " TLB0CFG " TARGET_FMT_lx
6883                        " TLB1CFG " TARGET_FMT_lx "\n",
6884                     env->spr[SPR_MMUCFG], env->spr[SPR_BOOKE_TLB0CFG],
6885                     env->spr[SPR_BOOKE_TLB1CFG]);
6886         break;
6887     default:
6888         break;
6889     }
6890 #endif
6891
6892 #undef RGPL
6893 #undef RFPL
6894 }
6895
6896 void ppc_cpu_dump_statistics(CPUState *cs, FILE*f,
6897                              fprintf_function cpu_fprintf, int flags)
6898 {
6899 #if defined(DO_PPC_STATISTICS)
6900     PowerPCCPU *cpu = POWERPC_CPU(cs);
6901     opc_handler_t **t1, **t2, **t3, *handler;
6902     int op1, op2, op3;
6903
6904     t1 = cpu->env.opcodes;
6905     for (op1 = 0; op1 < 64; op1++) {
6906         handler = t1[op1];
6907         if (is_indirect_opcode(handler)) {
6908             t2 = ind_table(handler);
6909             for (op2 = 0; op2 < 32; op2++) {
6910                 handler = t2[op2];
6911                 if (is_indirect_opcode(handler)) {
6912                     t3 = ind_table(handler);
6913                     for (op3 = 0; op3 < 32; op3++) {
6914                         handler = t3[op3];
6915                         if (handler->count == 0)
6916                             continue;
6917                         cpu_fprintf(f, "%02x %02x %02x (%02x %04d) %16s: "
6918                                     "%016" PRIx64 " %" PRId64 "\n",
6919                                     op1, op2, op3, op1, (op3 << 5) | op2,
6920                                     handler->oname,
6921                                     handler->count, handler->count);
6922                     }
6923                 } else {
6924                     if (handler->count == 0)
6925                         continue;
6926                     cpu_fprintf(f, "%02x %02x    (%02x %04d) %16s: "
6927                                 "%016" PRIx64 " %" PRId64 "\n",
6928                                 op1, op2, op1, op2, handler->oname,
6929                                 handler->count, handler->count);
6930                 }
6931             }
6932         } else {
6933             if (handler->count == 0)
6934                 continue;
6935             cpu_fprintf(f, "%02x       (%02x     ) %16s: %016" PRIx64
6936                         " %" PRId64 "\n",
6937                         op1, op1, handler->oname,
6938                         handler->count, handler->count);
6939         }
6940     }
6941 #endif
6942 }
6943
6944 /*****************************************************************************/
6945 void gen_intermediate_code(CPUPPCState *env, struct TranslationBlock *tb)
6946 {
6947     PowerPCCPU *cpu = ppc_env_get_cpu(env);
6948     CPUState *cs = CPU(cpu);
6949     DisasContext ctx, *ctxp = &ctx;
6950     opc_handler_t **table, *handler;
6951     target_ulong pc_start;
6952     int num_insns;
6953     int max_insns;
6954
6955     pc_start = tb->pc;
6956     ctx.nip = pc_start;
6957     ctx.tb = tb;
6958     ctx.exception = POWERPC_EXCP_NONE;
6959     ctx.spr_cb = env->spr_cb;
6960     ctx.pr = msr_pr;
6961     ctx.mem_idx = env->dmmu_idx;
6962     ctx.dr = msr_dr;
6963 #if !defined(CONFIG_USER_ONLY)
6964     ctx.hv = msr_hv || !env->has_hv_mode;
6965 #endif
6966     ctx.insns_flags = env->insns_flags;
6967     ctx.insns_flags2 = env->insns_flags2;
6968     ctx.access_type = -1;
6969     ctx.need_access_type = !(env->mmu_model & POWERPC_MMU_64B);
6970     ctx.le_mode = !!(env->hflags & (1 << MSR_LE));
6971     ctx.default_tcg_memop_mask = ctx.le_mode ? MO_LE : MO_BE;
6972 #if defined(TARGET_PPC64)
6973     ctx.sf_mode = msr_is_64bit(env, env->msr);
6974     ctx.has_cfar = !!(env->flags & POWERPC_FLAG_CFAR);
6975 #endif
6976     if (env->mmu_model == POWERPC_MMU_32B ||
6977         env->mmu_model == POWERPC_MMU_601 ||
6978         (env->mmu_model & POWERPC_MMU_64B))
6979             ctx.lazy_tlb_flush = true;
6980
6981     ctx.fpu_enabled = !!msr_fp;
6982     if ((env->flags & POWERPC_FLAG_SPE) && msr_spe)
6983         ctx.spe_enabled = !!msr_spe;
6984     else
6985         ctx.spe_enabled = false;
6986     if ((env->flags & POWERPC_FLAG_VRE) && msr_vr)
6987         ctx.altivec_enabled = !!msr_vr;
6988     else
6989         ctx.altivec_enabled = false;
6990     if ((env->flags & POWERPC_FLAG_VSX) && msr_vsx) {
6991         ctx.vsx_enabled = !!msr_vsx;
6992     } else {
6993         ctx.vsx_enabled = false;
6994     }
6995 #if defined(TARGET_PPC64)
6996     if ((env->flags & POWERPC_FLAG_TM) && msr_tm) {
6997         ctx.tm_enabled = !!msr_tm;
6998     } else {
6999         ctx.tm_enabled = false;
7000     }
7001 #endif
7002     if ((env->flags & POWERPC_FLAG_SE) && msr_se)
7003         ctx.singlestep_enabled = CPU_SINGLE_STEP;
7004     else
7005         ctx.singlestep_enabled = 0;
7006     if ((env->flags & POWERPC_FLAG_BE) && msr_be)
7007         ctx.singlestep_enabled |= CPU_BRANCH_STEP;
7008     if (unlikely(cs->singlestep_enabled)) {
7009         ctx.singlestep_enabled |= GDBSTUB_SINGLE_STEP;
7010     }
7011 #if defined (DO_SINGLE_STEP) && 0
7012     /* Single step trace mode */
7013     msr_se = 1;
7014 #endif
7015     num_insns = 0;
7016     max_insns = tb->cflags & CF_COUNT_MASK;
7017     if (max_insns == 0) {
7018         max_insns = CF_COUNT_MASK;
7019     }
7020     if (max_insns > TCG_MAX_INSNS) {
7021         max_insns = TCG_MAX_INSNS;
7022     }
7023
7024     gen_tb_start(tb);
7025     tcg_clear_temp_count();
7026     /* Set env in case of segfault during code fetch */
7027     while (ctx.exception == POWERPC_EXCP_NONE && !tcg_op_buf_full()) {
7028         tcg_gen_insn_start(ctx.nip);
7029         num_insns++;
7030
7031         if (unlikely(cpu_breakpoint_test(cs, ctx.nip, BP_ANY))) {
7032             gen_debug_exception(ctxp);
7033             /* The address covered by the breakpoint must be included in
7034                [tb->pc, tb->pc + tb->size) in order to for it to be
7035                properly cleared -- thus we increment the PC here so that
7036                the logic setting tb->size below does the right thing.  */
7037             ctx.nip += 4;
7038             break;
7039         }
7040
7041         LOG_DISAS("----------------\n");
7042         LOG_DISAS("nip=" TARGET_FMT_lx " super=%d ir=%d\n",
7043                   ctx.nip, ctx.mem_idx, (int)msr_ir);
7044         if (num_insns == max_insns && (tb->cflags & CF_LAST_IO))
7045             gen_io_start();
7046         if (unlikely(need_byteswap(&ctx))) {
7047             ctx.opcode = bswap32(cpu_ldl_code(env, ctx.nip));
7048         } else {
7049             ctx.opcode = cpu_ldl_code(env, ctx.nip);
7050         }
7051         LOG_DISAS("translate opcode %08x (%02x %02x %02x %02x) (%s)\n",
7052                   ctx.opcode, opc1(ctx.opcode), opc2(ctx.opcode),
7053                   opc3(ctx.opcode), opc4(ctx.opcode),
7054                   ctx.le_mode ? "little" : "big");
7055         ctx.nip += 4;
7056         table = env->opcodes;
7057         handler = table[opc1(ctx.opcode)];
7058         if (is_indirect_opcode(handler)) {
7059             table = ind_table(handler);
7060             handler = table[opc2(ctx.opcode)];
7061             if (is_indirect_opcode(handler)) {
7062                 table = ind_table(handler);
7063                 handler = table[opc3(ctx.opcode)];
7064                 if (is_indirect_opcode(handler)) {
7065                     table = ind_table(handler);
7066                     handler = table[opc4(ctx.opcode)];
7067                 }
7068             }
7069         }
7070         /* Is opcode *REALLY* valid ? */
7071         if (unlikely(handler->handler == &gen_invalid)) {
7072             qemu_log_mask(LOG_GUEST_ERROR, "invalid/unsupported opcode: "
7073                           "%02x - %02x - %02x - %02x (%08x) "
7074                           TARGET_FMT_lx " %d\n",
7075                           opc1(ctx.opcode), opc2(ctx.opcode),
7076                           opc3(ctx.opcode), opc4(ctx.opcode),
7077                           ctx.opcode, ctx.nip - 4, (int)msr_ir);
7078         } else {
7079             uint32_t inval;
7080
7081             if (unlikely(handler->type & (PPC_SPE | PPC_SPE_SINGLE | PPC_SPE_DOUBLE) && Rc(ctx.opcode))) {
7082                 inval = handler->inval2;
7083             } else {
7084                 inval = handler->inval1;
7085             }
7086
7087             if (unlikely((ctx.opcode & inval) != 0)) {
7088                 qemu_log_mask(LOG_GUEST_ERROR, "invalid bits: %08x for opcode: "
7089                               "%02x - %02x - %02x - %02x (%08x) "
7090                               TARGET_FMT_lx "\n", ctx.opcode & inval,
7091                               opc1(ctx.opcode), opc2(ctx.opcode),
7092                               opc3(ctx.opcode), opc4(ctx.opcode),
7093                               ctx.opcode, ctx.nip - 4);
7094                 gen_inval_exception(ctxp, POWERPC_EXCP_INVAL_INVAL);
7095                 break;
7096             }
7097         }
7098         (*(handler->handler))(&ctx);
7099 #if defined(DO_PPC_STATISTICS)
7100         handler->count++;
7101 #endif
7102         /* Check trace mode exceptions */
7103         if (unlikely(ctx.singlestep_enabled & CPU_SINGLE_STEP &&
7104                      (ctx.nip <= 0x100 || ctx.nip > 0xF00) &&
7105                      ctx.exception != POWERPC_SYSCALL &&
7106                      ctx.exception != POWERPC_EXCP_TRAP &&
7107                      ctx.exception != POWERPC_EXCP_BRANCH)) {
7108             gen_exception_nip(ctxp, POWERPC_EXCP_TRACE, ctx.nip);
7109         } else if (unlikely(((ctx.nip & (TARGET_PAGE_SIZE - 1)) == 0) ||
7110                             (cs->singlestep_enabled) ||
7111                             singlestep ||
7112                             num_insns >= max_insns)) {
7113             /* if we reach a page boundary or are single stepping, stop
7114              * generation
7115              */
7116             break;
7117         }
7118         if (tcg_check_temp_count()) {
7119             fprintf(stderr, "Opcode %02x %02x %02x %02x (%08x) leaked "
7120                     "temporaries\n", opc1(ctx.opcode), opc2(ctx.opcode),
7121                     opc3(ctx.opcode), opc4(ctx.opcode), ctx.opcode);
7122             exit(1);
7123         }
7124     }
7125     if (tb->cflags & CF_LAST_IO)
7126         gen_io_end();
7127     if (ctx.exception == POWERPC_EXCP_NONE) {
7128         gen_goto_tb(&ctx, 0, ctx.nip);
7129     } else if (ctx.exception != POWERPC_EXCP_BRANCH) {
7130         if (unlikely(cs->singlestep_enabled)) {
7131             gen_debug_exception(ctxp);
7132         }
7133         /* Generate the return instruction */
7134         tcg_gen_exit_tb(0);
7135     }
7136     gen_tb_end(tb, num_insns);
7137
7138     tb->size = ctx.nip - pc_start;
7139     tb->icount = num_insns;
7140
7141 #if defined(DEBUG_DISAS)
7142     if (qemu_loglevel_mask(CPU_LOG_TB_IN_ASM)
7143         && qemu_log_in_addr_range(pc_start)) {
7144         int flags;
7145         flags = env->bfd_mach;
7146         flags |= ctx.le_mode << 16;
7147         qemu_log("IN: %s\n", lookup_symbol(pc_start));
7148         log_target_disas(cs, pc_start, ctx.nip - pc_start, flags);
7149         qemu_log("\n");
7150     }
7151 #endif
7152 }
7153
7154 void restore_state_to_opc(CPUPPCState *env, TranslationBlock *tb,
7155                           target_ulong *data)
7156 {
7157     env->nip = data[0];
7158 }
This page took 0.414982 seconds and 4 git commands to generate.