2 * PowerPC CPU initialization for qemu.
4 * Copyright (c) 2003-2007 Jocelyn Mayer
5 * Copyright 2011 Freescale Semiconductor, Inc.
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.
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.
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/>.
21 #include "disas/bfd.h"
22 #include "exec/gdbstub.h"
23 #include <sysemu/kvm.h>
25 #include "sysemu/arch_init.h"
26 #include "sysemu/cpus.h"
27 #include "cpu-models.h"
28 #include "mmu-hash32.h"
29 #include "mmu-hash64.h"
30 #include "qemu/error-report.h"
31 #include "qapi/visitor.h"
32 #include "hw/qdev-properties.h"
34 //#define PPC_DUMP_CPU
35 //#define PPC_DEBUG_SPR
36 //#define PPC_DUMP_SPR_ACCESSES
37 /* #define USE_APPLE_GDB */
39 /* For user-mode emulation, we don't emulate any IRQ controller */
40 #if defined(CONFIG_USER_ONLY)
41 #define PPC_IRQ_INIT_FN(name) \
42 static inline void glue(glue(ppc, name),_irq_init) (CPUPPCState *env) \
46 #define PPC_IRQ_INIT_FN(name) \
47 void glue(glue(ppc, name),_irq_init) (CPUPPCState *env);
53 PPC_IRQ_INIT_FN(POWER7);
54 PPC_IRQ_INIT_FN(e500);
57 * do nothing but store/retrieve spr value
59 static void spr_load_dump_spr(int sprn)
61 #ifdef PPC_DUMP_SPR_ACCESSES
62 TCGv_i32 t0 = tcg_const_i32(sprn);
63 gen_helper_load_dump_spr(cpu_env, t0);
64 tcg_temp_free_i32(t0);
68 static void spr_read_generic (void *opaque, int gprn, int sprn)
70 gen_load_spr(cpu_gpr[gprn], sprn);
71 spr_load_dump_spr(sprn);
74 static void spr_store_dump_spr(int sprn)
76 #ifdef PPC_DUMP_SPR_ACCESSES
77 TCGv_i32 t0 = tcg_const_i32(sprn);
78 gen_helper_store_dump_spr(cpu_env, t0);
79 tcg_temp_free_i32(t0);
83 static void spr_write_generic (void *opaque, int sprn, int gprn)
85 gen_store_spr(sprn, cpu_gpr[gprn]);
86 spr_store_dump_spr(sprn);
89 #if !defined(CONFIG_USER_ONLY)
90 static void spr_write_generic32(void *opaque, int sprn, int gprn)
93 TCGv t0 = tcg_temp_new();
94 tcg_gen_ext32u_tl(t0, cpu_gpr[gprn]);
95 gen_store_spr(sprn, t0);
97 spr_store_dump_spr(sprn);
99 spr_write_generic(opaque, sprn, gprn);
103 static void spr_write_clear (void *opaque, int sprn, int gprn)
105 TCGv t0 = tcg_temp_new();
106 TCGv t1 = tcg_temp_new();
107 gen_load_spr(t0, sprn);
108 tcg_gen_neg_tl(t1, cpu_gpr[gprn]);
109 tcg_gen_and_tl(t0, t0, t1);
110 gen_store_spr(sprn, t0);
115 static void spr_access_nop(void *opaque, int sprn, int gprn)
121 /* SPR common to all PowerPC */
123 static void spr_read_xer (void *opaque, int gprn, int sprn)
125 gen_read_xer(cpu_gpr[gprn]);
128 static void spr_write_xer (void *opaque, int sprn, int gprn)
130 gen_write_xer(cpu_gpr[gprn]);
134 static void spr_read_lr (void *opaque, int gprn, int sprn)
136 tcg_gen_mov_tl(cpu_gpr[gprn], cpu_lr);
139 static void spr_write_lr (void *opaque, int sprn, int gprn)
141 tcg_gen_mov_tl(cpu_lr, cpu_gpr[gprn]);
145 #if defined(TARGET_PPC64) && !defined(CONFIG_USER_ONLY)
146 static void spr_read_cfar (void *opaque, int gprn, int sprn)
148 tcg_gen_mov_tl(cpu_gpr[gprn], cpu_cfar);
151 static void spr_write_cfar (void *opaque, int sprn, int gprn)
153 tcg_gen_mov_tl(cpu_cfar, cpu_gpr[gprn]);
155 #endif /* defined(TARGET_PPC64) && !defined(CONFIG_USER_ONLY) */
158 static void spr_read_ctr (void *opaque, int gprn, int sprn)
160 tcg_gen_mov_tl(cpu_gpr[gprn], cpu_ctr);
163 static void spr_write_ctr (void *opaque, int sprn, int gprn)
165 tcg_gen_mov_tl(cpu_ctr, cpu_gpr[gprn]);
168 /* User read access to SPR */
174 static void spr_read_ureg (void *opaque, int gprn, int sprn)
176 gen_load_spr(cpu_gpr[gprn], sprn + 0x10);
179 #if defined(TARGET_PPC64) && !defined(CONFIG_USER_ONLY)
180 static void spr_write_ureg(void *opaque, int sprn, int gprn)
182 gen_store_spr(sprn + 0x10, cpu_gpr[gprn]);
186 /* SPR common to all non-embedded PowerPC */
188 #if !defined(CONFIG_USER_ONLY)
189 static void spr_read_decr (void *opaque, int gprn, int sprn)
194 gen_helper_load_decr(cpu_gpr[gprn], cpu_env);
197 gen_stop_exception(opaque);
201 static void spr_write_decr (void *opaque, int sprn, int gprn)
206 gen_helper_store_decr(cpu_env, cpu_gpr[gprn]);
209 gen_stop_exception(opaque);
214 /* SPR common to all non-embedded PowerPC, except 601 */
216 static void spr_read_tbl (void *opaque, int gprn, int sprn)
221 gen_helper_load_tbl(cpu_gpr[gprn], cpu_env);
224 gen_stop_exception(opaque);
228 static void spr_read_tbu (void *opaque, int gprn, int sprn)
233 gen_helper_load_tbu(cpu_gpr[gprn], cpu_env);
236 gen_stop_exception(opaque);
240 __attribute__ (( unused ))
241 static void spr_read_atbl (void *opaque, int gprn, int sprn)
243 gen_helper_load_atbl(cpu_gpr[gprn], cpu_env);
246 __attribute__ (( unused ))
247 static void spr_read_atbu (void *opaque, int gprn, int sprn)
249 gen_helper_load_atbu(cpu_gpr[gprn], cpu_env);
252 #if !defined(CONFIG_USER_ONLY)
253 static void spr_write_tbl (void *opaque, int sprn, int gprn)
258 gen_helper_store_tbl(cpu_env, cpu_gpr[gprn]);
261 gen_stop_exception(opaque);
265 static void spr_write_tbu (void *opaque, int sprn, int gprn)
270 gen_helper_store_tbu(cpu_env, cpu_gpr[gprn]);
273 gen_stop_exception(opaque);
277 __attribute__ (( unused ))
278 static void spr_write_atbl (void *opaque, int sprn, int gprn)
280 gen_helper_store_atbl(cpu_env, cpu_gpr[gprn]);
283 __attribute__ (( unused ))
284 static void spr_write_atbu (void *opaque, int sprn, int gprn)
286 gen_helper_store_atbu(cpu_env, cpu_gpr[gprn]);
289 #if defined(TARGET_PPC64)
290 __attribute__ (( unused ))
291 static void spr_read_purr (void *opaque, int gprn, int sprn)
293 gen_helper_load_purr(cpu_gpr[gprn], cpu_env);
298 #if !defined(CONFIG_USER_ONLY)
299 /* IBAT0U...IBAT0U */
300 /* IBAT0L...IBAT7L */
301 static void spr_read_ibat (void *opaque, int gprn, int sprn)
303 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, IBAT[sprn & 1][(sprn - SPR_IBAT0U) / 2]));
306 static void spr_read_ibat_h (void *opaque, int gprn, int sprn)
308 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, IBAT[sprn & 1][(sprn - SPR_IBAT4U) / 2]));
311 static void spr_write_ibatu (void *opaque, int sprn, int gprn)
313 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_IBAT0U) / 2);
314 gen_helper_store_ibatu(cpu_env, t0, cpu_gpr[gprn]);
315 tcg_temp_free_i32(t0);
318 static void spr_write_ibatu_h (void *opaque, int sprn, int gprn)
320 TCGv_i32 t0 = tcg_const_i32(((sprn - SPR_IBAT4U) / 2) + 4);
321 gen_helper_store_ibatu(cpu_env, t0, cpu_gpr[gprn]);
322 tcg_temp_free_i32(t0);
325 static void spr_write_ibatl (void *opaque, int sprn, int gprn)
327 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_IBAT0L) / 2);
328 gen_helper_store_ibatl(cpu_env, t0, cpu_gpr[gprn]);
329 tcg_temp_free_i32(t0);
332 static void spr_write_ibatl_h (void *opaque, int sprn, int gprn)
334 TCGv_i32 t0 = tcg_const_i32(((sprn - SPR_IBAT4L) / 2) + 4);
335 gen_helper_store_ibatl(cpu_env, t0, cpu_gpr[gprn]);
336 tcg_temp_free_i32(t0);
339 /* DBAT0U...DBAT7U */
340 /* DBAT0L...DBAT7L */
341 static void spr_read_dbat (void *opaque, int gprn, int sprn)
343 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, DBAT[sprn & 1][(sprn - SPR_DBAT0U) / 2]));
346 static void spr_read_dbat_h (void *opaque, int gprn, int sprn)
348 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, DBAT[sprn & 1][((sprn - SPR_DBAT4U) / 2) + 4]));
351 static void spr_write_dbatu (void *opaque, int sprn, int gprn)
353 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_DBAT0U) / 2);
354 gen_helper_store_dbatu(cpu_env, t0, cpu_gpr[gprn]);
355 tcg_temp_free_i32(t0);
358 static void spr_write_dbatu_h (void *opaque, int sprn, int gprn)
360 TCGv_i32 t0 = tcg_const_i32(((sprn - SPR_DBAT4U) / 2) + 4);
361 gen_helper_store_dbatu(cpu_env, t0, cpu_gpr[gprn]);
362 tcg_temp_free_i32(t0);
365 static void spr_write_dbatl (void *opaque, int sprn, int gprn)
367 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_DBAT0L) / 2);
368 gen_helper_store_dbatl(cpu_env, t0, cpu_gpr[gprn]);
369 tcg_temp_free_i32(t0);
372 static void spr_write_dbatl_h (void *opaque, int sprn, int gprn)
374 TCGv_i32 t0 = tcg_const_i32(((sprn - SPR_DBAT4L) / 2) + 4);
375 gen_helper_store_dbatl(cpu_env, t0, cpu_gpr[gprn]);
376 tcg_temp_free_i32(t0);
380 static void spr_write_sdr1 (void *opaque, int sprn, int gprn)
382 gen_helper_store_sdr1(cpu_env, cpu_gpr[gprn]);
385 /* 64 bits PowerPC specific SPRs */
386 #if defined(TARGET_PPC64)
387 static void spr_read_hior (void *opaque, int gprn, int sprn)
389 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, excp_prefix));
392 static void spr_write_hior (void *opaque, int sprn, int gprn)
394 TCGv t0 = tcg_temp_new();
395 tcg_gen_andi_tl(t0, cpu_gpr[gprn], 0x3FFFFF00000ULL);
396 tcg_gen_st_tl(t0, cpu_env, offsetof(CPUPPCState, excp_prefix));
402 /* PowerPC 601 specific registers */
404 static void spr_read_601_rtcl (void *opaque, int gprn, int sprn)
406 gen_helper_load_601_rtcl(cpu_gpr[gprn], cpu_env);
409 static void spr_read_601_rtcu (void *opaque, int gprn, int sprn)
411 gen_helper_load_601_rtcu(cpu_gpr[gprn], cpu_env);
414 #if !defined(CONFIG_USER_ONLY)
415 static void spr_write_601_rtcu (void *opaque, int sprn, int gprn)
417 gen_helper_store_601_rtcu(cpu_env, cpu_gpr[gprn]);
420 static void spr_write_601_rtcl (void *opaque, int sprn, int gprn)
422 gen_helper_store_601_rtcl(cpu_env, cpu_gpr[gprn]);
425 static void spr_write_hid0_601 (void *opaque, int sprn, int gprn)
427 DisasContext *ctx = opaque;
429 gen_helper_store_hid0_601(cpu_env, cpu_gpr[gprn]);
430 /* Must stop the translation as endianness may have changed */
431 gen_stop_exception(ctx);
436 #if !defined(CONFIG_USER_ONLY)
437 static void spr_read_601_ubat (void *opaque, int gprn, int sprn)
439 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, IBAT[sprn & 1][(sprn - SPR_IBAT0U) / 2]));
442 static void spr_write_601_ubatu (void *opaque, int sprn, int gprn)
444 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_IBAT0U) / 2);
445 gen_helper_store_601_batl(cpu_env, t0, cpu_gpr[gprn]);
446 tcg_temp_free_i32(t0);
449 static void spr_write_601_ubatl (void *opaque, int sprn, int gprn)
451 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_IBAT0U) / 2);
452 gen_helper_store_601_batu(cpu_env, t0, cpu_gpr[gprn]);
453 tcg_temp_free_i32(t0);
457 /* PowerPC 40x specific registers */
458 #if !defined(CONFIG_USER_ONLY)
459 static void spr_read_40x_pit (void *opaque, int gprn, int sprn)
461 gen_helper_load_40x_pit(cpu_gpr[gprn], cpu_env);
464 static void spr_write_40x_pit (void *opaque, int sprn, int gprn)
466 gen_helper_store_40x_pit(cpu_env, cpu_gpr[gprn]);
469 static void spr_write_40x_dbcr0 (void *opaque, int sprn, int gprn)
471 DisasContext *ctx = opaque;
473 gen_helper_store_40x_dbcr0(cpu_env, cpu_gpr[gprn]);
474 /* We must stop translation as we may have rebooted */
475 gen_stop_exception(ctx);
478 static void spr_write_40x_sler (void *opaque, int sprn, int gprn)
480 gen_helper_store_40x_sler(cpu_env, cpu_gpr[gprn]);
483 static void spr_write_booke_tcr (void *opaque, int sprn, int gprn)
485 gen_helper_store_booke_tcr(cpu_env, cpu_gpr[gprn]);
488 static void spr_write_booke_tsr (void *opaque, int sprn, int gprn)
490 gen_helper_store_booke_tsr(cpu_env, cpu_gpr[gprn]);
494 /* PowerPC 403 specific registers */
495 /* PBL1 / PBU1 / PBL2 / PBU2 */
496 #if !defined(CONFIG_USER_ONLY)
497 static void spr_read_403_pbr (void *opaque, int gprn, int sprn)
499 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, pb[sprn - SPR_403_PBL1]));
502 static void spr_write_403_pbr (void *opaque, int sprn, int gprn)
504 TCGv_i32 t0 = tcg_const_i32(sprn - SPR_403_PBL1);
505 gen_helper_store_403_pbr(cpu_env, t0, cpu_gpr[gprn]);
506 tcg_temp_free_i32(t0);
509 static void spr_write_pir (void *opaque, int sprn, int gprn)
511 TCGv t0 = tcg_temp_new();
512 tcg_gen_andi_tl(t0, cpu_gpr[gprn], 0xF);
513 gen_store_spr(SPR_PIR, t0);
518 /* SPE specific registers */
519 static void spr_read_spefscr (void *opaque, int gprn, int sprn)
521 TCGv_i32 t0 = tcg_temp_new_i32();
522 tcg_gen_ld_i32(t0, cpu_env, offsetof(CPUPPCState, spe_fscr));
523 tcg_gen_extu_i32_tl(cpu_gpr[gprn], t0);
524 tcg_temp_free_i32(t0);
527 static void spr_write_spefscr (void *opaque, int sprn, int gprn)
529 TCGv_i32 t0 = tcg_temp_new_i32();
530 tcg_gen_trunc_tl_i32(t0, cpu_gpr[gprn]);
531 tcg_gen_st_i32(t0, cpu_env, offsetof(CPUPPCState, spe_fscr));
532 tcg_temp_free_i32(t0);
535 #if !defined(CONFIG_USER_ONLY)
536 /* Callback used to write the exception vector base */
537 static void spr_write_excp_prefix (void *opaque, int sprn, int gprn)
539 TCGv t0 = tcg_temp_new();
540 tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUPPCState, ivpr_mask));
541 tcg_gen_and_tl(t0, t0, cpu_gpr[gprn]);
542 tcg_gen_st_tl(t0, cpu_env, offsetof(CPUPPCState, excp_prefix));
543 gen_store_spr(sprn, t0);
547 static void spr_write_excp_vector (void *opaque, int sprn, int gprn)
549 DisasContext *ctx = opaque;
552 if (sprn >= SPR_BOOKE_IVOR0 && sprn <= SPR_BOOKE_IVOR15) {
553 sprn_offs = sprn - SPR_BOOKE_IVOR0;
554 } else if (sprn >= SPR_BOOKE_IVOR32 && sprn <= SPR_BOOKE_IVOR37) {
555 sprn_offs = sprn - SPR_BOOKE_IVOR32 + 32;
556 } else if (sprn >= SPR_BOOKE_IVOR38 && sprn <= SPR_BOOKE_IVOR42) {
557 sprn_offs = sprn - SPR_BOOKE_IVOR38 + 38;
559 printf("Trying to write an unknown exception vector %d %03x\n",
561 gen_inval_exception(ctx, POWERPC_EXCP_PRIV_REG);
565 TCGv t0 = tcg_temp_new();
566 tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUPPCState, ivor_mask));
567 tcg_gen_and_tl(t0, t0, cpu_gpr[gprn]);
568 tcg_gen_st_tl(t0, cpu_env, offsetof(CPUPPCState, excp_vectors[sprn_offs]));
569 gen_store_spr(sprn, t0);
574 static inline void vscr_init (CPUPPCState *env, uint32_t val)
577 /* Altivec always uses round-to-nearest */
578 set_float_rounding_mode(float_round_nearest_even, &env->vec_status);
579 set_flush_to_zero(vscr_nj, &env->vec_status);
582 #ifdef CONFIG_USER_ONLY
583 #define spr_register_kvm(env, num, name, uea_read, uea_write, \
584 oea_read, oea_write, one_reg_id, initial_value) \
585 _spr_register(env, num, name, uea_read, uea_write, initial_value)
587 #if !defined(CONFIG_KVM)
588 #define spr_register_kvm(env, num, name, uea_read, uea_write, \
589 oea_read, oea_write, one_reg_id, initial_value) \
590 _spr_register(env, num, name, uea_read, uea_write, \
591 oea_read, oea_write, initial_value)
593 #define spr_register_kvm(env, num, name, uea_read, uea_write, \
594 oea_read, oea_write, one_reg_id, initial_value) \
595 _spr_register(env, num, name, uea_read, uea_write, \
596 oea_read, oea_write, one_reg_id, initial_value)
600 #define spr_register(env, num, name, uea_read, uea_write, \
601 oea_read, oea_write, initial_value) \
602 spr_register_kvm(env, num, name, uea_read, uea_write, \
603 oea_read, oea_write, 0, initial_value)
605 static inline void _spr_register(CPUPPCState *env, int num,
607 void (*uea_read)(void *opaque, int gprn, int sprn),
608 void (*uea_write)(void *opaque, int sprn, int gprn),
609 #if !defined(CONFIG_USER_ONLY)
611 void (*oea_read)(void *opaque, int gprn, int sprn),
612 void (*oea_write)(void *opaque, int sprn, int gprn),
614 #if defined(CONFIG_KVM)
617 target_ulong initial_value)
621 spr = &env->spr_cb[num];
622 if (spr->name != NULL ||env-> spr[num] != 0x00000000 ||
623 #if !defined(CONFIG_USER_ONLY)
624 spr->oea_read != NULL || spr->oea_write != NULL ||
626 spr->uea_read != NULL || spr->uea_write != NULL) {
627 printf("Error: Trying to register SPR %d (%03x) twice !\n", num, num);
630 #if defined(PPC_DEBUG_SPR)
631 printf("*** register spr %d (%03x) %s val " TARGET_FMT_lx "\n", num, num,
632 name, initial_value);
635 spr->uea_read = uea_read;
636 spr->uea_write = uea_write;
637 #if !defined(CONFIG_USER_ONLY)
638 spr->oea_read = oea_read;
639 spr->oea_write = oea_write;
641 #if defined(CONFIG_KVM)
642 spr->one_reg_id = one_reg_id,
644 env->spr[num] = spr->default_value = initial_value;
647 /* Generic PowerPC SPRs */
648 static void gen_spr_generic (CPUPPCState *env)
650 /* Integer processing */
651 spr_register(env, SPR_XER, "XER",
652 &spr_read_xer, &spr_write_xer,
653 &spr_read_xer, &spr_write_xer,
656 spr_register(env, SPR_LR, "LR",
657 &spr_read_lr, &spr_write_lr,
658 &spr_read_lr, &spr_write_lr,
660 spr_register(env, SPR_CTR, "CTR",
661 &spr_read_ctr, &spr_write_ctr,
662 &spr_read_ctr, &spr_write_ctr,
664 /* Interrupt processing */
665 spr_register(env, SPR_SRR0, "SRR0",
666 SPR_NOACCESS, SPR_NOACCESS,
667 &spr_read_generic, &spr_write_generic,
669 spr_register(env, SPR_SRR1, "SRR1",
670 SPR_NOACCESS, SPR_NOACCESS,
671 &spr_read_generic, &spr_write_generic,
673 /* Processor control */
674 spr_register(env, SPR_SPRG0, "SPRG0",
675 SPR_NOACCESS, SPR_NOACCESS,
676 &spr_read_generic, &spr_write_generic,
678 spr_register(env, SPR_SPRG1, "SPRG1",
679 SPR_NOACCESS, SPR_NOACCESS,
680 &spr_read_generic, &spr_write_generic,
682 spr_register(env, SPR_SPRG2, "SPRG2",
683 SPR_NOACCESS, SPR_NOACCESS,
684 &spr_read_generic, &spr_write_generic,
686 spr_register(env, SPR_SPRG3, "SPRG3",
687 SPR_NOACCESS, SPR_NOACCESS,
688 &spr_read_generic, &spr_write_generic,
692 /* SPR common to all non-embedded PowerPC, including 601 */
693 static void gen_spr_ne_601 (CPUPPCState *env)
695 /* Exception processing */
696 spr_register_kvm(env, SPR_DSISR, "DSISR",
697 SPR_NOACCESS, SPR_NOACCESS,
698 &spr_read_generic, &spr_write_generic,
699 KVM_REG_PPC_DSISR, 0x00000000);
700 spr_register_kvm(env, SPR_DAR, "DAR",
701 SPR_NOACCESS, SPR_NOACCESS,
702 &spr_read_generic, &spr_write_generic,
703 KVM_REG_PPC_DAR, 0x00000000);
705 spr_register(env, SPR_DECR, "DECR",
706 SPR_NOACCESS, SPR_NOACCESS,
707 &spr_read_decr, &spr_write_decr,
709 /* Memory management */
710 spr_register(env, SPR_SDR1, "SDR1",
711 SPR_NOACCESS, SPR_NOACCESS,
712 &spr_read_generic, &spr_write_sdr1,
717 static void gen_low_BATs (CPUPPCState *env)
719 #if !defined(CONFIG_USER_ONLY)
720 spr_register(env, SPR_IBAT0U, "IBAT0U",
721 SPR_NOACCESS, SPR_NOACCESS,
722 &spr_read_ibat, &spr_write_ibatu,
724 spr_register(env, SPR_IBAT0L, "IBAT0L",
725 SPR_NOACCESS, SPR_NOACCESS,
726 &spr_read_ibat, &spr_write_ibatl,
728 spr_register(env, SPR_IBAT1U, "IBAT1U",
729 SPR_NOACCESS, SPR_NOACCESS,
730 &spr_read_ibat, &spr_write_ibatu,
732 spr_register(env, SPR_IBAT1L, "IBAT1L",
733 SPR_NOACCESS, SPR_NOACCESS,
734 &spr_read_ibat, &spr_write_ibatl,
736 spr_register(env, SPR_IBAT2U, "IBAT2U",
737 SPR_NOACCESS, SPR_NOACCESS,
738 &spr_read_ibat, &spr_write_ibatu,
740 spr_register(env, SPR_IBAT2L, "IBAT2L",
741 SPR_NOACCESS, SPR_NOACCESS,
742 &spr_read_ibat, &spr_write_ibatl,
744 spr_register(env, SPR_IBAT3U, "IBAT3U",
745 SPR_NOACCESS, SPR_NOACCESS,
746 &spr_read_ibat, &spr_write_ibatu,
748 spr_register(env, SPR_IBAT3L, "IBAT3L",
749 SPR_NOACCESS, SPR_NOACCESS,
750 &spr_read_ibat, &spr_write_ibatl,
752 spr_register(env, SPR_DBAT0U, "DBAT0U",
753 SPR_NOACCESS, SPR_NOACCESS,
754 &spr_read_dbat, &spr_write_dbatu,
756 spr_register(env, SPR_DBAT0L, "DBAT0L",
757 SPR_NOACCESS, SPR_NOACCESS,
758 &spr_read_dbat, &spr_write_dbatl,
760 spr_register(env, SPR_DBAT1U, "DBAT1U",
761 SPR_NOACCESS, SPR_NOACCESS,
762 &spr_read_dbat, &spr_write_dbatu,
764 spr_register(env, SPR_DBAT1L, "DBAT1L",
765 SPR_NOACCESS, SPR_NOACCESS,
766 &spr_read_dbat, &spr_write_dbatl,
768 spr_register(env, SPR_DBAT2U, "DBAT2U",
769 SPR_NOACCESS, SPR_NOACCESS,
770 &spr_read_dbat, &spr_write_dbatu,
772 spr_register(env, SPR_DBAT2L, "DBAT2L",
773 SPR_NOACCESS, SPR_NOACCESS,
774 &spr_read_dbat, &spr_write_dbatl,
776 spr_register(env, SPR_DBAT3U, "DBAT3U",
777 SPR_NOACCESS, SPR_NOACCESS,
778 &spr_read_dbat, &spr_write_dbatu,
780 spr_register(env, SPR_DBAT3L, "DBAT3L",
781 SPR_NOACCESS, SPR_NOACCESS,
782 &spr_read_dbat, &spr_write_dbatl,
789 static void gen_high_BATs (CPUPPCState *env)
791 #if !defined(CONFIG_USER_ONLY)
792 spr_register(env, SPR_IBAT4U, "IBAT4U",
793 SPR_NOACCESS, SPR_NOACCESS,
794 &spr_read_ibat_h, &spr_write_ibatu_h,
796 spr_register(env, SPR_IBAT4L, "IBAT4L",
797 SPR_NOACCESS, SPR_NOACCESS,
798 &spr_read_ibat_h, &spr_write_ibatl_h,
800 spr_register(env, SPR_IBAT5U, "IBAT5U",
801 SPR_NOACCESS, SPR_NOACCESS,
802 &spr_read_ibat_h, &spr_write_ibatu_h,
804 spr_register(env, SPR_IBAT5L, "IBAT5L",
805 SPR_NOACCESS, SPR_NOACCESS,
806 &spr_read_ibat_h, &spr_write_ibatl_h,
808 spr_register(env, SPR_IBAT6U, "IBAT6U",
809 SPR_NOACCESS, SPR_NOACCESS,
810 &spr_read_ibat_h, &spr_write_ibatu_h,
812 spr_register(env, SPR_IBAT6L, "IBAT6L",
813 SPR_NOACCESS, SPR_NOACCESS,
814 &spr_read_ibat_h, &spr_write_ibatl_h,
816 spr_register(env, SPR_IBAT7U, "IBAT7U",
817 SPR_NOACCESS, SPR_NOACCESS,
818 &spr_read_ibat_h, &spr_write_ibatu_h,
820 spr_register(env, SPR_IBAT7L, "IBAT7L",
821 SPR_NOACCESS, SPR_NOACCESS,
822 &spr_read_ibat_h, &spr_write_ibatl_h,
824 spr_register(env, SPR_DBAT4U, "DBAT4U",
825 SPR_NOACCESS, SPR_NOACCESS,
826 &spr_read_dbat_h, &spr_write_dbatu_h,
828 spr_register(env, SPR_DBAT4L, "DBAT4L",
829 SPR_NOACCESS, SPR_NOACCESS,
830 &spr_read_dbat_h, &spr_write_dbatl_h,
832 spr_register(env, SPR_DBAT5U, "DBAT5U",
833 SPR_NOACCESS, SPR_NOACCESS,
834 &spr_read_dbat_h, &spr_write_dbatu_h,
836 spr_register(env, SPR_DBAT5L, "DBAT5L",
837 SPR_NOACCESS, SPR_NOACCESS,
838 &spr_read_dbat_h, &spr_write_dbatl_h,
840 spr_register(env, SPR_DBAT6U, "DBAT6U",
841 SPR_NOACCESS, SPR_NOACCESS,
842 &spr_read_dbat_h, &spr_write_dbatu_h,
844 spr_register(env, SPR_DBAT6L, "DBAT6L",
845 SPR_NOACCESS, SPR_NOACCESS,
846 &spr_read_dbat_h, &spr_write_dbatl_h,
848 spr_register(env, SPR_DBAT7U, "DBAT7U",
849 SPR_NOACCESS, SPR_NOACCESS,
850 &spr_read_dbat_h, &spr_write_dbatu_h,
852 spr_register(env, SPR_DBAT7L, "DBAT7L",
853 SPR_NOACCESS, SPR_NOACCESS,
854 &spr_read_dbat_h, &spr_write_dbatl_h,
860 /* Generic PowerPC time base */
861 static void gen_tbl (CPUPPCState *env)
863 spr_register(env, SPR_VTBL, "TBL",
864 &spr_read_tbl, SPR_NOACCESS,
865 &spr_read_tbl, SPR_NOACCESS,
867 spr_register(env, SPR_TBL, "TBL",
868 &spr_read_tbl, SPR_NOACCESS,
869 &spr_read_tbl, &spr_write_tbl,
871 spr_register(env, SPR_VTBU, "TBU",
872 &spr_read_tbu, SPR_NOACCESS,
873 &spr_read_tbu, SPR_NOACCESS,
875 spr_register(env, SPR_TBU, "TBU",
876 &spr_read_tbu, SPR_NOACCESS,
877 &spr_read_tbu, &spr_write_tbu,
881 /* Softare table search registers */
882 static void gen_6xx_7xx_soft_tlb (CPUPPCState *env, int nb_tlbs, int nb_ways)
884 #if !defined(CONFIG_USER_ONLY)
885 env->nb_tlb = nb_tlbs;
886 env->nb_ways = nb_ways;
888 env->tlb_type = TLB_6XX;
889 spr_register(env, SPR_DMISS, "DMISS",
890 SPR_NOACCESS, SPR_NOACCESS,
891 &spr_read_generic, SPR_NOACCESS,
893 spr_register(env, SPR_DCMP, "DCMP",
894 SPR_NOACCESS, SPR_NOACCESS,
895 &spr_read_generic, SPR_NOACCESS,
897 spr_register(env, SPR_HASH1, "HASH1",
898 SPR_NOACCESS, SPR_NOACCESS,
899 &spr_read_generic, SPR_NOACCESS,
901 spr_register(env, SPR_HASH2, "HASH2",
902 SPR_NOACCESS, SPR_NOACCESS,
903 &spr_read_generic, SPR_NOACCESS,
905 spr_register(env, SPR_IMISS, "IMISS",
906 SPR_NOACCESS, SPR_NOACCESS,
907 &spr_read_generic, SPR_NOACCESS,
909 spr_register(env, SPR_ICMP, "ICMP",
910 SPR_NOACCESS, SPR_NOACCESS,
911 &spr_read_generic, SPR_NOACCESS,
913 spr_register(env, SPR_RPA, "RPA",
914 SPR_NOACCESS, SPR_NOACCESS,
915 &spr_read_generic, &spr_write_generic,
920 /* SPR common to MPC755 and G2 */
921 static void gen_spr_G2_755 (CPUPPCState *env)
924 spr_register(env, SPR_SPRG4, "SPRG4",
925 SPR_NOACCESS, SPR_NOACCESS,
926 &spr_read_generic, &spr_write_generic,
928 spr_register(env, SPR_SPRG5, "SPRG5",
929 SPR_NOACCESS, SPR_NOACCESS,
930 &spr_read_generic, &spr_write_generic,
932 spr_register(env, SPR_SPRG6, "SPRG6",
933 SPR_NOACCESS, SPR_NOACCESS,
934 &spr_read_generic, &spr_write_generic,
936 spr_register(env, SPR_SPRG7, "SPRG7",
937 SPR_NOACCESS, SPR_NOACCESS,
938 &spr_read_generic, &spr_write_generic,
942 /* SPR common to all 7xx PowerPC implementations */
943 static void gen_spr_7xx (CPUPPCState *env)
946 /* XXX : not implemented */
947 spr_register_kvm(env, SPR_DABR, "DABR",
948 SPR_NOACCESS, SPR_NOACCESS,
949 &spr_read_generic, &spr_write_generic,
950 KVM_REG_PPC_DABR, 0x00000000);
951 /* XXX : not implemented */
952 spr_register(env, SPR_IABR, "IABR",
953 SPR_NOACCESS, SPR_NOACCESS,
954 &spr_read_generic, &spr_write_generic,
956 /* Cache management */
957 /* XXX : not implemented */
958 spr_register(env, SPR_ICTC, "ICTC",
959 SPR_NOACCESS, SPR_NOACCESS,
960 &spr_read_generic, &spr_write_generic,
962 /* Performance monitors */
963 /* XXX : not implemented */
964 spr_register(env, SPR_7XX_MMCR0, "MMCR0",
965 SPR_NOACCESS, SPR_NOACCESS,
966 &spr_read_generic, &spr_write_generic,
968 /* XXX : not implemented */
969 spr_register(env, SPR_7XX_MMCR1, "MMCR1",
970 SPR_NOACCESS, SPR_NOACCESS,
971 &spr_read_generic, &spr_write_generic,
973 /* XXX : not implemented */
974 spr_register(env, SPR_7XX_PMC1, "PMC1",
975 SPR_NOACCESS, SPR_NOACCESS,
976 &spr_read_generic, &spr_write_generic,
978 /* XXX : not implemented */
979 spr_register(env, SPR_7XX_PMC2, "PMC2",
980 SPR_NOACCESS, SPR_NOACCESS,
981 &spr_read_generic, &spr_write_generic,
983 /* XXX : not implemented */
984 spr_register(env, SPR_7XX_PMC3, "PMC3",
985 SPR_NOACCESS, SPR_NOACCESS,
986 &spr_read_generic, &spr_write_generic,
988 /* XXX : not implemented */
989 spr_register(env, SPR_7XX_PMC4, "PMC4",
990 SPR_NOACCESS, SPR_NOACCESS,
991 &spr_read_generic, &spr_write_generic,
993 /* XXX : not implemented */
994 spr_register(env, SPR_7XX_SIAR, "SIAR",
995 SPR_NOACCESS, SPR_NOACCESS,
996 &spr_read_generic, SPR_NOACCESS,
998 /* XXX : not implemented */
999 spr_register(env, SPR_7XX_UMMCR0, "UMMCR0",
1000 &spr_read_ureg, SPR_NOACCESS,
1001 &spr_read_ureg, SPR_NOACCESS,
1003 /* XXX : not implemented */
1004 spr_register(env, SPR_7XX_UMMCR1, "UMMCR1",
1005 &spr_read_ureg, SPR_NOACCESS,
1006 &spr_read_ureg, SPR_NOACCESS,
1008 /* XXX : not implemented */
1009 spr_register(env, SPR_7XX_UPMC1, "UPMC1",
1010 &spr_read_ureg, SPR_NOACCESS,
1011 &spr_read_ureg, SPR_NOACCESS,
1013 /* XXX : not implemented */
1014 spr_register(env, SPR_7XX_UPMC2, "UPMC2",
1015 &spr_read_ureg, SPR_NOACCESS,
1016 &spr_read_ureg, SPR_NOACCESS,
1018 /* XXX : not implemented */
1019 spr_register(env, SPR_7XX_UPMC3, "UPMC3",
1020 &spr_read_ureg, SPR_NOACCESS,
1021 &spr_read_ureg, SPR_NOACCESS,
1023 /* XXX : not implemented */
1024 spr_register(env, SPR_7XX_UPMC4, "UPMC4",
1025 &spr_read_ureg, SPR_NOACCESS,
1026 &spr_read_ureg, SPR_NOACCESS,
1028 /* XXX : not implemented */
1029 spr_register(env, SPR_7XX_USIAR, "USIAR",
1030 &spr_read_ureg, SPR_NOACCESS,
1031 &spr_read_ureg, SPR_NOACCESS,
1033 /* External access control */
1034 /* XXX : not implemented */
1035 spr_register(env, SPR_EAR, "EAR",
1036 SPR_NOACCESS, SPR_NOACCESS,
1037 &spr_read_generic, &spr_write_generic,
1042 #ifndef CONFIG_USER_ONLY
1043 static void spr_read_uamr (void *opaque, int gprn, int sprn)
1045 gen_load_spr(cpu_gpr[gprn], SPR_AMR);
1046 spr_load_dump_spr(SPR_AMR);
1049 static void spr_write_uamr (void *opaque, int sprn, int gprn)
1051 gen_store_spr(SPR_AMR, cpu_gpr[gprn]);
1052 spr_store_dump_spr(SPR_AMR);
1055 static void spr_write_uamr_pr (void *opaque, int sprn, int gprn)
1057 TCGv t0 = tcg_temp_new();
1059 gen_load_spr(t0, SPR_UAMOR);
1060 tcg_gen_and_tl(t0, t0, cpu_gpr[gprn]);
1061 gen_store_spr(SPR_AMR, t0);
1062 spr_store_dump_spr(SPR_AMR);
1064 #endif /* CONFIG_USER_ONLY */
1066 static void gen_spr_amr (CPUPPCState *env)
1068 #ifndef CONFIG_USER_ONLY
1069 /* Virtual Page Class Key protection */
1070 /* The AMR is accessible either via SPR 13 or SPR 29. 13 is
1071 * userspace accessible, 29 is privileged. So we only need to set
1072 * the kvm ONE_REG id on one of them, we use 29 */
1073 spr_register(env, SPR_UAMR, "UAMR",
1074 &spr_read_uamr, &spr_write_uamr_pr,
1075 &spr_read_uamr, &spr_write_uamr,
1077 spr_register_kvm(env, SPR_AMR, "AMR",
1078 SPR_NOACCESS, SPR_NOACCESS,
1079 &spr_read_generic, &spr_write_generic,
1080 KVM_REG_PPC_AMR, 0);
1081 spr_register_kvm(env, SPR_UAMOR, "UAMOR",
1082 SPR_NOACCESS, SPR_NOACCESS,
1083 &spr_read_generic, &spr_write_generic,
1084 KVM_REG_PPC_UAMOR, 0);
1085 #endif /* !CONFIG_USER_ONLY */
1087 #endif /* TARGET_PPC64 */
1089 static void gen_spr_thrm (CPUPPCState *env)
1091 /* Thermal management */
1092 /* XXX : not implemented */
1093 spr_register(env, SPR_THRM1, "THRM1",
1094 SPR_NOACCESS, SPR_NOACCESS,
1095 &spr_read_generic, &spr_write_generic,
1097 /* XXX : not implemented */
1098 spr_register(env, SPR_THRM2, "THRM2",
1099 SPR_NOACCESS, SPR_NOACCESS,
1100 &spr_read_generic, &spr_write_generic,
1102 /* XXX : not implemented */
1103 spr_register(env, SPR_THRM3, "THRM3",
1104 SPR_NOACCESS, SPR_NOACCESS,
1105 &spr_read_generic, &spr_write_generic,
1109 /* SPR specific to PowerPC 604 implementation */
1110 static void gen_spr_604 (CPUPPCState *env)
1112 /* Processor identification */
1113 spr_register(env, SPR_PIR, "PIR",
1114 SPR_NOACCESS, SPR_NOACCESS,
1115 &spr_read_generic, &spr_write_pir,
1118 /* XXX : not implemented */
1119 spr_register(env, SPR_IABR, "IABR",
1120 SPR_NOACCESS, SPR_NOACCESS,
1121 &spr_read_generic, &spr_write_generic,
1123 /* XXX : not implemented */
1124 spr_register_kvm(env, SPR_DABR, "DABR",
1125 SPR_NOACCESS, SPR_NOACCESS,
1126 &spr_read_generic, &spr_write_generic,
1127 KVM_REG_PPC_DABR, 0x00000000);
1128 /* Performance counters */
1129 /* XXX : not implemented */
1130 spr_register(env, SPR_7XX_MMCR0, "MMCR0",
1131 SPR_NOACCESS, SPR_NOACCESS,
1132 &spr_read_generic, &spr_write_generic,
1134 /* XXX : not implemented */
1135 spr_register(env, SPR_7XX_PMC1, "PMC1",
1136 SPR_NOACCESS, SPR_NOACCESS,
1137 &spr_read_generic, &spr_write_generic,
1139 /* XXX : not implemented */
1140 spr_register(env, SPR_7XX_PMC2, "PMC2",
1141 SPR_NOACCESS, SPR_NOACCESS,
1142 &spr_read_generic, &spr_write_generic,
1144 /* XXX : not implemented */
1145 spr_register(env, SPR_7XX_SIAR, "SIAR",
1146 SPR_NOACCESS, SPR_NOACCESS,
1147 &spr_read_generic, SPR_NOACCESS,
1149 /* XXX : not implemented */
1150 spr_register(env, SPR_SDA, "SDA",
1151 SPR_NOACCESS, SPR_NOACCESS,
1152 &spr_read_generic, SPR_NOACCESS,
1154 /* External access control */
1155 /* XXX : not implemented */
1156 spr_register(env, SPR_EAR, "EAR",
1157 SPR_NOACCESS, SPR_NOACCESS,
1158 &spr_read_generic, &spr_write_generic,
1162 /* SPR specific to PowerPC 603 implementation */
1163 static void gen_spr_603 (CPUPPCState *env)
1165 /* External access control */
1166 /* XXX : not implemented */
1167 spr_register(env, SPR_EAR, "EAR",
1168 SPR_NOACCESS, SPR_NOACCESS,
1169 &spr_read_generic, &spr_write_generic,
1172 /* XXX : not implemented */
1173 spr_register(env, SPR_IABR, "IABR",
1174 SPR_NOACCESS, SPR_NOACCESS,
1175 &spr_read_generic, &spr_write_generic,
1180 /* SPR specific to PowerPC G2 implementation */
1181 static void gen_spr_G2 (CPUPPCState *env)
1183 /* Memory base address */
1185 /* XXX : not implemented */
1186 spr_register(env, SPR_MBAR, "MBAR",
1187 SPR_NOACCESS, SPR_NOACCESS,
1188 &spr_read_generic, &spr_write_generic,
1190 /* Exception processing */
1191 spr_register(env, SPR_BOOKE_CSRR0, "CSRR0",
1192 SPR_NOACCESS, SPR_NOACCESS,
1193 &spr_read_generic, &spr_write_generic,
1195 spr_register(env, SPR_BOOKE_CSRR1, "CSRR1",
1196 SPR_NOACCESS, SPR_NOACCESS,
1197 &spr_read_generic, &spr_write_generic,
1200 /* XXX : not implemented */
1201 spr_register(env, SPR_DABR, "DABR",
1202 SPR_NOACCESS, SPR_NOACCESS,
1203 &spr_read_generic, &spr_write_generic,
1205 /* XXX : not implemented */
1206 spr_register(env, SPR_DABR2, "DABR2",
1207 SPR_NOACCESS, SPR_NOACCESS,
1208 &spr_read_generic, &spr_write_generic,
1210 /* XXX : not implemented */
1211 spr_register(env, SPR_IABR, "IABR",
1212 SPR_NOACCESS, SPR_NOACCESS,
1213 &spr_read_generic, &spr_write_generic,
1215 /* XXX : not implemented */
1216 spr_register(env, SPR_IABR2, "IABR2",
1217 SPR_NOACCESS, SPR_NOACCESS,
1218 &spr_read_generic, &spr_write_generic,
1220 /* XXX : not implemented */
1221 spr_register(env, SPR_IBCR, "IBCR",
1222 SPR_NOACCESS, SPR_NOACCESS,
1223 &spr_read_generic, &spr_write_generic,
1225 /* XXX : not implemented */
1226 spr_register(env, SPR_DBCR, "DBCR",
1227 SPR_NOACCESS, SPR_NOACCESS,
1228 &spr_read_generic, &spr_write_generic,
1232 /* SPR specific to PowerPC 602 implementation */
1233 static void gen_spr_602 (CPUPPCState *env)
1236 /* XXX : not implemented */
1237 spr_register(env, SPR_SER, "SER",
1238 SPR_NOACCESS, SPR_NOACCESS,
1239 &spr_read_generic, &spr_write_generic,
1241 /* XXX : not implemented */
1242 spr_register(env, SPR_SEBR, "SEBR",
1243 SPR_NOACCESS, SPR_NOACCESS,
1244 &spr_read_generic, &spr_write_generic,
1246 /* XXX : not implemented */
1247 spr_register(env, SPR_ESASRR, "ESASRR",
1248 SPR_NOACCESS, SPR_NOACCESS,
1249 &spr_read_generic, &spr_write_generic,
1251 /* Floating point status */
1252 /* XXX : not implemented */
1253 spr_register(env, SPR_SP, "SP",
1254 SPR_NOACCESS, SPR_NOACCESS,
1255 &spr_read_generic, &spr_write_generic,
1257 /* XXX : not implemented */
1258 spr_register(env, SPR_LT, "LT",
1259 SPR_NOACCESS, SPR_NOACCESS,
1260 &spr_read_generic, &spr_write_generic,
1262 /* Watchdog timer */
1263 /* XXX : not implemented */
1264 spr_register(env, SPR_TCR, "TCR",
1265 SPR_NOACCESS, SPR_NOACCESS,
1266 &spr_read_generic, &spr_write_generic,
1268 /* Interrupt base */
1269 spr_register(env, SPR_IBR, "IBR",
1270 SPR_NOACCESS, SPR_NOACCESS,
1271 &spr_read_generic, &spr_write_generic,
1273 /* XXX : not implemented */
1274 spr_register(env, SPR_IABR, "IABR",
1275 SPR_NOACCESS, SPR_NOACCESS,
1276 &spr_read_generic, &spr_write_generic,
1280 /* SPR specific to PowerPC 601 implementation */
1281 static void gen_spr_601 (CPUPPCState *env)
1283 /* Multiplication/division register */
1285 spr_register(env, SPR_MQ, "MQ",
1286 &spr_read_generic, &spr_write_generic,
1287 &spr_read_generic, &spr_write_generic,
1290 spr_register(env, SPR_601_RTCU, "RTCU",
1291 SPR_NOACCESS, SPR_NOACCESS,
1292 SPR_NOACCESS, &spr_write_601_rtcu,
1294 spr_register(env, SPR_601_VRTCU, "RTCU",
1295 &spr_read_601_rtcu, SPR_NOACCESS,
1296 &spr_read_601_rtcu, SPR_NOACCESS,
1298 spr_register(env, SPR_601_RTCL, "RTCL",
1299 SPR_NOACCESS, SPR_NOACCESS,
1300 SPR_NOACCESS, &spr_write_601_rtcl,
1302 spr_register(env, SPR_601_VRTCL, "RTCL",
1303 &spr_read_601_rtcl, SPR_NOACCESS,
1304 &spr_read_601_rtcl, SPR_NOACCESS,
1308 spr_register(env, SPR_601_UDECR, "UDECR",
1309 &spr_read_decr, SPR_NOACCESS,
1310 &spr_read_decr, SPR_NOACCESS,
1313 /* External access control */
1314 /* XXX : not implemented */
1315 spr_register(env, SPR_EAR, "EAR",
1316 SPR_NOACCESS, SPR_NOACCESS,
1317 &spr_read_generic, &spr_write_generic,
1319 /* Memory management */
1320 #if !defined(CONFIG_USER_ONLY)
1321 spr_register(env, SPR_IBAT0U, "IBAT0U",
1322 SPR_NOACCESS, SPR_NOACCESS,
1323 &spr_read_601_ubat, &spr_write_601_ubatu,
1325 spr_register(env, SPR_IBAT0L, "IBAT0L",
1326 SPR_NOACCESS, SPR_NOACCESS,
1327 &spr_read_601_ubat, &spr_write_601_ubatl,
1329 spr_register(env, SPR_IBAT1U, "IBAT1U",
1330 SPR_NOACCESS, SPR_NOACCESS,
1331 &spr_read_601_ubat, &spr_write_601_ubatu,
1333 spr_register(env, SPR_IBAT1L, "IBAT1L",
1334 SPR_NOACCESS, SPR_NOACCESS,
1335 &spr_read_601_ubat, &spr_write_601_ubatl,
1337 spr_register(env, SPR_IBAT2U, "IBAT2U",
1338 SPR_NOACCESS, SPR_NOACCESS,
1339 &spr_read_601_ubat, &spr_write_601_ubatu,
1341 spr_register(env, SPR_IBAT2L, "IBAT2L",
1342 SPR_NOACCESS, SPR_NOACCESS,
1343 &spr_read_601_ubat, &spr_write_601_ubatl,
1345 spr_register(env, SPR_IBAT3U, "IBAT3U",
1346 SPR_NOACCESS, SPR_NOACCESS,
1347 &spr_read_601_ubat, &spr_write_601_ubatu,
1349 spr_register(env, SPR_IBAT3L, "IBAT3L",
1350 SPR_NOACCESS, SPR_NOACCESS,
1351 &spr_read_601_ubat, &spr_write_601_ubatl,
1357 static void gen_spr_74xx (CPUPPCState *env)
1359 /* Processor identification */
1360 spr_register(env, SPR_PIR, "PIR",
1361 SPR_NOACCESS, SPR_NOACCESS,
1362 &spr_read_generic, &spr_write_pir,
1364 /* XXX : not implemented */
1365 spr_register(env, SPR_74XX_MMCR2, "MMCR2",
1366 SPR_NOACCESS, SPR_NOACCESS,
1367 &spr_read_generic, &spr_write_generic,
1369 /* XXX : not implemented */
1370 spr_register(env, SPR_74XX_UMMCR2, "UMMCR2",
1371 &spr_read_ureg, SPR_NOACCESS,
1372 &spr_read_ureg, SPR_NOACCESS,
1374 /* XXX: not implemented */
1375 spr_register(env, SPR_BAMR, "BAMR",
1376 SPR_NOACCESS, SPR_NOACCESS,
1377 &spr_read_generic, &spr_write_generic,
1379 /* XXX : not implemented */
1380 spr_register(env, SPR_MSSCR0, "MSSCR0",
1381 SPR_NOACCESS, SPR_NOACCESS,
1382 &spr_read_generic, &spr_write_generic,
1384 /* Hardware implementation registers */
1385 /* XXX : not implemented */
1386 spr_register(env, SPR_HID0, "HID0",
1387 SPR_NOACCESS, SPR_NOACCESS,
1388 &spr_read_generic, &spr_write_generic,
1390 /* XXX : not implemented */
1391 spr_register(env, SPR_HID1, "HID1",
1392 SPR_NOACCESS, SPR_NOACCESS,
1393 &spr_read_generic, &spr_write_generic,
1396 spr_register(env, SPR_VRSAVE, "VRSAVE",
1397 &spr_read_generic, &spr_write_generic,
1398 &spr_read_generic, &spr_write_generic,
1400 /* XXX : not implemented */
1401 spr_register(env, SPR_L2CR, "L2CR",
1402 SPR_NOACCESS, SPR_NOACCESS,
1403 &spr_read_generic, spr_access_nop,
1405 /* Not strictly an SPR */
1406 vscr_init(env, 0x00010000);
1409 static void gen_l3_ctrl (CPUPPCState *env)
1412 /* XXX : not implemented */
1413 spr_register(env, SPR_L3CR, "L3CR",
1414 SPR_NOACCESS, SPR_NOACCESS,
1415 &spr_read_generic, &spr_write_generic,
1418 /* XXX : not implemented */
1419 spr_register(env, SPR_L3ITCR0, "L3ITCR0",
1420 SPR_NOACCESS, SPR_NOACCESS,
1421 &spr_read_generic, &spr_write_generic,
1424 /* XXX : not implemented */
1425 spr_register(env, SPR_L3PM, "L3PM",
1426 SPR_NOACCESS, SPR_NOACCESS,
1427 &spr_read_generic, &spr_write_generic,
1431 static void gen_74xx_soft_tlb (CPUPPCState *env, int nb_tlbs, int nb_ways)
1433 #if !defined(CONFIG_USER_ONLY)
1434 env->nb_tlb = nb_tlbs;
1435 env->nb_ways = nb_ways;
1437 env->tlb_type = TLB_6XX;
1438 /* XXX : not implemented */
1439 spr_register(env, SPR_PTEHI, "PTEHI",
1440 SPR_NOACCESS, SPR_NOACCESS,
1441 &spr_read_generic, &spr_write_generic,
1443 /* XXX : not implemented */
1444 spr_register(env, SPR_PTELO, "PTELO",
1445 SPR_NOACCESS, SPR_NOACCESS,
1446 &spr_read_generic, &spr_write_generic,
1448 /* XXX : not implemented */
1449 spr_register(env, SPR_TLBMISS, "TLBMISS",
1450 SPR_NOACCESS, SPR_NOACCESS,
1451 &spr_read_generic, &spr_write_generic,
1456 #if !defined(CONFIG_USER_ONLY)
1457 static void spr_write_e500_l1csr0 (void *opaque, int sprn, int gprn)
1459 TCGv t0 = tcg_temp_new();
1461 tcg_gen_andi_tl(t0, cpu_gpr[gprn], L1CSR0_DCE | L1CSR0_CPE);
1462 gen_store_spr(sprn, t0);
1466 static void spr_write_e500_l1csr1(void *opaque, int sprn, int gprn)
1468 TCGv t0 = tcg_temp_new();
1470 tcg_gen_andi_tl(t0, cpu_gpr[gprn], L1CSR1_ICE | L1CSR1_CPE);
1471 gen_store_spr(sprn, t0);
1475 static void spr_write_booke206_mmucsr0 (void *opaque, int sprn, int gprn)
1477 gen_helper_booke206_tlbflush(cpu_env, cpu_gpr[gprn]);
1480 static void spr_write_booke_pid (void *opaque, int sprn, int gprn)
1482 TCGv_i32 t0 = tcg_const_i32(sprn);
1483 gen_helper_booke_setpid(cpu_env, t0, cpu_gpr[gprn]);
1484 tcg_temp_free_i32(t0);
1488 static void gen_spr_usprgh (CPUPPCState *env)
1490 spr_register(env, SPR_USPRG4, "USPRG4",
1491 &spr_read_ureg, SPR_NOACCESS,
1492 &spr_read_ureg, SPR_NOACCESS,
1494 spr_register(env, SPR_USPRG5, "USPRG5",
1495 &spr_read_ureg, SPR_NOACCESS,
1496 &spr_read_ureg, SPR_NOACCESS,
1498 spr_register(env, SPR_USPRG6, "USPRG6",
1499 &spr_read_ureg, SPR_NOACCESS,
1500 &spr_read_ureg, SPR_NOACCESS,
1502 spr_register(env, SPR_USPRG7, "USPRG7",
1503 &spr_read_ureg, SPR_NOACCESS,
1504 &spr_read_ureg, SPR_NOACCESS,
1508 /* PowerPC BookE SPR */
1509 static void gen_spr_BookE (CPUPPCState *env, uint64_t ivor_mask)
1511 const char *ivor_names[64] = {
1512 "IVOR0", "IVOR1", "IVOR2", "IVOR3",
1513 "IVOR4", "IVOR5", "IVOR6", "IVOR7",
1514 "IVOR8", "IVOR9", "IVOR10", "IVOR11",
1515 "IVOR12", "IVOR13", "IVOR14", "IVOR15",
1516 "IVOR16", "IVOR17", "IVOR18", "IVOR19",
1517 "IVOR20", "IVOR21", "IVOR22", "IVOR23",
1518 "IVOR24", "IVOR25", "IVOR26", "IVOR27",
1519 "IVOR28", "IVOR29", "IVOR30", "IVOR31",
1520 "IVOR32", "IVOR33", "IVOR34", "IVOR35",
1521 "IVOR36", "IVOR37", "IVOR38", "IVOR39",
1522 "IVOR40", "IVOR41", "IVOR42", "IVOR43",
1523 "IVOR44", "IVOR45", "IVOR46", "IVOR47",
1524 "IVOR48", "IVOR49", "IVOR50", "IVOR51",
1525 "IVOR52", "IVOR53", "IVOR54", "IVOR55",
1526 "IVOR56", "IVOR57", "IVOR58", "IVOR59",
1527 "IVOR60", "IVOR61", "IVOR62", "IVOR63",
1529 #define SPR_BOOKE_IVORxx (-1)
1530 int ivor_sprn[64] = {
1531 SPR_BOOKE_IVOR0, SPR_BOOKE_IVOR1, SPR_BOOKE_IVOR2, SPR_BOOKE_IVOR3,
1532 SPR_BOOKE_IVOR4, SPR_BOOKE_IVOR5, SPR_BOOKE_IVOR6, SPR_BOOKE_IVOR7,
1533 SPR_BOOKE_IVOR8, SPR_BOOKE_IVOR9, SPR_BOOKE_IVOR10, SPR_BOOKE_IVOR11,
1534 SPR_BOOKE_IVOR12, SPR_BOOKE_IVOR13, SPR_BOOKE_IVOR14, SPR_BOOKE_IVOR15,
1535 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1536 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1537 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1538 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1539 SPR_BOOKE_IVOR32, SPR_BOOKE_IVOR33, SPR_BOOKE_IVOR34, SPR_BOOKE_IVOR35,
1540 SPR_BOOKE_IVOR36, SPR_BOOKE_IVOR37, SPR_BOOKE_IVOR38, SPR_BOOKE_IVOR39,
1541 SPR_BOOKE_IVOR40, SPR_BOOKE_IVOR41, SPR_BOOKE_IVOR42, SPR_BOOKE_IVORxx,
1542 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1543 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1544 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1545 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1546 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1550 /* Interrupt processing */
1551 spr_register(env, SPR_BOOKE_CSRR0, "CSRR0",
1552 SPR_NOACCESS, SPR_NOACCESS,
1553 &spr_read_generic, &spr_write_generic,
1555 spr_register(env, SPR_BOOKE_CSRR1, "CSRR1",
1556 SPR_NOACCESS, SPR_NOACCESS,
1557 &spr_read_generic, &spr_write_generic,
1560 /* XXX : not implemented */
1561 spr_register(env, SPR_BOOKE_IAC1, "IAC1",
1562 SPR_NOACCESS, SPR_NOACCESS,
1563 &spr_read_generic, &spr_write_generic,
1565 /* XXX : not implemented */
1566 spr_register(env, SPR_BOOKE_IAC2, "IAC2",
1567 SPR_NOACCESS, SPR_NOACCESS,
1568 &spr_read_generic, &spr_write_generic,
1570 /* XXX : not implemented */
1571 spr_register(env, SPR_BOOKE_DAC1, "DAC1",
1572 SPR_NOACCESS, SPR_NOACCESS,
1573 &spr_read_generic, &spr_write_generic,
1575 /* XXX : not implemented */
1576 spr_register(env, SPR_BOOKE_DAC2, "DAC2",
1577 SPR_NOACCESS, SPR_NOACCESS,
1578 &spr_read_generic, &spr_write_generic,
1580 /* XXX : not implemented */
1581 spr_register(env, SPR_BOOKE_DBCR0, "DBCR0",
1582 SPR_NOACCESS, SPR_NOACCESS,
1583 &spr_read_generic, &spr_write_40x_dbcr0,
1585 /* XXX : not implemented */
1586 spr_register(env, SPR_BOOKE_DBCR1, "DBCR1",
1587 SPR_NOACCESS, SPR_NOACCESS,
1588 &spr_read_generic, &spr_write_generic,
1590 /* XXX : not implemented */
1591 spr_register(env, SPR_BOOKE_DBCR2, "DBCR2",
1592 SPR_NOACCESS, SPR_NOACCESS,
1593 &spr_read_generic, &spr_write_generic,
1595 /* XXX : not implemented */
1596 spr_register(env, SPR_BOOKE_DBSR, "DBSR",
1597 SPR_NOACCESS, SPR_NOACCESS,
1598 &spr_read_generic, &spr_write_clear,
1600 spr_register(env, SPR_BOOKE_DEAR, "DEAR",
1601 SPR_NOACCESS, SPR_NOACCESS,
1602 &spr_read_generic, &spr_write_generic,
1604 spr_register(env, SPR_BOOKE_ESR, "ESR",
1605 SPR_NOACCESS, SPR_NOACCESS,
1606 &spr_read_generic, &spr_write_generic,
1608 spr_register(env, SPR_BOOKE_IVPR, "IVPR",
1609 SPR_NOACCESS, SPR_NOACCESS,
1610 &spr_read_generic, &spr_write_excp_prefix,
1612 /* Exception vectors */
1613 for (i = 0; i < 64; i++) {
1614 if (ivor_mask & (1ULL << i)) {
1615 if (ivor_sprn[i] == SPR_BOOKE_IVORxx) {
1616 fprintf(stderr, "ERROR: IVOR %d SPR is not defined\n", i);
1619 spr_register(env, ivor_sprn[i], ivor_names[i],
1620 SPR_NOACCESS, SPR_NOACCESS,
1621 &spr_read_generic, &spr_write_excp_vector,
1625 spr_register(env, SPR_BOOKE_PID, "PID",
1626 SPR_NOACCESS, SPR_NOACCESS,
1627 &spr_read_generic, &spr_write_booke_pid,
1629 spr_register(env, SPR_BOOKE_TCR, "TCR",
1630 SPR_NOACCESS, SPR_NOACCESS,
1631 &spr_read_generic, &spr_write_booke_tcr,
1633 spr_register(env, SPR_BOOKE_TSR, "TSR",
1634 SPR_NOACCESS, SPR_NOACCESS,
1635 &spr_read_generic, &spr_write_booke_tsr,
1638 spr_register(env, SPR_DECR, "DECR",
1639 SPR_NOACCESS, SPR_NOACCESS,
1640 &spr_read_decr, &spr_write_decr,
1642 spr_register(env, SPR_BOOKE_DECAR, "DECAR",
1643 SPR_NOACCESS, SPR_NOACCESS,
1644 SPR_NOACCESS, &spr_write_generic,
1647 spr_register(env, SPR_USPRG0, "USPRG0",
1648 &spr_read_generic, &spr_write_generic,
1649 &spr_read_generic, &spr_write_generic,
1651 spr_register(env, SPR_SPRG4, "SPRG4",
1652 SPR_NOACCESS, SPR_NOACCESS,
1653 &spr_read_generic, &spr_write_generic,
1655 spr_register(env, SPR_SPRG5, "SPRG5",
1656 SPR_NOACCESS, SPR_NOACCESS,
1657 &spr_read_generic, &spr_write_generic,
1659 spr_register(env, SPR_SPRG6, "SPRG6",
1660 SPR_NOACCESS, SPR_NOACCESS,
1661 &spr_read_generic, &spr_write_generic,
1663 spr_register(env, SPR_SPRG7, "SPRG7",
1664 SPR_NOACCESS, SPR_NOACCESS,
1665 &spr_read_generic, &spr_write_generic,
1669 static inline uint32_t gen_tlbncfg(uint32_t assoc, uint32_t minsize,
1670 uint32_t maxsize, uint32_t flags,
1673 return (assoc << TLBnCFG_ASSOC_SHIFT) |
1674 (minsize << TLBnCFG_MINSIZE_SHIFT) |
1675 (maxsize << TLBnCFG_MAXSIZE_SHIFT) |
1679 /* BookE 2.06 storage control registers */
1680 static void gen_spr_BookE206(CPUPPCState *env, uint32_t mas_mask,
1683 #if !defined(CONFIG_USER_ONLY)
1684 const char *mas_names[8] = {
1685 "MAS0", "MAS1", "MAS2", "MAS3", "MAS4", "MAS5", "MAS6", "MAS7",
1688 SPR_BOOKE_MAS0, SPR_BOOKE_MAS1, SPR_BOOKE_MAS2, SPR_BOOKE_MAS3,
1689 SPR_BOOKE_MAS4, SPR_BOOKE_MAS5, SPR_BOOKE_MAS6, SPR_BOOKE_MAS7,
1693 /* TLB assist registers */
1694 /* XXX : not implemented */
1695 for (i = 0; i < 8; i++) {
1696 void (*uea_write)(void *o, int sprn, int gprn) = &spr_write_generic32;
1697 if (i == 2 && (mas_mask & (1 << i)) && (env->insns_flags & PPC_64B)) {
1698 uea_write = &spr_write_generic;
1700 if (mas_mask & (1 << i)) {
1701 spr_register(env, mas_sprn[i], mas_names[i],
1702 SPR_NOACCESS, SPR_NOACCESS,
1703 &spr_read_generic, uea_write,
1707 if (env->nb_pids > 1) {
1708 /* XXX : not implemented */
1709 spr_register(env, SPR_BOOKE_PID1, "PID1",
1710 SPR_NOACCESS, SPR_NOACCESS,
1711 &spr_read_generic, &spr_write_booke_pid,
1714 if (env->nb_pids > 2) {
1715 /* XXX : not implemented */
1716 spr_register(env, SPR_BOOKE_PID2, "PID2",
1717 SPR_NOACCESS, SPR_NOACCESS,
1718 &spr_read_generic, &spr_write_booke_pid,
1721 /* XXX : not implemented */
1722 spr_register(env, SPR_MMUCFG, "MMUCFG",
1723 SPR_NOACCESS, SPR_NOACCESS,
1724 &spr_read_generic, SPR_NOACCESS,
1725 0x00000000); /* TOFIX */
1726 switch (env->nb_ways) {
1728 spr_register(env, SPR_BOOKE_TLB3CFG, "TLB3CFG",
1729 SPR_NOACCESS, SPR_NOACCESS,
1730 &spr_read_generic, SPR_NOACCESS,
1734 spr_register(env, SPR_BOOKE_TLB2CFG, "TLB2CFG",
1735 SPR_NOACCESS, SPR_NOACCESS,
1736 &spr_read_generic, SPR_NOACCESS,
1740 spr_register(env, SPR_BOOKE_TLB1CFG, "TLB1CFG",
1741 SPR_NOACCESS, SPR_NOACCESS,
1742 &spr_read_generic, SPR_NOACCESS,
1746 spr_register(env, SPR_BOOKE_TLB0CFG, "TLB0CFG",
1747 SPR_NOACCESS, SPR_NOACCESS,
1748 &spr_read_generic, SPR_NOACCESS,
1757 gen_spr_usprgh(env);
1760 /* SPR specific to PowerPC 440 implementation */
1761 static void gen_spr_440 (CPUPPCState *env)
1764 /* XXX : not implemented */
1765 spr_register(env, SPR_440_DNV0, "DNV0",
1766 SPR_NOACCESS, SPR_NOACCESS,
1767 &spr_read_generic, &spr_write_generic,
1769 /* XXX : not implemented */
1770 spr_register(env, SPR_440_DNV1, "DNV1",
1771 SPR_NOACCESS, SPR_NOACCESS,
1772 &spr_read_generic, &spr_write_generic,
1774 /* XXX : not implemented */
1775 spr_register(env, SPR_440_DNV2, "DNV2",
1776 SPR_NOACCESS, SPR_NOACCESS,
1777 &spr_read_generic, &spr_write_generic,
1779 /* XXX : not implemented */
1780 spr_register(env, SPR_440_DNV3, "DNV3",
1781 SPR_NOACCESS, SPR_NOACCESS,
1782 &spr_read_generic, &spr_write_generic,
1784 /* XXX : not implemented */
1785 spr_register(env, SPR_440_DTV0, "DTV0",
1786 SPR_NOACCESS, SPR_NOACCESS,
1787 &spr_read_generic, &spr_write_generic,
1789 /* XXX : not implemented */
1790 spr_register(env, SPR_440_DTV1, "DTV1",
1791 SPR_NOACCESS, SPR_NOACCESS,
1792 &spr_read_generic, &spr_write_generic,
1794 /* XXX : not implemented */
1795 spr_register(env, SPR_440_DTV2, "DTV2",
1796 SPR_NOACCESS, SPR_NOACCESS,
1797 &spr_read_generic, &spr_write_generic,
1799 /* XXX : not implemented */
1800 spr_register(env, SPR_440_DTV3, "DTV3",
1801 SPR_NOACCESS, SPR_NOACCESS,
1802 &spr_read_generic, &spr_write_generic,
1804 /* XXX : not implemented */
1805 spr_register(env, SPR_440_DVLIM, "DVLIM",
1806 SPR_NOACCESS, SPR_NOACCESS,
1807 &spr_read_generic, &spr_write_generic,
1809 /* XXX : not implemented */
1810 spr_register(env, SPR_440_INV0, "INV0",
1811 SPR_NOACCESS, SPR_NOACCESS,
1812 &spr_read_generic, &spr_write_generic,
1814 /* XXX : not implemented */
1815 spr_register(env, SPR_440_INV1, "INV1",
1816 SPR_NOACCESS, SPR_NOACCESS,
1817 &spr_read_generic, &spr_write_generic,
1819 /* XXX : not implemented */
1820 spr_register(env, SPR_440_INV2, "INV2",
1821 SPR_NOACCESS, SPR_NOACCESS,
1822 &spr_read_generic, &spr_write_generic,
1824 /* XXX : not implemented */
1825 spr_register(env, SPR_440_INV3, "INV3",
1826 SPR_NOACCESS, SPR_NOACCESS,
1827 &spr_read_generic, &spr_write_generic,
1829 /* XXX : not implemented */
1830 spr_register(env, SPR_440_ITV0, "ITV0",
1831 SPR_NOACCESS, SPR_NOACCESS,
1832 &spr_read_generic, &spr_write_generic,
1834 /* XXX : not implemented */
1835 spr_register(env, SPR_440_ITV1, "ITV1",
1836 SPR_NOACCESS, SPR_NOACCESS,
1837 &spr_read_generic, &spr_write_generic,
1839 /* XXX : not implemented */
1840 spr_register(env, SPR_440_ITV2, "ITV2",
1841 SPR_NOACCESS, SPR_NOACCESS,
1842 &spr_read_generic, &spr_write_generic,
1844 /* XXX : not implemented */
1845 spr_register(env, SPR_440_ITV3, "ITV3",
1846 SPR_NOACCESS, SPR_NOACCESS,
1847 &spr_read_generic, &spr_write_generic,
1849 /* XXX : not implemented */
1850 spr_register(env, SPR_440_IVLIM, "IVLIM",
1851 SPR_NOACCESS, SPR_NOACCESS,
1852 &spr_read_generic, &spr_write_generic,
1855 /* XXX : not implemented */
1856 spr_register(env, SPR_BOOKE_DCDBTRH, "DCDBTRH",
1857 SPR_NOACCESS, SPR_NOACCESS,
1858 &spr_read_generic, SPR_NOACCESS,
1860 /* XXX : not implemented */
1861 spr_register(env, SPR_BOOKE_DCDBTRL, "DCDBTRL",
1862 SPR_NOACCESS, SPR_NOACCESS,
1863 &spr_read_generic, SPR_NOACCESS,
1865 /* XXX : not implemented */
1866 spr_register(env, SPR_BOOKE_ICDBDR, "ICDBDR",
1867 SPR_NOACCESS, SPR_NOACCESS,
1868 &spr_read_generic, SPR_NOACCESS,
1870 /* XXX : not implemented */
1871 spr_register(env, SPR_BOOKE_ICDBTRH, "ICDBTRH",
1872 SPR_NOACCESS, SPR_NOACCESS,
1873 &spr_read_generic, SPR_NOACCESS,
1875 /* XXX : not implemented */
1876 spr_register(env, SPR_BOOKE_ICDBTRL, "ICDBTRL",
1877 SPR_NOACCESS, SPR_NOACCESS,
1878 &spr_read_generic, SPR_NOACCESS,
1880 /* XXX : not implemented */
1881 spr_register(env, SPR_440_DBDR, "DBDR",
1882 SPR_NOACCESS, SPR_NOACCESS,
1883 &spr_read_generic, &spr_write_generic,
1885 /* Processor control */
1886 spr_register(env, SPR_4xx_CCR0, "CCR0",
1887 SPR_NOACCESS, SPR_NOACCESS,
1888 &spr_read_generic, &spr_write_generic,
1890 spr_register(env, SPR_440_RSTCFG, "RSTCFG",
1891 SPR_NOACCESS, SPR_NOACCESS,
1892 &spr_read_generic, SPR_NOACCESS,
1894 /* Storage control */
1895 spr_register(env, SPR_440_MMUCR, "MMUCR",
1896 SPR_NOACCESS, SPR_NOACCESS,
1897 &spr_read_generic, &spr_write_generic,
1901 /* SPR shared between PowerPC 40x implementations */
1902 static void gen_spr_40x (CPUPPCState *env)
1905 /* not emulated, as QEMU do not emulate caches */
1906 spr_register(env, SPR_40x_DCCR, "DCCR",
1907 SPR_NOACCESS, SPR_NOACCESS,
1908 &spr_read_generic, &spr_write_generic,
1910 /* not emulated, as QEMU do not emulate caches */
1911 spr_register(env, SPR_40x_ICCR, "ICCR",
1912 SPR_NOACCESS, SPR_NOACCESS,
1913 &spr_read_generic, &spr_write_generic,
1915 /* not emulated, as QEMU do not emulate caches */
1916 spr_register(env, SPR_BOOKE_ICDBDR, "ICDBDR",
1917 SPR_NOACCESS, SPR_NOACCESS,
1918 &spr_read_generic, SPR_NOACCESS,
1921 spr_register(env, SPR_40x_DEAR, "DEAR",
1922 SPR_NOACCESS, SPR_NOACCESS,
1923 &spr_read_generic, &spr_write_generic,
1925 spr_register(env, SPR_40x_ESR, "ESR",
1926 SPR_NOACCESS, SPR_NOACCESS,
1927 &spr_read_generic, &spr_write_generic,
1929 spr_register(env, SPR_40x_EVPR, "EVPR",
1930 SPR_NOACCESS, SPR_NOACCESS,
1931 &spr_read_generic, &spr_write_excp_prefix,
1933 spr_register(env, SPR_40x_SRR2, "SRR2",
1934 &spr_read_generic, &spr_write_generic,
1935 &spr_read_generic, &spr_write_generic,
1937 spr_register(env, SPR_40x_SRR3, "SRR3",
1938 &spr_read_generic, &spr_write_generic,
1939 &spr_read_generic, &spr_write_generic,
1942 spr_register(env, SPR_40x_PIT, "PIT",
1943 SPR_NOACCESS, SPR_NOACCESS,
1944 &spr_read_40x_pit, &spr_write_40x_pit,
1946 spr_register(env, SPR_40x_TCR, "TCR",
1947 SPR_NOACCESS, SPR_NOACCESS,
1948 &spr_read_generic, &spr_write_booke_tcr,
1950 spr_register(env, SPR_40x_TSR, "TSR",
1951 SPR_NOACCESS, SPR_NOACCESS,
1952 &spr_read_generic, &spr_write_booke_tsr,
1956 /* SPR specific to PowerPC 405 implementation */
1957 static void gen_spr_405 (CPUPPCState *env)
1960 spr_register(env, SPR_40x_PID, "PID",
1961 SPR_NOACCESS, SPR_NOACCESS,
1962 &spr_read_generic, &spr_write_generic,
1964 spr_register(env, SPR_4xx_CCR0, "CCR0",
1965 SPR_NOACCESS, SPR_NOACCESS,
1966 &spr_read_generic, &spr_write_generic,
1968 /* Debug interface */
1969 /* XXX : not implemented */
1970 spr_register(env, SPR_40x_DBCR0, "DBCR0",
1971 SPR_NOACCESS, SPR_NOACCESS,
1972 &spr_read_generic, &spr_write_40x_dbcr0,
1974 /* XXX : not implemented */
1975 spr_register(env, SPR_405_DBCR1, "DBCR1",
1976 SPR_NOACCESS, SPR_NOACCESS,
1977 &spr_read_generic, &spr_write_generic,
1979 /* XXX : not implemented */
1980 spr_register(env, SPR_40x_DBSR, "DBSR",
1981 SPR_NOACCESS, SPR_NOACCESS,
1982 &spr_read_generic, &spr_write_clear,
1983 /* Last reset was system reset */
1985 /* XXX : not implemented */
1986 spr_register(env, SPR_40x_DAC1, "DAC1",
1987 SPR_NOACCESS, SPR_NOACCESS,
1988 &spr_read_generic, &spr_write_generic,
1990 spr_register(env, SPR_40x_DAC2, "DAC2",
1991 SPR_NOACCESS, SPR_NOACCESS,
1992 &spr_read_generic, &spr_write_generic,
1994 /* XXX : not implemented */
1995 spr_register(env, SPR_405_DVC1, "DVC1",
1996 SPR_NOACCESS, SPR_NOACCESS,
1997 &spr_read_generic, &spr_write_generic,
1999 /* XXX : not implemented */
2000 spr_register(env, SPR_405_DVC2, "DVC2",
2001 SPR_NOACCESS, SPR_NOACCESS,
2002 &spr_read_generic, &spr_write_generic,
2004 /* XXX : not implemented */
2005 spr_register(env, SPR_40x_IAC1, "IAC1",
2006 SPR_NOACCESS, SPR_NOACCESS,
2007 &spr_read_generic, &spr_write_generic,
2009 spr_register(env, SPR_40x_IAC2, "IAC2",
2010 SPR_NOACCESS, SPR_NOACCESS,
2011 &spr_read_generic, &spr_write_generic,
2013 /* XXX : not implemented */
2014 spr_register(env, SPR_405_IAC3, "IAC3",
2015 SPR_NOACCESS, SPR_NOACCESS,
2016 &spr_read_generic, &spr_write_generic,
2018 /* XXX : not implemented */
2019 spr_register(env, SPR_405_IAC4, "IAC4",
2020 SPR_NOACCESS, SPR_NOACCESS,
2021 &spr_read_generic, &spr_write_generic,
2023 /* Storage control */
2024 /* XXX: TODO: not implemented */
2025 spr_register(env, SPR_405_SLER, "SLER",
2026 SPR_NOACCESS, SPR_NOACCESS,
2027 &spr_read_generic, &spr_write_40x_sler,
2029 spr_register(env, SPR_40x_ZPR, "ZPR",
2030 SPR_NOACCESS, SPR_NOACCESS,
2031 &spr_read_generic, &spr_write_generic,
2033 /* XXX : not implemented */
2034 spr_register(env, SPR_405_SU0R, "SU0R",
2035 SPR_NOACCESS, SPR_NOACCESS,
2036 &spr_read_generic, &spr_write_generic,
2039 spr_register(env, SPR_USPRG0, "USPRG0",
2040 &spr_read_ureg, SPR_NOACCESS,
2041 &spr_read_ureg, SPR_NOACCESS,
2043 spr_register(env, SPR_SPRG4, "SPRG4",
2044 SPR_NOACCESS, SPR_NOACCESS,
2045 &spr_read_generic, &spr_write_generic,
2047 spr_register(env, SPR_SPRG5, "SPRG5",
2048 SPR_NOACCESS, SPR_NOACCESS,
2049 spr_read_generic, &spr_write_generic,
2051 spr_register(env, SPR_SPRG6, "SPRG6",
2052 SPR_NOACCESS, SPR_NOACCESS,
2053 spr_read_generic, &spr_write_generic,
2055 spr_register(env, SPR_SPRG7, "SPRG7",
2056 SPR_NOACCESS, SPR_NOACCESS,
2057 spr_read_generic, &spr_write_generic,
2059 gen_spr_usprgh(env);
2062 /* SPR shared between PowerPC 401 & 403 implementations */
2063 static void gen_spr_401_403 (CPUPPCState *env)
2066 spr_register(env, SPR_403_VTBL, "TBL",
2067 &spr_read_tbl, SPR_NOACCESS,
2068 &spr_read_tbl, SPR_NOACCESS,
2070 spr_register(env, SPR_403_TBL, "TBL",
2071 SPR_NOACCESS, SPR_NOACCESS,
2072 SPR_NOACCESS, &spr_write_tbl,
2074 spr_register(env, SPR_403_VTBU, "TBU",
2075 &spr_read_tbu, SPR_NOACCESS,
2076 &spr_read_tbu, SPR_NOACCESS,
2078 spr_register(env, SPR_403_TBU, "TBU",
2079 SPR_NOACCESS, SPR_NOACCESS,
2080 SPR_NOACCESS, &spr_write_tbu,
2083 /* not emulated, as QEMU do not emulate caches */
2084 spr_register(env, SPR_403_CDBCR, "CDBCR",
2085 SPR_NOACCESS, SPR_NOACCESS,
2086 &spr_read_generic, &spr_write_generic,
2090 /* SPR specific to PowerPC 401 implementation */
2091 static void gen_spr_401 (CPUPPCState *env)
2093 /* Debug interface */
2094 /* XXX : not implemented */
2095 spr_register(env, SPR_40x_DBCR0, "DBCR",
2096 SPR_NOACCESS, SPR_NOACCESS,
2097 &spr_read_generic, &spr_write_40x_dbcr0,
2099 /* XXX : not implemented */
2100 spr_register(env, SPR_40x_DBSR, "DBSR",
2101 SPR_NOACCESS, SPR_NOACCESS,
2102 &spr_read_generic, &spr_write_clear,
2103 /* Last reset was system reset */
2105 /* XXX : not implemented */
2106 spr_register(env, SPR_40x_DAC1, "DAC",
2107 SPR_NOACCESS, SPR_NOACCESS,
2108 &spr_read_generic, &spr_write_generic,
2110 /* XXX : not implemented */
2111 spr_register(env, SPR_40x_IAC1, "IAC",
2112 SPR_NOACCESS, SPR_NOACCESS,
2113 &spr_read_generic, &spr_write_generic,
2115 /* Storage control */
2116 /* XXX: TODO: not implemented */
2117 spr_register(env, SPR_405_SLER, "SLER",
2118 SPR_NOACCESS, SPR_NOACCESS,
2119 &spr_read_generic, &spr_write_40x_sler,
2121 /* not emulated, as QEMU never does speculative access */
2122 spr_register(env, SPR_40x_SGR, "SGR",
2123 SPR_NOACCESS, SPR_NOACCESS,
2124 &spr_read_generic, &spr_write_generic,
2126 /* not emulated, as QEMU do not emulate caches */
2127 spr_register(env, SPR_40x_DCWR, "DCWR",
2128 SPR_NOACCESS, SPR_NOACCESS,
2129 &spr_read_generic, &spr_write_generic,
2133 static void gen_spr_401x2 (CPUPPCState *env)
2136 spr_register(env, SPR_40x_PID, "PID",
2137 SPR_NOACCESS, SPR_NOACCESS,
2138 &spr_read_generic, &spr_write_generic,
2140 spr_register(env, SPR_40x_ZPR, "ZPR",
2141 SPR_NOACCESS, SPR_NOACCESS,
2142 &spr_read_generic, &spr_write_generic,
2146 /* SPR specific to PowerPC 403 implementation */
2147 static void gen_spr_403 (CPUPPCState *env)
2149 /* Debug interface */
2150 /* XXX : not implemented */
2151 spr_register(env, SPR_40x_DBCR0, "DBCR0",
2152 SPR_NOACCESS, SPR_NOACCESS,
2153 &spr_read_generic, &spr_write_40x_dbcr0,
2155 /* XXX : not implemented */
2156 spr_register(env, SPR_40x_DBSR, "DBSR",
2157 SPR_NOACCESS, SPR_NOACCESS,
2158 &spr_read_generic, &spr_write_clear,
2159 /* Last reset was system reset */
2161 /* XXX : not implemented */
2162 spr_register(env, SPR_40x_DAC1, "DAC1",
2163 SPR_NOACCESS, SPR_NOACCESS,
2164 &spr_read_generic, &spr_write_generic,
2166 /* XXX : not implemented */
2167 spr_register(env, SPR_40x_DAC2, "DAC2",
2168 SPR_NOACCESS, SPR_NOACCESS,
2169 &spr_read_generic, &spr_write_generic,
2171 /* XXX : not implemented */
2172 spr_register(env, SPR_40x_IAC1, "IAC1",
2173 SPR_NOACCESS, SPR_NOACCESS,
2174 &spr_read_generic, &spr_write_generic,
2176 /* XXX : not implemented */
2177 spr_register(env, SPR_40x_IAC2, "IAC2",
2178 SPR_NOACCESS, SPR_NOACCESS,
2179 &spr_read_generic, &spr_write_generic,
2183 static void gen_spr_403_real (CPUPPCState *env)
2185 spr_register(env, SPR_403_PBL1, "PBL1",
2186 SPR_NOACCESS, SPR_NOACCESS,
2187 &spr_read_403_pbr, &spr_write_403_pbr,
2189 spr_register(env, SPR_403_PBU1, "PBU1",
2190 SPR_NOACCESS, SPR_NOACCESS,
2191 &spr_read_403_pbr, &spr_write_403_pbr,
2193 spr_register(env, SPR_403_PBL2, "PBL2",
2194 SPR_NOACCESS, SPR_NOACCESS,
2195 &spr_read_403_pbr, &spr_write_403_pbr,
2197 spr_register(env, SPR_403_PBU2, "PBU2",
2198 SPR_NOACCESS, SPR_NOACCESS,
2199 &spr_read_403_pbr, &spr_write_403_pbr,
2203 static void gen_spr_403_mmu (CPUPPCState *env)
2206 spr_register(env, SPR_40x_PID, "PID",
2207 SPR_NOACCESS, SPR_NOACCESS,
2208 &spr_read_generic, &spr_write_generic,
2210 spr_register(env, SPR_40x_ZPR, "ZPR",
2211 SPR_NOACCESS, SPR_NOACCESS,
2212 &spr_read_generic, &spr_write_generic,
2216 /* SPR specific to PowerPC compression coprocessor extension */
2217 static void gen_spr_compress (CPUPPCState *env)
2219 /* XXX : not implemented */
2220 spr_register(env, SPR_401_SKR, "SKR",
2221 SPR_NOACCESS, SPR_NOACCESS,
2222 &spr_read_generic, &spr_write_generic,
2226 static void gen_spr_5xx_8xx (CPUPPCState *env)
2228 /* Exception processing */
2229 spr_register_kvm(env, SPR_DSISR, "DSISR",
2230 SPR_NOACCESS, SPR_NOACCESS,
2231 &spr_read_generic, &spr_write_generic,
2232 KVM_REG_PPC_DSISR, 0x00000000);
2233 spr_register_kvm(env, SPR_DAR, "DAR",
2234 SPR_NOACCESS, SPR_NOACCESS,
2235 &spr_read_generic, &spr_write_generic,
2236 KVM_REG_PPC_DAR, 0x00000000);
2238 spr_register(env, SPR_DECR, "DECR",
2239 SPR_NOACCESS, SPR_NOACCESS,
2240 &spr_read_decr, &spr_write_decr,
2242 /* XXX : not implemented */
2243 spr_register(env, SPR_MPC_EIE, "EIE",
2244 SPR_NOACCESS, SPR_NOACCESS,
2245 &spr_read_generic, &spr_write_generic,
2247 /* XXX : not implemented */
2248 spr_register(env, SPR_MPC_EID, "EID",
2249 SPR_NOACCESS, SPR_NOACCESS,
2250 &spr_read_generic, &spr_write_generic,
2252 /* XXX : not implemented */
2253 spr_register(env, SPR_MPC_NRI, "NRI",
2254 SPR_NOACCESS, SPR_NOACCESS,
2255 &spr_read_generic, &spr_write_generic,
2257 /* XXX : not implemented */
2258 spr_register(env, SPR_MPC_CMPA, "CMPA",
2259 SPR_NOACCESS, SPR_NOACCESS,
2260 &spr_read_generic, &spr_write_generic,
2262 /* XXX : not implemented */
2263 spr_register(env, SPR_MPC_CMPB, "CMPB",
2264 SPR_NOACCESS, SPR_NOACCESS,
2265 &spr_read_generic, &spr_write_generic,
2267 /* XXX : not implemented */
2268 spr_register(env, SPR_MPC_CMPC, "CMPC",
2269 SPR_NOACCESS, SPR_NOACCESS,
2270 &spr_read_generic, &spr_write_generic,
2272 /* XXX : not implemented */
2273 spr_register(env, SPR_MPC_CMPD, "CMPD",
2274 SPR_NOACCESS, SPR_NOACCESS,
2275 &spr_read_generic, &spr_write_generic,
2277 /* XXX : not implemented */
2278 spr_register(env, SPR_MPC_ECR, "ECR",
2279 SPR_NOACCESS, SPR_NOACCESS,
2280 &spr_read_generic, &spr_write_generic,
2282 /* XXX : not implemented */
2283 spr_register(env, SPR_MPC_DER, "DER",
2284 SPR_NOACCESS, SPR_NOACCESS,
2285 &spr_read_generic, &spr_write_generic,
2287 /* XXX : not implemented */
2288 spr_register(env, SPR_MPC_COUNTA, "COUNTA",
2289 SPR_NOACCESS, SPR_NOACCESS,
2290 &spr_read_generic, &spr_write_generic,
2292 /* XXX : not implemented */
2293 spr_register(env, SPR_MPC_COUNTB, "COUNTB",
2294 SPR_NOACCESS, SPR_NOACCESS,
2295 &spr_read_generic, &spr_write_generic,
2297 /* XXX : not implemented */
2298 spr_register(env, SPR_MPC_CMPE, "CMPE",
2299 SPR_NOACCESS, SPR_NOACCESS,
2300 &spr_read_generic, &spr_write_generic,
2302 /* XXX : not implemented */
2303 spr_register(env, SPR_MPC_CMPF, "CMPF",
2304 SPR_NOACCESS, SPR_NOACCESS,
2305 &spr_read_generic, &spr_write_generic,
2307 /* XXX : not implemented */
2308 spr_register(env, SPR_MPC_CMPG, "CMPG",
2309 SPR_NOACCESS, SPR_NOACCESS,
2310 &spr_read_generic, &spr_write_generic,
2312 /* XXX : not implemented */
2313 spr_register(env, SPR_MPC_CMPH, "CMPH",
2314 SPR_NOACCESS, SPR_NOACCESS,
2315 &spr_read_generic, &spr_write_generic,
2317 /* XXX : not implemented */
2318 spr_register(env, SPR_MPC_LCTRL1, "LCTRL1",
2319 SPR_NOACCESS, SPR_NOACCESS,
2320 &spr_read_generic, &spr_write_generic,
2322 /* XXX : not implemented */
2323 spr_register(env, SPR_MPC_LCTRL2, "LCTRL2",
2324 SPR_NOACCESS, SPR_NOACCESS,
2325 &spr_read_generic, &spr_write_generic,
2327 /* XXX : not implemented */
2328 spr_register(env, SPR_MPC_BAR, "BAR",
2329 SPR_NOACCESS, SPR_NOACCESS,
2330 &spr_read_generic, &spr_write_generic,
2332 /* XXX : not implemented */
2333 spr_register(env, SPR_MPC_DPDR, "DPDR",
2334 SPR_NOACCESS, SPR_NOACCESS,
2335 &spr_read_generic, &spr_write_generic,
2337 /* XXX : not implemented */
2338 spr_register(env, SPR_MPC_IMMR, "IMMR",
2339 SPR_NOACCESS, SPR_NOACCESS,
2340 &spr_read_generic, &spr_write_generic,
2344 static void gen_spr_5xx (CPUPPCState *env)
2346 /* XXX : not implemented */
2347 spr_register(env, SPR_RCPU_MI_GRA, "MI_GRA",
2348 SPR_NOACCESS, SPR_NOACCESS,
2349 &spr_read_generic, &spr_write_generic,
2351 /* XXX : not implemented */
2352 spr_register(env, SPR_RCPU_L2U_GRA, "L2U_GRA",
2353 SPR_NOACCESS, SPR_NOACCESS,
2354 &spr_read_generic, &spr_write_generic,
2356 /* XXX : not implemented */
2357 spr_register(env, SPR_RPCU_BBCMCR, "L2U_BBCMCR",
2358 SPR_NOACCESS, SPR_NOACCESS,
2359 &spr_read_generic, &spr_write_generic,
2361 /* XXX : not implemented */
2362 spr_register(env, SPR_RCPU_L2U_MCR, "L2U_MCR",
2363 SPR_NOACCESS, SPR_NOACCESS,
2364 &spr_read_generic, &spr_write_generic,
2366 /* XXX : not implemented */
2367 spr_register(env, SPR_RCPU_MI_RBA0, "MI_RBA0",
2368 SPR_NOACCESS, SPR_NOACCESS,
2369 &spr_read_generic, &spr_write_generic,
2371 /* XXX : not implemented */
2372 spr_register(env, SPR_RCPU_MI_RBA1, "MI_RBA1",
2373 SPR_NOACCESS, SPR_NOACCESS,
2374 &spr_read_generic, &spr_write_generic,
2376 /* XXX : not implemented */
2377 spr_register(env, SPR_RCPU_MI_RBA2, "MI_RBA2",
2378 SPR_NOACCESS, SPR_NOACCESS,
2379 &spr_read_generic, &spr_write_generic,
2381 /* XXX : not implemented */
2382 spr_register(env, SPR_RCPU_MI_RBA3, "MI_RBA3",
2383 SPR_NOACCESS, SPR_NOACCESS,
2384 &spr_read_generic, &spr_write_generic,
2386 /* XXX : not implemented */
2387 spr_register(env, SPR_RCPU_L2U_RBA0, "L2U_RBA0",
2388 SPR_NOACCESS, SPR_NOACCESS,
2389 &spr_read_generic, &spr_write_generic,
2391 /* XXX : not implemented */
2392 spr_register(env, SPR_RCPU_L2U_RBA1, "L2U_RBA1",
2393 SPR_NOACCESS, SPR_NOACCESS,
2394 &spr_read_generic, &spr_write_generic,
2396 /* XXX : not implemented */
2397 spr_register(env, SPR_RCPU_L2U_RBA2, "L2U_RBA2",
2398 SPR_NOACCESS, SPR_NOACCESS,
2399 &spr_read_generic, &spr_write_generic,
2401 /* XXX : not implemented */
2402 spr_register(env, SPR_RCPU_L2U_RBA3, "L2U_RBA3",
2403 SPR_NOACCESS, SPR_NOACCESS,
2404 &spr_read_generic, &spr_write_generic,
2406 /* XXX : not implemented */
2407 spr_register(env, SPR_RCPU_MI_RA0, "MI_RA0",
2408 SPR_NOACCESS, SPR_NOACCESS,
2409 &spr_read_generic, &spr_write_generic,
2411 /* XXX : not implemented */
2412 spr_register(env, SPR_RCPU_MI_RA1, "MI_RA1",
2413 SPR_NOACCESS, SPR_NOACCESS,
2414 &spr_read_generic, &spr_write_generic,
2416 /* XXX : not implemented */
2417 spr_register(env, SPR_RCPU_MI_RA2, "MI_RA2",
2418 SPR_NOACCESS, SPR_NOACCESS,
2419 &spr_read_generic, &spr_write_generic,
2421 /* XXX : not implemented */
2422 spr_register(env, SPR_RCPU_MI_RA3, "MI_RA3",
2423 SPR_NOACCESS, SPR_NOACCESS,
2424 &spr_read_generic, &spr_write_generic,
2426 /* XXX : not implemented */
2427 spr_register(env, SPR_RCPU_L2U_RA0, "L2U_RA0",
2428 SPR_NOACCESS, SPR_NOACCESS,
2429 &spr_read_generic, &spr_write_generic,
2431 /* XXX : not implemented */
2432 spr_register(env, SPR_RCPU_L2U_RA1, "L2U_RA1",
2433 SPR_NOACCESS, SPR_NOACCESS,
2434 &spr_read_generic, &spr_write_generic,
2436 /* XXX : not implemented */
2437 spr_register(env, SPR_RCPU_L2U_RA2, "L2U_RA2",
2438 SPR_NOACCESS, SPR_NOACCESS,
2439 &spr_read_generic, &spr_write_generic,
2441 /* XXX : not implemented */
2442 spr_register(env, SPR_RCPU_L2U_RA3, "L2U_RA3",
2443 SPR_NOACCESS, SPR_NOACCESS,
2444 &spr_read_generic, &spr_write_generic,
2446 /* XXX : not implemented */
2447 spr_register(env, SPR_RCPU_FPECR, "FPECR",
2448 SPR_NOACCESS, SPR_NOACCESS,
2449 &spr_read_generic, &spr_write_generic,
2453 static void gen_spr_8xx (CPUPPCState *env)
2455 /* XXX : not implemented */
2456 spr_register(env, SPR_MPC_IC_CST, "IC_CST",
2457 SPR_NOACCESS, SPR_NOACCESS,
2458 &spr_read_generic, &spr_write_generic,
2460 /* XXX : not implemented */
2461 spr_register(env, SPR_MPC_IC_ADR, "IC_ADR",
2462 SPR_NOACCESS, SPR_NOACCESS,
2463 &spr_read_generic, &spr_write_generic,
2465 /* XXX : not implemented */
2466 spr_register(env, SPR_MPC_IC_DAT, "IC_DAT",
2467 SPR_NOACCESS, SPR_NOACCESS,
2468 &spr_read_generic, &spr_write_generic,
2470 /* XXX : not implemented */
2471 spr_register(env, SPR_MPC_DC_CST, "DC_CST",
2472 SPR_NOACCESS, SPR_NOACCESS,
2473 &spr_read_generic, &spr_write_generic,
2475 /* XXX : not implemented */
2476 spr_register(env, SPR_MPC_DC_ADR, "DC_ADR",
2477 SPR_NOACCESS, SPR_NOACCESS,
2478 &spr_read_generic, &spr_write_generic,
2480 /* XXX : not implemented */
2481 spr_register(env, SPR_MPC_DC_DAT, "DC_DAT",
2482 SPR_NOACCESS, SPR_NOACCESS,
2483 &spr_read_generic, &spr_write_generic,
2485 /* XXX : not implemented */
2486 spr_register(env, SPR_MPC_MI_CTR, "MI_CTR",
2487 SPR_NOACCESS, SPR_NOACCESS,
2488 &spr_read_generic, &spr_write_generic,
2490 /* XXX : not implemented */
2491 spr_register(env, SPR_MPC_MI_AP, "MI_AP",
2492 SPR_NOACCESS, SPR_NOACCESS,
2493 &spr_read_generic, &spr_write_generic,
2495 /* XXX : not implemented */
2496 spr_register(env, SPR_MPC_MI_EPN, "MI_EPN",
2497 SPR_NOACCESS, SPR_NOACCESS,
2498 &spr_read_generic, &spr_write_generic,
2500 /* XXX : not implemented */
2501 spr_register(env, SPR_MPC_MI_TWC, "MI_TWC",
2502 SPR_NOACCESS, SPR_NOACCESS,
2503 &spr_read_generic, &spr_write_generic,
2505 /* XXX : not implemented */
2506 spr_register(env, SPR_MPC_MI_RPN, "MI_RPN",
2507 SPR_NOACCESS, SPR_NOACCESS,
2508 &spr_read_generic, &spr_write_generic,
2510 /* XXX : not implemented */
2511 spr_register(env, SPR_MPC_MI_DBCAM, "MI_DBCAM",
2512 SPR_NOACCESS, SPR_NOACCESS,
2513 &spr_read_generic, &spr_write_generic,
2515 /* XXX : not implemented */
2516 spr_register(env, SPR_MPC_MI_DBRAM0, "MI_DBRAM0",
2517 SPR_NOACCESS, SPR_NOACCESS,
2518 &spr_read_generic, &spr_write_generic,
2520 /* XXX : not implemented */
2521 spr_register(env, SPR_MPC_MI_DBRAM1, "MI_DBRAM1",
2522 SPR_NOACCESS, SPR_NOACCESS,
2523 &spr_read_generic, &spr_write_generic,
2525 /* XXX : not implemented */
2526 spr_register(env, SPR_MPC_MD_CTR, "MD_CTR",
2527 SPR_NOACCESS, SPR_NOACCESS,
2528 &spr_read_generic, &spr_write_generic,
2530 /* XXX : not implemented */
2531 spr_register(env, SPR_MPC_MD_CASID, "MD_CASID",
2532 SPR_NOACCESS, SPR_NOACCESS,
2533 &spr_read_generic, &spr_write_generic,
2535 /* XXX : not implemented */
2536 spr_register(env, SPR_MPC_MD_AP, "MD_AP",
2537 SPR_NOACCESS, SPR_NOACCESS,
2538 &spr_read_generic, &spr_write_generic,
2540 /* XXX : not implemented */
2541 spr_register(env, SPR_MPC_MD_EPN, "MD_EPN",
2542 SPR_NOACCESS, SPR_NOACCESS,
2543 &spr_read_generic, &spr_write_generic,
2545 /* XXX : not implemented */
2546 spr_register(env, SPR_MPC_MD_TWB, "MD_TWB",
2547 SPR_NOACCESS, SPR_NOACCESS,
2548 &spr_read_generic, &spr_write_generic,
2550 /* XXX : not implemented */
2551 spr_register(env, SPR_MPC_MD_TWC, "MD_TWC",
2552 SPR_NOACCESS, SPR_NOACCESS,
2553 &spr_read_generic, &spr_write_generic,
2555 /* XXX : not implemented */
2556 spr_register(env, SPR_MPC_MD_RPN, "MD_RPN",
2557 SPR_NOACCESS, SPR_NOACCESS,
2558 &spr_read_generic, &spr_write_generic,
2560 /* XXX : not implemented */
2561 spr_register(env, SPR_MPC_MD_TW, "MD_TW",
2562 SPR_NOACCESS, SPR_NOACCESS,
2563 &spr_read_generic, &spr_write_generic,
2565 /* XXX : not implemented */
2566 spr_register(env, SPR_MPC_MD_DBCAM, "MD_DBCAM",
2567 SPR_NOACCESS, SPR_NOACCESS,
2568 &spr_read_generic, &spr_write_generic,
2570 /* XXX : not implemented */
2571 spr_register(env, SPR_MPC_MD_DBRAM0, "MD_DBRAM0",
2572 SPR_NOACCESS, SPR_NOACCESS,
2573 &spr_read_generic, &spr_write_generic,
2575 /* XXX : not implemented */
2576 spr_register(env, SPR_MPC_MD_DBRAM1, "MD_DBRAM1",
2577 SPR_NOACCESS, SPR_NOACCESS,
2578 &spr_read_generic, &spr_write_generic,
2584 * AMR => SPR 29 (Power 2.04)
2585 * CTRL => SPR 136 (Power 2.04)
2586 * CTRL => SPR 152 (Power 2.04)
2587 * SCOMC => SPR 276 (64 bits ?)
2588 * SCOMD => SPR 277 (64 bits ?)
2589 * TBU40 => SPR 286 (Power 2.04 hypv)
2590 * HSPRG0 => SPR 304 (Power 2.04 hypv)
2591 * HSPRG1 => SPR 305 (Power 2.04 hypv)
2592 * HDSISR => SPR 306 (Power 2.04 hypv)
2593 * HDAR => SPR 307 (Power 2.04 hypv)
2594 * PURR => SPR 309 (Power 2.04 hypv)
2595 * HDEC => SPR 310 (Power 2.04 hypv)
2596 * HIOR => SPR 311 (hypv)
2597 * RMOR => SPR 312 (970)
2598 * HRMOR => SPR 313 (Power 2.04 hypv)
2599 * HSRR0 => SPR 314 (Power 2.04 hypv)
2600 * HSRR1 => SPR 315 (Power 2.04 hypv)
2601 * LPIDR => SPR 317 (970)
2602 * EPR => SPR 702 (Power 2.04 emb)
2603 * perf => 768-783 (Power 2.04)
2604 * perf => 784-799 (Power 2.04)
2605 * PPR => SPR 896 (Power 2.04)
2606 * EPLC => SPR 947 (Power 2.04 emb)
2607 * EPSC => SPR 948 (Power 2.04 emb)
2608 * DABRX => 1015 (Power 2.04 hypv)
2609 * FPECR => SPR 1022 (?)
2610 * ... and more (thermal management, performance counters, ...)
2613 /*****************************************************************************/
2614 /* Exception vectors models */
2615 static void init_excp_4xx_real (CPUPPCState *env)
2617 #if !defined(CONFIG_USER_ONLY)
2618 env->excp_vectors[POWERPC_EXCP_CRITICAL] = 0x00000100;
2619 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2620 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2621 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2622 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2623 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2624 env->excp_vectors[POWERPC_EXCP_PIT] = 0x00001000;
2625 env->excp_vectors[POWERPC_EXCP_FIT] = 0x00001010;
2626 env->excp_vectors[POWERPC_EXCP_WDT] = 0x00001020;
2627 env->excp_vectors[POWERPC_EXCP_DEBUG] = 0x00002000;
2628 env->ivor_mask = 0x0000FFF0UL;
2629 env->ivpr_mask = 0xFFFF0000UL;
2630 /* Hardware reset vector */
2631 env->hreset_vector = 0xFFFFFFFCUL;
2635 static void init_excp_4xx_softmmu (CPUPPCState *env)
2637 #if !defined(CONFIG_USER_ONLY)
2638 env->excp_vectors[POWERPC_EXCP_CRITICAL] = 0x00000100;
2639 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2640 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2641 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2642 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2643 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2644 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2645 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2646 env->excp_vectors[POWERPC_EXCP_PIT] = 0x00001000;
2647 env->excp_vectors[POWERPC_EXCP_FIT] = 0x00001010;
2648 env->excp_vectors[POWERPC_EXCP_WDT] = 0x00001020;
2649 env->excp_vectors[POWERPC_EXCP_DTLB] = 0x00001100;
2650 env->excp_vectors[POWERPC_EXCP_ITLB] = 0x00001200;
2651 env->excp_vectors[POWERPC_EXCP_DEBUG] = 0x00002000;
2652 env->ivor_mask = 0x0000FFF0UL;
2653 env->ivpr_mask = 0xFFFF0000UL;
2654 /* Hardware reset vector */
2655 env->hreset_vector = 0xFFFFFFFCUL;
2659 static void init_excp_MPC5xx (CPUPPCState *env)
2661 #if !defined(CONFIG_USER_ONLY)
2662 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2663 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2664 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2665 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2666 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2667 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000900;
2668 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2669 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2670 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2671 env->excp_vectors[POWERPC_EXCP_FPA] = 0x00000E00;
2672 env->excp_vectors[POWERPC_EXCP_EMUL] = 0x00001000;
2673 env->excp_vectors[POWERPC_EXCP_DABR] = 0x00001C00;
2674 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001C00;
2675 env->excp_vectors[POWERPC_EXCP_MEXTBR] = 0x00001E00;
2676 env->excp_vectors[POWERPC_EXCP_NMEXTBR] = 0x00001F00;
2677 env->ivor_mask = 0x0000FFF0UL;
2678 env->ivpr_mask = 0xFFFF0000UL;
2679 /* Hardware reset vector */
2680 env->hreset_vector = 0x00000100UL;
2684 static void init_excp_MPC8xx (CPUPPCState *env)
2686 #if !defined(CONFIG_USER_ONLY)
2687 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2688 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2689 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2690 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2691 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2692 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2693 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2694 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000900;
2695 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2696 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2697 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2698 env->excp_vectors[POWERPC_EXCP_FPA] = 0x00000E00;
2699 env->excp_vectors[POWERPC_EXCP_EMUL] = 0x00001000;
2700 env->excp_vectors[POWERPC_EXCP_ITLB] = 0x00001100;
2701 env->excp_vectors[POWERPC_EXCP_DTLB] = 0x00001200;
2702 env->excp_vectors[POWERPC_EXCP_ITLBE] = 0x00001300;
2703 env->excp_vectors[POWERPC_EXCP_DTLBE] = 0x00001400;
2704 env->excp_vectors[POWERPC_EXCP_DABR] = 0x00001C00;
2705 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001C00;
2706 env->excp_vectors[POWERPC_EXCP_MEXTBR] = 0x00001E00;
2707 env->excp_vectors[POWERPC_EXCP_NMEXTBR] = 0x00001F00;
2708 env->ivor_mask = 0x0000FFF0UL;
2709 env->ivpr_mask = 0xFFFF0000UL;
2710 /* Hardware reset vector */
2711 env->hreset_vector = 0x00000100UL;
2715 static void init_excp_G2 (CPUPPCState *env)
2717 #if !defined(CONFIG_USER_ONLY)
2718 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2719 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2720 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2721 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2722 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2723 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2724 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2725 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2726 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2727 env->excp_vectors[POWERPC_EXCP_CRITICAL] = 0x00000A00;
2728 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2729 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2730 env->excp_vectors[POWERPC_EXCP_IFTLB] = 0x00001000;
2731 env->excp_vectors[POWERPC_EXCP_DLTLB] = 0x00001100;
2732 env->excp_vectors[POWERPC_EXCP_DSTLB] = 0x00001200;
2733 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
2734 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
2735 /* Hardware reset vector */
2736 env->hreset_vector = 0x00000100UL;
2740 static void init_excp_e200(CPUPPCState *env, target_ulong ivpr_mask)
2742 #if !defined(CONFIG_USER_ONLY)
2743 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000FFC;
2744 env->excp_vectors[POWERPC_EXCP_CRITICAL] = 0x00000000;
2745 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000000;
2746 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000000;
2747 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000000;
2748 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000000;
2749 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000000;
2750 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000000;
2751 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000000;
2752 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000000;
2753 env->excp_vectors[POWERPC_EXCP_APU] = 0x00000000;
2754 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000000;
2755 env->excp_vectors[POWERPC_EXCP_FIT] = 0x00000000;
2756 env->excp_vectors[POWERPC_EXCP_WDT] = 0x00000000;
2757 env->excp_vectors[POWERPC_EXCP_DTLB] = 0x00000000;
2758 env->excp_vectors[POWERPC_EXCP_ITLB] = 0x00000000;
2759 env->excp_vectors[POWERPC_EXCP_DEBUG] = 0x00000000;
2760 env->excp_vectors[POWERPC_EXCP_SPEU] = 0x00000000;
2761 env->excp_vectors[POWERPC_EXCP_EFPDI] = 0x00000000;
2762 env->excp_vectors[POWERPC_EXCP_EFPRI] = 0x00000000;
2763 env->ivor_mask = 0x0000FFF7UL;
2764 env->ivpr_mask = ivpr_mask;
2765 /* Hardware reset vector */
2766 env->hreset_vector = 0xFFFFFFFCUL;
2770 static void init_excp_BookE (CPUPPCState *env)
2772 #if !defined(CONFIG_USER_ONLY)
2773 env->excp_vectors[POWERPC_EXCP_CRITICAL] = 0x00000000;
2774 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000000;
2775 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000000;
2776 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000000;
2777 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000000;
2778 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000000;
2779 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000000;
2780 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000000;
2781 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000000;
2782 env->excp_vectors[POWERPC_EXCP_APU] = 0x00000000;
2783 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000000;
2784 env->excp_vectors[POWERPC_EXCP_FIT] = 0x00000000;
2785 env->excp_vectors[POWERPC_EXCP_WDT] = 0x00000000;
2786 env->excp_vectors[POWERPC_EXCP_DTLB] = 0x00000000;
2787 env->excp_vectors[POWERPC_EXCP_ITLB] = 0x00000000;
2788 env->excp_vectors[POWERPC_EXCP_DEBUG] = 0x00000000;
2789 env->ivor_mask = 0x0000FFF0UL;
2790 env->ivpr_mask = 0xFFFF0000UL;
2791 /* Hardware reset vector */
2792 env->hreset_vector = 0xFFFFFFFCUL;
2796 static void init_excp_601 (CPUPPCState *env)
2798 #if !defined(CONFIG_USER_ONLY)
2799 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2800 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2801 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2802 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2803 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2804 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2805 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2806 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2807 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2808 env->excp_vectors[POWERPC_EXCP_IO] = 0x00000A00;
2809 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2810 env->excp_vectors[POWERPC_EXCP_RUNM] = 0x00002000;
2811 /* Hardware reset vector */
2812 env->hreset_vector = 0x00000100UL;
2816 static void init_excp_602 (CPUPPCState *env)
2818 #if !defined(CONFIG_USER_ONLY)
2819 /* XXX: exception prefix has a special behavior on 602 */
2820 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2821 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2822 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2823 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2824 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2825 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2826 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2827 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2828 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2829 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2830 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2831 env->excp_vectors[POWERPC_EXCP_IFTLB] = 0x00001000;
2832 env->excp_vectors[POWERPC_EXCP_DLTLB] = 0x00001100;
2833 env->excp_vectors[POWERPC_EXCP_DSTLB] = 0x00001200;
2834 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
2835 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
2836 env->excp_vectors[POWERPC_EXCP_WDT] = 0x00001500;
2837 env->excp_vectors[POWERPC_EXCP_EMUL] = 0x00001600;
2838 /* Hardware reset vector */
2839 env->hreset_vector = 0x00000100UL;
2843 static void init_excp_603 (CPUPPCState *env)
2845 #if !defined(CONFIG_USER_ONLY)
2846 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2847 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2848 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2849 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2850 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2851 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2852 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2853 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2854 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2855 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2856 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2857 env->excp_vectors[POWERPC_EXCP_IFTLB] = 0x00001000;
2858 env->excp_vectors[POWERPC_EXCP_DLTLB] = 0x00001100;
2859 env->excp_vectors[POWERPC_EXCP_DSTLB] = 0x00001200;
2860 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
2861 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
2862 /* Hardware reset vector */
2863 env->hreset_vector = 0x00000100UL;
2867 static void init_excp_604 (CPUPPCState *env)
2869 #if !defined(CONFIG_USER_ONLY)
2870 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2871 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2872 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2873 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2874 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2875 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2876 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2877 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2878 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2879 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2880 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2881 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
2882 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
2883 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
2884 /* Hardware reset vector */
2885 env->hreset_vector = 0x00000100UL;
2889 static void init_excp_7x0 (CPUPPCState *env)
2891 #if !defined(CONFIG_USER_ONLY)
2892 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2893 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2894 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2895 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2896 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2897 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2898 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2899 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2900 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2901 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2902 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2903 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
2904 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
2905 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
2906 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001700;
2907 /* Hardware reset vector */
2908 env->hreset_vector = 0x00000100UL;
2912 static void init_excp_750cl (CPUPPCState *env)
2914 #if !defined(CONFIG_USER_ONLY)
2915 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2916 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2917 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2918 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2919 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2920 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2921 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2922 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2923 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2924 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2925 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2926 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
2927 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
2928 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
2929 /* Hardware reset vector */
2930 env->hreset_vector = 0x00000100UL;
2934 static void init_excp_750cx (CPUPPCState *env)
2936 #if !defined(CONFIG_USER_ONLY)
2937 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2938 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2939 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2940 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2941 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2942 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2943 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2944 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2945 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2946 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2947 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2948 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
2949 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
2950 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001700;
2951 /* Hardware reset vector */
2952 env->hreset_vector = 0x00000100UL;
2956 /* XXX: Check if this is correct */
2957 static void init_excp_7x5 (CPUPPCState *env)
2959 #if !defined(CONFIG_USER_ONLY)
2960 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2961 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2962 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2963 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2964 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2965 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2966 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2967 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2968 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2969 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2970 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2971 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
2972 env->excp_vectors[POWERPC_EXCP_IFTLB] = 0x00001000;
2973 env->excp_vectors[POWERPC_EXCP_DLTLB] = 0x00001100;
2974 env->excp_vectors[POWERPC_EXCP_DSTLB] = 0x00001200;
2975 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
2976 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
2977 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001700;
2978 /* Hardware reset vector */
2979 env->hreset_vector = 0x00000100UL;
2983 static void init_excp_7400 (CPUPPCState *env)
2985 #if !defined(CONFIG_USER_ONLY)
2986 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2987 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2988 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2989 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2990 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2991 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2992 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2993 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2994 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2995 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2996 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2997 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
2998 env->excp_vectors[POWERPC_EXCP_VPU] = 0x00000F20;
2999 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3000 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
3001 env->excp_vectors[POWERPC_EXCP_VPUA] = 0x00001600;
3002 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001700;
3003 /* Hardware reset vector */
3004 env->hreset_vector = 0x00000100UL;
3008 static void init_excp_7450 (CPUPPCState *env)
3010 #if !defined(CONFIG_USER_ONLY)
3011 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3012 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3013 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3014 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3015 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3016 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3017 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3018 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3019 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3020 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3021 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3022 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3023 env->excp_vectors[POWERPC_EXCP_VPU] = 0x00000F20;
3024 env->excp_vectors[POWERPC_EXCP_IFTLB] = 0x00001000;
3025 env->excp_vectors[POWERPC_EXCP_DLTLB] = 0x00001100;
3026 env->excp_vectors[POWERPC_EXCP_DSTLB] = 0x00001200;
3027 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3028 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
3029 env->excp_vectors[POWERPC_EXCP_VPUA] = 0x00001600;
3030 /* Hardware reset vector */
3031 env->hreset_vector = 0x00000100UL;
3035 #if defined (TARGET_PPC64)
3036 static void init_excp_970 (CPUPPCState *env)
3038 #if !defined(CONFIG_USER_ONLY)
3039 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3040 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3041 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3042 env->excp_vectors[POWERPC_EXCP_DSEG] = 0x00000380;
3043 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3044 env->excp_vectors[POWERPC_EXCP_ISEG] = 0x00000480;
3045 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3046 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3047 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3048 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3049 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3050 env->excp_vectors[POWERPC_EXCP_HDECR] = 0x00000980;
3051 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3052 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3053 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3054 env->excp_vectors[POWERPC_EXCP_VPU] = 0x00000F20;
3055 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3056 env->excp_vectors[POWERPC_EXCP_MAINT] = 0x00001600;
3057 env->excp_vectors[POWERPC_EXCP_VPUA] = 0x00001700;
3058 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001800;
3059 /* Hardware reset vector */
3060 env->hreset_vector = 0x0000000000000100ULL;
3064 static void init_excp_POWER7 (CPUPPCState *env)
3066 #if !defined(CONFIG_USER_ONLY)
3067 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3068 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3069 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3070 env->excp_vectors[POWERPC_EXCP_DSEG] = 0x00000380;
3071 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3072 env->excp_vectors[POWERPC_EXCP_ISEG] = 0x00000480;
3073 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3074 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3075 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3076 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3077 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3078 env->excp_vectors[POWERPC_EXCP_HDECR] = 0x00000980;
3079 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3080 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3081 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3082 env->excp_vectors[POWERPC_EXCP_VPU] = 0x00000F20;
3083 env->excp_vectors[POWERPC_EXCP_VSXU] = 0x00000F40;
3084 env->excp_vectors[POWERPC_EXCP_FU] = 0x00000F60;
3085 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3086 env->excp_vectors[POWERPC_EXCP_MAINT] = 0x00001600;
3087 env->excp_vectors[POWERPC_EXCP_VPUA] = 0x00001700;
3088 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001800;
3089 /* Hardware reset vector */
3090 env->hreset_vector = 0x0000000000000100ULL;
3095 /*****************************************************************************/
3096 /* Power management enable checks */
3097 static int check_pow_none (CPUPPCState *env)
3102 static int check_pow_nocheck (CPUPPCState *env)
3107 static int check_pow_hid0 (CPUPPCState *env)
3109 if (env->spr[SPR_HID0] & 0x00E00000)
3115 static int check_pow_hid0_74xx (CPUPPCState *env)
3117 if (env->spr[SPR_HID0] & 0x00600000)
3123 static bool ppc_cpu_interrupts_big_endian_always(PowerPCCPU *cpu)
3129 static bool ppc_cpu_interrupts_big_endian_lpcr(PowerPCCPU *cpu)
3131 return !(cpu->env.spr[SPR_LPCR] & LPCR_ILE);
3135 /*****************************************************************************/
3136 /* PowerPC implementations definitions */
3138 #define POWERPC_FAMILY(_name) \
3140 glue(glue(ppc_, _name), _cpu_family_class_init)(ObjectClass *, void *); \
3142 static const TypeInfo \
3143 glue(glue(ppc_, _name), _cpu_family_type_info) = { \
3144 .name = stringify(_name) "-family-" TYPE_POWERPC_CPU, \
3145 .parent = TYPE_POWERPC_CPU, \
3147 .class_init = glue(glue(ppc_, _name), _cpu_family_class_init), \
3150 static void glue(glue(ppc_, _name), _cpu_family_register_types)(void) \
3152 type_register_static( \
3153 &glue(glue(ppc_, _name), _cpu_family_type_info)); \
3156 type_init(glue(glue(ppc_, _name), _cpu_family_register_types)) \
3158 static void glue(glue(ppc_, _name), _cpu_family_class_init)
3160 static void init_proc_401 (CPUPPCState *env)
3163 gen_spr_401_403(env);
3165 init_excp_4xx_real(env);
3166 env->dcache_line_size = 32;
3167 env->icache_line_size = 32;
3168 /* Allocate hardware IRQ controller */
3169 ppc40x_irq_init(env);
3171 SET_FIT_PERIOD(12, 16, 20, 24);
3172 SET_WDT_PERIOD(16, 20, 24, 28);
3175 POWERPC_FAMILY(401)(ObjectClass *oc, void *data)
3177 DeviceClass *dc = DEVICE_CLASS(oc);
3178 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3180 dc->desc = "PowerPC 401";
3181 pcc->init_proc = init_proc_401;
3182 pcc->check_pow = check_pow_nocheck;
3183 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3184 PPC_WRTEE | PPC_DCR |
3185 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3187 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3188 PPC_4xx_COMMON | PPC_40x_EXCP;
3189 pcc->msr_mask = (1ull << MSR_KEY) |
3198 pcc->mmu_model = POWERPC_MMU_REAL;
3199 pcc->excp_model = POWERPC_EXCP_40x;
3200 pcc->bus_model = PPC_FLAGS_INPUT_401;
3201 pcc->bfd_mach = bfd_mach_ppc_403;
3202 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
3203 POWERPC_FLAG_BUS_CLK;
3206 static void init_proc_401x2 (CPUPPCState *env)
3209 gen_spr_401_403(env);
3211 gen_spr_compress(env);
3212 /* Memory management */
3213 #if !defined(CONFIG_USER_ONLY)
3217 env->tlb_type = TLB_EMB;
3219 init_excp_4xx_softmmu(env);
3220 env->dcache_line_size = 32;
3221 env->icache_line_size = 32;
3222 /* Allocate hardware IRQ controller */
3223 ppc40x_irq_init(env);
3225 SET_FIT_PERIOD(12, 16, 20, 24);
3226 SET_WDT_PERIOD(16, 20, 24, 28);
3229 POWERPC_FAMILY(401x2)(ObjectClass *oc, void *data)
3231 DeviceClass *dc = DEVICE_CLASS(oc);
3232 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3234 dc->desc = "PowerPC 401x2";
3235 pcc->init_proc = init_proc_401x2;
3236 pcc->check_pow = check_pow_nocheck;
3237 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
3238 PPC_DCR | PPC_WRTEE |
3239 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3240 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3241 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3242 PPC_40x_TLB | PPC_MEM_TLBIA | PPC_MEM_TLBSYNC |
3243 PPC_4xx_COMMON | PPC_40x_EXCP;
3244 pcc->msr_mask = (1ull << 20) |
3256 pcc->mmu_model = POWERPC_MMU_SOFT_4xx_Z;
3257 pcc->excp_model = POWERPC_EXCP_40x;
3258 pcc->bus_model = PPC_FLAGS_INPUT_401;
3259 pcc->bfd_mach = bfd_mach_ppc_403;
3260 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
3261 POWERPC_FLAG_BUS_CLK;
3264 static void init_proc_401x3 (CPUPPCState *env)
3267 gen_spr_401_403(env);
3270 gen_spr_compress(env);
3271 init_excp_4xx_softmmu(env);
3272 env->dcache_line_size = 32;
3273 env->icache_line_size = 32;
3274 /* Allocate hardware IRQ controller */
3275 ppc40x_irq_init(env);
3277 SET_FIT_PERIOD(12, 16, 20, 24);
3278 SET_WDT_PERIOD(16, 20, 24, 28);
3281 POWERPC_FAMILY(401x3)(ObjectClass *oc, void *data)
3283 DeviceClass *dc = DEVICE_CLASS(oc);
3284 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3286 dc->desc = "PowerPC 401x3";
3287 pcc->init_proc = init_proc_401x3;
3288 pcc->check_pow = check_pow_nocheck;
3289 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
3290 PPC_DCR | PPC_WRTEE |
3291 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3292 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3293 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3294 PPC_40x_TLB | PPC_MEM_TLBIA | PPC_MEM_TLBSYNC |
3295 PPC_4xx_COMMON | PPC_40x_EXCP;
3296 pcc->msr_mask = (1ull << 20) |
3309 pcc->mmu_model = POWERPC_MMU_SOFT_4xx_Z;
3310 pcc->excp_model = POWERPC_EXCP_40x;
3311 pcc->bus_model = PPC_FLAGS_INPUT_401;
3312 pcc->bfd_mach = bfd_mach_ppc_403;
3313 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
3314 POWERPC_FLAG_BUS_CLK;
3317 static void init_proc_IOP480 (CPUPPCState *env)
3320 gen_spr_401_403(env);
3322 gen_spr_compress(env);
3323 /* Memory management */
3324 #if !defined(CONFIG_USER_ONLY)
3328 env->tlb_type = TLB_EMB;
3330 init_excp_4xx_softmmu(env);
3331 env->dcache_line_size = 32;
3332 env->icache_line_size = 32;
3333 /* Allocate hardware IRQ controller */
3334 ppc40x_irq_init(env);
3336 SET_FIT_PERIOD(8, 12, 16, 20);
3337 SET_WDT_PERIOD(16, 20, 24, 28);
3340 POWERPC_FAMILY(IOP480)(ObjectClass *oc, void *data)
3342 DeviceClass *dc = DEVICE_CLASS(oc);
3343 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3345 dc->desc = "IOP480";
3346 pcc->init_proc = init_proc_IOP480;
3347 pcc->check_pow = check_pow_nocheck;
3348 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3349 PPC_DCR | PPC_WRTEE |
3350 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3351 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3352 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3353 PPC_40x_TLB | PPC_MEM_TLBIA | PPC_MEM_TLBSYNC |
3354 PPC_4xx_COMMON | PPC_40x_EXCP;
3355 pcc->msr_mask = (1ull << 20) |
3367 pcc->mmu_model = POWERPC_MMU_SOFT_4xx_Z;
3368 pcc->excp_model = POWERPC_EXCP_40x;
3369 pcc->bus_model = PPC_FLAGS_INPUT_401;
3370 pcc->bfd_mach = bfd_mach_ppc_403;
3371 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
3372 POWERPC_FLAG_BUS_CLK;
3375 static void init_proc_403 (CPUPPCState *env)
3378 gen_spr_401_403(env);
3380 gen_spr_403_real(env);
3381 init_excp_4xx_real(env);
3382 env->dcache_line_size = 32;
3383 env->icache_line_size = 32;
3384 /* Allocate hardware IRQ controller */
3385 ppc40x_irq_init(env);
3387 SET_FIT_PERIOD(8, 12, 16, 20);
3388 SET_WDT_PERIOD(16, 20, 24, 28);
3391 POWERPC_FAMILY(403)(ObjectClass *oc, void *data)
3393 DeviceClass *dc = DEVICE_CLASS(oc);
3394 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3396 dc->desc = "PowerPC 403";
3397 pcc->init_proc = init_proc_403;
3398 pcc->check_pow = check_pow_nocheck;
3399 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3400 PPC_DCR | PPC_WRTEE |
3401 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3403 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3404 PPC_4xx_COMMON | PPC_40x_EXCP;
3405 pcc->msr_mask = (1ull << MSR_POW) |
3414 pcc->mmu_model = POWERPC_MMU_REAL;
3415 pcc->excp_model = POWERPC_EXCP_40x;
3416 pcc->bus_model = PPC_FLAGS_INPUT_401;
3417 pcc->bfd_mach = bfd_mach_ppc_403;
3418 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_PX |
3419 POWERPC_FLAG_BUS_CLK;
3422 static void init_proc_403GCX (CPUPPCState *env)
3425 gen_spr_401_403(env);
3427 gen_spr_403_real(env);
3428 gen_spr_403_mmu(env);
3429 /* Bus access control */
3430 /* not emulated, as QEMU never does speculative access */
3431 spr_register(env, SPR_40x_SGR, "SGR",
3432 SPR_NOACCESS, SPR_NOACCESS,
3433 &spr_read_generic, &spr_write_generic,
3435 /* not emulated, as QEMU do not emulate caches */
3436 spr_register(env, SPR_40x_DCWR, "DCWR",
3437 SPR_NOACCESS, SPR_NOACCESS,
3438 &spr_read_generic, &spr_write_generic,
3440 /* Memory management */
3441 #if !defined(CONFIG_USER_ONLY)
3445 env->tlb_type = TLB_EMB;
3447 init_excp_4xx_softmmu(env);
3448 env->dcache_line_size = 32;
3449 env->icache_line_size = 32;
3450 /* Allocate hardware IRQ controller */
3451 ppc40x_irq_init(env);
3453 SET_FIT_PERIOD(8, 12, 16, 20);
3454 SET_WDT_PERIOD(16, 20, 24, 28);
3457 POWERPC_FAMILY(403GCX)(ObjectClass *oc, void *data)
3459 DeviceClass *dc = DEVICE_CLASS(oc);
3460 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3462 dc->desc = "PowerPC 403 GCX";
3463 pcc->init_proc = init_proc_403GCX;
3464 pcc->check_pow = check_pow_nocheck;
3465 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3466 PPC_DCR | PPC_WRTEE |
3467 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3469 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3470 PPC_40x_TLB | PPC_MEM_TLBIA | PPC_MEM_TLBSYNC |
3471 PPC_4xx_COMMON | PPC_40x_EXCP;
3472 pcc->msr_mask = (1ull << MSR_POW) |
3481 pcc->mmu_model = POWERPC_MMU_SOFT_4xx_Z;
3482 pcc->excp_model = POWERPC_EXCP_40x;
3483 pcc->bus_model = PPC_FLAGS_INPUT_401;
3484 pcc->bfd_mach = bfd_mach_ppc_403;
3485 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_PX |
3486 POWERPC_FLAG_BUS_CLK;
3489 static void init_proc_405 (CPUPPCState *env)
3495 /* Bus access control */
3496 /* not emulated, as QEMU never does speculative access */
3497 spr_register(env, SPR_40x_SGR, "SGR",
3498 SPR_NOACCESS, SPR_NOACCESS,
3499 &spr_read_generic, &spr_write_generic,
3501 /* not emulated, as QEMU do not emulate caches */
3502 spr_register(env, SPR_40x_DCWR, "DCWR",
3503 SPR_NOACCESS, SPR_NOACCESS,
3504 &spr_read_generic, &spr_write_generic,
3506 /* Memory management */
3507 #if !defined(CONFIG_USER_ONLY)
3511 env->tlb_type = TLB_EMB;
3513 init_excp_4xx_softmmu(env);
3514 env->dcache_line_size = 32;
3515 env->icache_line_size = 32;
3516 /* Allocate hardware IRQ controller */
3517 ppc40x_irq_init(env);
3519 SET_FIT_PERIOD(8, 12, 16, 20);
3520 SET_WDT_PERIOD(16, 20, 24, 28);
3523 POWERPC_FAMILY(405)(ObjectClass *oc, void *data)
3525 DeviceClass *dc = DEVICE_CLASS(oc);
3526 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3528 dc->desc = "PowerPC 405";
3529 pcc->init_proc = init_proc_405;
3530 pcc->check_pow = check_pow_nocheck;
3531 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
3532 PPC_DCR | PPC_WRTEE |
3533 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3534 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3535 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3536 PPC_40x_TLB | PPC_MEM_TLBIA | PPC_MEM_TLBSYNC |
3537 PPC_4xx_COMMON | PPC_405_MAC | PPC_40x_EXCP;
3538 pcc->msr_mask = (1ull << MSR_POW) |
3547 pcc->mmu_model = POWERPC_MMU_SOFT_4xx;
3548 pcc->excp_model = POWERPC_EXCP_40x;
3549 pcc->bus_model = PPC_FLAGS_INPUT_405;
3550 pcc->bfd_mach = bfd_mach_ppc_403;
3551 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
3552 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
3555 static void init_proc_440EP (CPUPPCState *env)
3559 gen_spr_BookE(env, 0x000000000000FFFFULL);
3561 gen_spr_usprgh(env);
3562 /* Processor identification */
3563 spr_register(env, SPR_BOOKE_PIR, "PIR",
3564 SPR_NOACCESS, SPR_NOACCESS,
3565 &spr_read_generic, &spr_write_pir,
3567 /* XXX : not implemented */
3568 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
3569 SPR_NOACCESS, SPR_NOACCESS,
3570 &spr_read_generic, &spr_write_generic,
3572 /* XXX : not implemented */
3573 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
3574 SPR_NOACCESS, SPR_NOACCESS,
3575 &spr_read_generic, &spr_write_generic,
3577 /* XXX : not implemented */
3578 spr_register(env, SPR_BOOKE_DVC1, "DVC1",
3579 SPR_NOACCESS, SPR_NOACCESS,
3580 &spr_read_generic, &spr_write_generic,
3582 /* XXX : not implemented */
3583 spr_register(env, SPR_BOOKE_DVC2, "DVC2",
3584 SPR_NOACCESS, SPR_NOACCESS,
3585 &spr_read_generic, &spr_write_generic,
3587 /* XXX : not implemented */
3588 spr_register(env, SPR_BOOKE_MCSR, "MCSR",
3589 SPR_NOACCESS, SPR_NOACCESS,
3590 &spr_read_generic, &spr_write_generic,
3592 spr_register(env, SPR_BOOKE_MCSRR0, "MCSRR0",
3593 SPR_NOACCESS, SPR_NOACCESS,
3594 &spr_read_generic, &spr_write_generic,
3596 spr_register(env, SPR_BOOKE_MCSRR1, "MCSRR1",
3597 SPR_NOACCESS, SPR_NOACCESS,
3598 &spr_read_generic, &spr_write_generic,
3600 /* XXX : not implemented */
3601 spr_register(env, SPR_440_CCR1, "CCR1",
3602 SPR_NOACCESS, SPR_NOACCESS,
3603 &spr_read_generic, &spr_write_generic,
3605 /* Memory management */
3606 #if !defined(CONFIG_USER_ONLY)
3610 env->tlb_type = TLB_EMB;
3612 init_excp_BookE(env);
3613 env->dcache_line_size = 32;
3614 env->icache_line_size = 32;
3615 ppc40x_irq_init(env);
3617 SET_FIT_PERIOD(12, 16, 20, 24);
3618 SET_WDT_PERIOD(20, 24, 28, 32);
3621 POWERPC_FAMILY(440EP)(ObjectClass *oc, void *data)
3623 DeviceClass *dc = DEVICE_CLASS(oc);
3624 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3626 dc->desc = "PowerPC 440 EP";
3627 pcc->init_proc = init_proc_440EP;
3628 pcc->check_pow = check_pow_nocheck;
3629 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3630 PPC_FLOAT | PPC_FLOAT_FRES | PPC_FLOAT_FSEL |
3631 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
3633 PPC_DCR | PPC_WRTEE | PPC_RFMCI |
3634 PPC_CACHE | PPC_CACHE_ICBI |
3635 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3636 PPC_MEM_TLBSYNC | PPC_MFTB |
3637 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
3639 pcc->msr_mask = (1ull << MSR_POW) |
3651 pcc->mmu_model = POWERPC_MMU_BOOKE;
3652 pcc->excp_model = POWERPC_EXCP_BOOKE;
3653 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
3654 pcc->bfd_mach = bfd_mach_ppc_403;
3655 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
3656 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
3659 static void init_proc_440GP (CPUPPCState *env)
3663 gen_spr_BookE(env, 0x000000000000FFFFULL);
3665 gen_spr_usprgh(env);
3666 /* Processor identification */
3667 spr_register(env, SPR_BOOKE_PIR, "PIR",
3668 SPR_NOACCESS, SPR_NOACCESS,
3669 &spr_read_generic, &spr_write_pir,
3671 /* XXX : not implemented */
3672 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
3673 SPR_NOACCESS, SPR_NOACCESS,
3674 &spr_read_generic, &spr_write_generic,
3676 /* XXX : not implemented */
3677 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
3678 SPR_NOACCESS, SPR_NOACCESS,
3679 &spr_read_generic, &spr_write_generic,
3681 /* XXX : not implemented */
3682 spr_register(env, SPR_BOOKE_DVC1, "DVC1",
3683 SPR_NOACCESS, SPR_NOACCESS,
3684 &spr_read_generic, &spr_write_generic,
3686 /* XXX : not implemented */
3687 spr_register(env, SPR_BOOKE_DVC2, "DVC2",
3688 SPR_NOACCESS, SPR_NOACCESS,
3689 &spr_read_generic, &spr_write_generic,
3691 /* Memory management */
3692 #if !defined(CONFIG_USER_ONLY)
3696 env->tlb_type = TLB_EMB;
3698 init_excp_BookE(env);
3699 env->dcache_line_size = 32;
3700 env->icache_line_size = 32;
3701 /* XXX: TODO: allocate internal IRQ controller */
3703 SET_FIT_PERIOD(12, 16, 20, 24);
3704 SET_WDT_PERIOD(20, 24, 28, 32);
3707 POWERPC_FAMILY(440GP)(ObjectClass *oc, void *data)
3709 DeviceClass *dc = DEVICE_CLASS(oc);
3710 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3712 dc->desc = "PowerPC 440 GP";
3713 pcc->init_proc = init_proc_440GP;
3714 pcc->check_pow = check_pow_nocheck;
3715 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3716 PPC_DCR | PPC_DCRX | PPC_WRTEE | PPC_MFAPIDI |
3717 PPC_CACHE | PPC_CACHE_ICBI |
3718 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3719 PPC_MEM_TLBSYNC | PPC_TLBIVA | PPC_MFTB |
3720 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
3722 pcc->msr_mask = (1ull << MSR_POW) |
3734 pcc->mmu_model = POWERPC_MMU_BOOKE;
3735 pcc->excp_model = POWERPC_EXCP_BOOKE;
3736 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
3737 pcc->bfd_mach = bfd_mach_ppc_403;
3738 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
3739 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
3742 static void init_proc_440x4 (CPUPPCState *env)
3746 gen_spr_BookE(env, 0x000000000000FFFFULL);
3748 gen_spr_usprgh(env);
3749 /* Processor identification */
3750 spr_register(env, SPR_BOOKE_PIR, "PIR",
3751 SPR_NOACCESS, SPR_NOACCESS,
3752 &spr_read_generic, &spr_write_pir,
3754 /* XXX : not implemented */
3755 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
3756 SPR_NOACCESS, SPR_NOACCESS,
3757 &spr_read_generic, &spr_write_generic,
3759 /* XXX : not implemented */
3760 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
3761 SPR_NOACCESS, SPR_NOACCESS,
3762 &spr_read_generic, &spr_write_generic,
3764 /* XXX : not implemented */
3765 spr_register(env, SPR_BOOKE_DVC1, "DVC1",
3766 SPR_NOACCESS, SPR_NOACCESS,
3767 &spr_read_generic, &spr_write_generic,
3769 /* XXX : not implemented */
3770 spr_register(env, SPR_BOOKE_DVC2, "DVC2",
3771 SPR_NOACCESS, SPR_NOACCESS,
3772 &spr_read_generic, &spr_write_generic,
3774 /* Memory management */
3775 #if !defined(CONFIG_USER_ONLY)
3779 env->tlb_type = TLB_EMB;
3781 init_excp_BookE(env);
3782 env->dcache_line_size = 32;
3783 env->icache_line_size = 32;
3784 /* XXX: TODO: allocate internal IRQ controller */
3786 SET_FIT_PERIOD(12, 16, 20, 24);
3787 SET_WDT_PERIOD(20, 24, 28, 32);
3790 POWERPC_FAMILY(440x4)(ObjectClass *oc, void *data)
3792 DeviceClass *dc = DEVICE_CLASS(oc);
3793 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3795 dc->desc = "PowerPC 440x4";
3796 pcc->init_proc = init_proc_440x4;
3797 pcc->check_pow = check_pow_nocheck;
3798 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3799 PPC_DCR | PPC_WRTEE |
3800 PPC_CACHE | PPC_CACHE_ICBI |
3801 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3802 PPC_MEM_TLBSYNC | PPC_MFTB |
3803 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
3805 pcc->msr_mask = (1ull << MSR_POW) |
3817 pcc->mmu_model = POWERPC_MMU_BOOKE;
3818 pcc->excp_model = POWERPC_EXCP_BOOKE;
3819 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
3820 pcc->bfd_mach = bfd_mach_ppc_403;
3821 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
3822 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
3825 static void init_proc_440x5 (CPUPPCState *env)
3829 gen_spr_BookE(env, 0x000000000000FFFFULL);
3831 gen_spr_usprgh(env);
3832 /* Processor identification */
3833 spr_register(env, SPR_BOOKE_PIR, "PIR",
3834 SPR_NOACCESS, SPR_NOACCESS,
3835 &spr_read_generic, &spr_write_pir,
3837 /* XXX : not implemented */
3838 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
3839 SPR_NOACCESS, SPR_NOACCESS,
3840 &spr_read_generic, &spr_write_generic,
3842 /* XXX : not implemented */
3843 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
3844 SPR_NOACCESS, SPR_NOACCESS,
3845 &spr_read_generic, &spr_write_generic,
3847 /* XXX : not implemented */
3848 spr_register(env, SPR_BOOKE_DVC1, "DVC1",
3849 SPR_NOACCESS, SPR_NOACCESS,
3850 &spr_read_generic, &spr_write_generic,
3852 /* XXX : not implemented */
3853 spr_register(env, SPR_BOOKE_DVC2, "DVC2",
3854 SPR_NOACCESS, SPR_NOACCESS,
3855 &spr_read_generic, &spr_write_generic,
3857 /* XXX : not implemented */
3858 spr_register(env, SPR_BOOKE_MCSR, "MCSR",
3859 SPR_NOACCESS, SPR_NOACCESS,
3860 &spr_read_generic, &spr_write_generic,
3862 spr_register(env, SPR_BOOKE_MCSRR0, "MCSRR0",
3863 SPR_NOACCESS, SPR_NOACCESS,
3864 &spr_read_generic, &spr_write_generic,
3866 spr_register(env, SPR_BOOKE_MCSRR1, "MCSRR1",
3867 SPR_NOACCESS, SPR_NOACCESS,
3868 &spr_read_generic, &spr_write_generic,
3870 /* XXX : not implemented */
3871 spr_register(env, SPR_440_CCR1, "CCR1",
3872 SPR_NOACCESS, SPR_NOACCESS,
3873 &spr_read_generic, &spr_write_generic,
3875 /* Memory management */
3876 #if !defined(CONFIG_USER_ONLY)
3880 env->tlb_type = TLB_EMB;
3882 init_excp_BookE(env);
3883 env->dcache_line_size = 32;
3884 env->icache_line_size = 32;
3885 ppc40x_irq_init(env);
3887 SET_FIT_PERIOD(12, 16, 20, 24);
3888 SET_WDT_PERIOD(20, 24, 28, 32);
3891 POWERPC_FAMILY(440x5)(ObjectClass *oc, void *data)
3893 DeviceClass *dc = DEVICE_CLASS(oc);
3894 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3896 dc->desc = "PowerPC 440x5";
3897 pcc->init_proc = init_proc_440x5;
3898 pcc->check_pow = check_pow_nocheck;
3899 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3900 PPC_DCR | PPC_WRTEE | PPC_RFMCI |
3901 PPC_CACHE | PPC_CACHE_ICBI |
3902 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3903 PPC_MEM_TLBSYNC | PPC_MFTB |
3904 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
3906 pcc->msr_mask = (1ull << MSR_POW) |
3918 pcc->mmu_model = POWERPC_MMU_BOOKE;
3919 pcc->excp_model = POWERPC_EXCP_BOOKE;
3920 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
3921 pcc->bfd_mach = bfd_mach_ppc_403;
3922 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
3923 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
3926 POWERPC_FAMILY(440x5wDFPU)(ObjectClass *oc, void *data)
3928 DeviceClass *dc = DEVICE_CLASS(oc);
3929 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3931 dc->desc = "PowerPC 440x5 with double precision FPU";
3932 pcc->init_proc = init_proc_440x5;
3933 pcc->check_pow = check_pow_nocheck;
3934 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3935 PPC_FLOAT | PPC_FLOAT_FSQRT |
3937 PPC_DCR | PPC_WRTEE | PPC_RFMCI |
3938 PPC_CACHE | PPC_CACHE_ICBI |
3939 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3940 PPC_MEM_TLBSYNC | PPC_MFTB |
3941 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
3943 pcc->insns_flags2 = PPC2_FP_CVT_S64;
3944 pcc->msr_mask = (1ull << MSR_POW) |
3956 pcc->mmu_model = POWERPC_MMU_BOOKE;
3957 pcc->excp_model = POWERPC_EXCP_BOOKE;
3958 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
3959 pcc->bfd_mach = bfd_mach_ppc_403;
3960 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
3961 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
3964 static void init_proc_460 (CPUPPCState *env)
3968 gen_spr_BookE(env, 0x000000000000FFFFULL);
3970 gen_spr_usprgh(env);
3971 /* Processor identification */
3972 spr_register(env, SPR_BOOKE_PIR, "PIR",
3973 SPR_NOACCESS, SPR_NOACCESS,
3974 &spr_read_generic, &spr_write_pir,
3976 /* XXX : not implemented */
3977 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
3978 SPR_NOACCESS, SPR_NOACCESS,
3979 &spr_read_generic, &spr_write_generic,
3981 /* XXX : not implemented */
3982 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
3983 SPR_NOACCESS, SPR_NOACCESS,
3984 &spr_read_generic, &spr_write_generic,
3986 /* XXX : not implemented */
3987 spr_register(env, SPR_BOOKE_DVC1, "DVC1",
3988 SPR_NOACCESS, SPR_NOACCESS,
3989 &spr_read_generic, &spr_write_generic,
3991 /* XXX : not implemented */
3992 spr_register(env, SPR_BOOKE_DVC2, "DVC2",
3993 SPR_NOACCESS, SPR_NOACCESS,
3994 &spr_read_generic, &spr_write_generic,
3996 /* XXX : not implemented */
3997 spr_register(env, SPR_BOOKE_MCSR, "MCSR",
3998 SPR_NOACCESS, SPR_NOACCESS,
3999 &spr_read_generic, &spr_write_generic,
4001 spr_register(env, SPR_BOOKE_MCSRR0, "MCSRR0",
4002 SPR_NOACCESS, SPR_NOACCESS,
4003 &spr_read_generic, &spr_write_generic,
4005 spr_register(env, SPR_BOOKE_MCSRR1, "MCSRR1",
4006 SPR_NOACCESS, SPR_NOACCESS,
4007 &spr_read_generic, &spr_write_generic,
4009 /* XXX : not implemented */
4010 spr_register(env, SPR_440_CCR1, "CCR1",
4011 SPR_NOACCESS, SPR_NOACCESS,
4012 &spr_read_generic, &spr_write_generic,
4014 /* XXX : not implemented */
4015 spr_register(env, SPR_DCRIPR, "SPR_DCRIPR",
4016 &spr_read_generic, &spr_write_generic,
4017 &spr_read_generic, &spr_write_generic,
4019 /* Memory management */
4020 #if !defined(CONFIG_USER_ONLY)
4024 env->tlb_type = TLB_EMB;
4026 init_excp_BookE(env);
4027 env->dcache_line_size = 32;
4028 env->icache_line_size = 32;
4029 /* XXX: TODO: allocate internal IRQ controller */
4031 SET_FIT_PERIOD(12, 16, 20, 24);
4032 SET_WDT_PERIOD(20, 24, 28, 32);
4035 POWERPC_FAMILY(460)(ObjectClass *oc, void *data)
4037 DeviceClass *dc = DEVICE_CLASS(oc);
4038 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4040 dc->desc = "PowerPC 460 (guessed)";
4041 pcc->init_proc = init_proc_460;
4042 pcc->check_pow = check_pow_nocheck;
4043 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
4044 PPC_DCR | PPC_DCRX | PPC_DCRUX |
4045 PPC_WRTEE | PPC_MFAPIDI | PPC_MFTB |
4046 PPC_CACHE | PPC_CACHE_ICBI |
4047 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
4048 PPC_MEM_TLBSYNC | PPC_TLBIVA |
4049 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
4051 pcc->msr_mask = (1ull << MSR_POW) |
4063 pcc->mmu_model = POWERPC_MMU_BOOKE;
4064 pcc->excp_model = POWERPC_EXCP_BOOKE;
4065 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
4066 pcc->bfd_mach = bfd_mach_ppc_403;
4067 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
4068 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
4071 static void init_proc_460F (CPUPPCState *env)
4075 gen_spr_BookE(env, 0x000000000000FFFFULL);
4077 gen_spr_usprgh(env);
4078 /* Processor identification */
4079 spr_register(env, SPR_BOOKE_PIR, "PIR",
4080 SPR_NOACCESS, SPR_NOACCESS,
4081 &spr_read_generic, &spr_write_pir,
4083 /* XXX : not implemented */
4084 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
4085 SPR_NOACCESS, SPR_NOACCESS,
4086 &spr_read_generic, &spr_write_generic,
4088 /* XXX : not implemented */
4089 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
4090 SPR_NOACCESS, SPR_NOACCESS,
4091 &spr_read_generic, &spr_write_generic,
4093 /* XXX : not implemented */
4094 spr_register(env, SPR_BOOKE_DVC1, "DVC1",
4095 SPR_NOACCESS, SPR_NOACCESS,
4096 &spr_read_generic, &spr_write_generic,
4098 /* XXX : not implemented */
4099 spr_register(env, SPR_BOOKE_DVC2, "DVC2",
4100 SPR_NOACCESS, SPR_NOACCESS,
4101 &spr_read_generic, &spr_write_generic,
4103 /* XXX : not implemented */
4104 spr_register(env, SPR_BOOKE_MCSR, "MCSR",
4105 SPR_NOACCESS, SPR_NOACCESS,
4106 &spr_read_generic, &spr_write_generic,
4108 spr_register(env, SPR_BOOKE_MCSRR0, "MCSRR0",
4109 SPR_NOACCESS, SPR_NOACCESS,
4110 &spr_read_generic, &spr_write_generic,
4112 spr_register(env, SPR_BOOKE_MCSRR1, "MCSRR1",
4113 SPR_NOACCESS, SPR_NOACCESS,
4114 &spr_read_generic, &spr_write_generic,
4116 /* XXX : not implemented */
4117 spr_register(env, SPR_440_CCR1, "CCR1",
4118 SPR_NOACCESS, SPR_NOACCESS,
4119 &spr_read_generic, &spr_write_generic,
4121 /* XXX : not implemented */
4122 spr_register(env, SPR_DCRIPR, "SPR_DCRIPR",
4123 &spr_read_generic, &spr_write_generic,
4124 &spr_read_generic, &spr_write_generic,
4126 /* Memory management */
4127 #if !defined(CONFIG_USER_ONLY)
4131 env->tlb_type = TLB_EMB;
4133 init_excp_BookE(env);
4134 env->dcache_line_size = 32;
4135 env->icache_line_size = 32;
4136 /* XXX: TODO: allocate internal IRQ controller */
4138 SET_FIT_PERIOD(12, 16, 20, 24);
4139 SET_WDT_PERIOD(20, 24, 28, 32);
4142 POWERPC_FAMILY(460F)(ObjectClass *oc, void *data)
4144 DeviceClass *dc = DEVICE_CLASS(oc);
4145 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4147 dc->desc = "PowerPC 460F (guessed)";
4148 pcc->init_proc = init_proc_460F;
4149 pcc->check_pow = check_pow_nocheck;
4150 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
4151 PPC_FLOAT | PPC_FLOAT_FRES | PPC_FLOAT_FSEL |
4152 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
4153 PPC_FLOAT_STFIWX | PPC_MFTB |
4154 PPC_DCR | PPC_DCRX | PPC_DCRUX |
4155 PPC_WRTEE | PPC_MFAPIDI |
4156 PPC_CACHE | PPC_CACHE_ICBI |
4157 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
4158 PPC_MEM_TLBSYNC | PPC_TLBIVA |
4159 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
4161 pcc->msr_mask = (1ull << MSR_POW) |
4173 pcc->mmu_model = POWERPC_MMU_BOOKE;
4174 pcc->excp_model = POWERPC_EXCP_BOOKE;
4175 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
4176 pcc->bfd_mach = bfd_mach_ppc_403;
4177 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
4178 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
4181 static void init_proc_MPC5xx (CPUPPCState *env)
4185 gen_spr_5xx_8xx(env);
4187 init_excp_MPC5xx(env);
4188 env->dcache_line_size = 32;
4189 env->icache_line_size = 32;
4190 /* XXX: TODO: allocate internal IRQ controller */
4193 POWERPC_FAMILY(MPC5xx)(ObjectClass *oc, void *data)
4195 DeviceClass *dc = DEVICE_CLASS(oc);
4196 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4198 dc->desc = "Freescale 5xx cores (aka RCPU)";
4199 pcc->init_proc = init_proc_MPC5xx;
4200 pcc->check_pow = check_pow_none;
4201 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
4202 PPC_MEM_EIEIO | PPC_MEM_SYNC |
4203 PPC_CACHE_ICBI | PPC_FLOAT | PPC_FLOAT_STFIWX |
4205 pcc->msr_mask = (1ull << MSR_ILE) |
4217 pcc->mmu_model = POWERPC_MMU_REAL;
4218 pcc->excp_model = POWERPC_EXCP_603;
4219 pcc->bus_model = PPC_FLAGS_INPUT_RCPU;
4220 pcc->bfd_mach = bfd_mach_ppc_505;
4221 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
4222 POWERPC_FLAG_BUS_CLK;
4225 static void init_proc_MPC8xx (CPUPPCState *env)
4229 gen_spr_5xx_8xx(env);
4231 init_excp_MPC8xx(env);
4232 env->dcache_line_size = 32;
4233 env->icache_line_size = 32;
4234 /* XXX: TODO: allocate internal IRQ controller */
4237 POWERPC_FAMILY(MPC8xx)(ObjectClass *oc, void *data)
4239 DeviceClass *dc = DEVICE_CLASS(oc);
4240 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4242 dc->desc = "Freescale 8xx cores (aka PowerQUICC)";
4243 pcc->init_proc = init_proc_MPC8xx;
4244 pcc->check_pow = check_pow_none;
4245 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
4246 PPC_MEM_EIEIO | PPC_MEM_SYNC |
4247 PPC_CACHE_ICBI | PPC_MFTB;
4248 pcc->msr_mask = (1ull << MSR_ILE) |
4260 pcc->mmu_model = POWERPC_MMU_MPC8xx;
4261 pcc->excp_model = POWERPC_EXCP_603;
4262 pcc->bus_model = PPC_FLAGS_INPUT_RCPU;
4263 pcc->bfd_mach = bfd_mach_ppc_860;
4264 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
4265 POWERPC_FLAG_BUS_CLK;
4268 /* Freescale 82xx cores (aka PowerQUICC-II) */
4270 static void init_proc_G2 (CPUPPCState *env)
4272 gen_spr_ne_601(env);
4273 gen_spr_G2_755(env);
4277 /* External access control */
4278 /* XXX : not implemented */
4279 spr_register(env, SPR_EAR, "EAR",
4280 SPR_NOACCESS, SPR_NOACCESS,
4281 &spr_read_generic, &spr_write_generic,
4283 /* Hardware implementation register */
4284 /* XXX : not implemented */
4285 spr_register(env, SPR_HID0, "HID0",
4286 SPR_NOACCESS, SPR_NOACCESS,
4287 &spr_read_generic, &spr_write_generic,
4289 /* XXX : not implemented */
4290 spr_register(env, SPR_HID1, "HID1",
4291 SPR_NOACCESS, SPR_NOACCESS,
4292 &spr_read_generic, &spr_write_generic,
4294 /* XXX : not implemented */
4295 spr_register(env, SPR_HID2, "HID2",
4296 SPR_NOACCESS, SPR_NOACCESS,
4297 &spr_read_generic, &spr_write_generic,
4299 /* Memory management */
4302 gen_6xx_7xx_soft_tlb(env, 64, 2);
4304 env->dcache_line_size = 32;
4305 env->icache_line_size = 32;
4306 /* Allocate hardware IRQ controller */
4307 ppc6xx_irq_init(env);
4310 POWERPC_FAMILY(G2)(ObjectClass *oc, void *data)
4312 DeviceClass *dc = DEVICE_CLASS(oc);
4313 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4315 dc->desc = "PowerPC G2";
4316 pcc->init_proc = init_proc_G2;
4317 pcc->check_pow = check_pow_hid0;
4318 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
4319 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
4321 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
4322 PPC_MEM_SYNC | PPC_MEM_EIEIO |
4323 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
4324 PPC_SEGMENT | PPC_EXTERN;
4325 pcc->msr_mask = (1ull << MSR_POW) |
4326 (1ull << MSR_TGPR) |
4340 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
4341 pcc->excp_model = POWERPC_EXCP_G2;
4342 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
4343 pcc->bfd_mach = bfd_mach_ppc_ec603e;
4344 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
4345 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
4348 static void init_proc_G2LE (CPUPPCState *env)
4350 gen_spr_ne_601(env);
4351 gen_spr_G2_755(env);
4355 /* External access control */
4356 /* XXX : not implemented */
4357 spr_register(env, SPR_EAR, "EAR",
4358 SPR_NOACCESS, SPR_NOACCESS,
4359 &spr_read_generic, &spr_write_generic,
4361 /* Hardware implementation register */
4362 /* XXX : not implemented */
4363 spr_register(env, SPR_HID0, "HID0",
4364 SPR_NOACCESS, SPR_NOACCESS,
4365 &spr_read_generic, &spr_write_generic,
4367 /* XXX : not implemented */
4368 spr_register(env, SPR_HID1, "HID1",
4369 SPR_NOACCESS, SPR_NOACCESS,
4370 &spr_read_generic, &spr_write_generic,
4372 /* XXX : not implemented */
4373 spr_register(env, SPR_HID2, "HID2",
4374 SPR_NOACCESS, SPR_NOACCESS,
4375 &spr_read_generic, &spr_write_generic,
4378 /* Memory management */
4381 gen_6xx_7xx_soft_tlb(env, 64, 2);
4383 env->dcache_line_size = 32;
4384 env->icache_line_size = 32;
4385 /* Allocate hardware IRQ controller */
4386 ppc6xx_irq_init(env);
4389 POWERPC_FAMILY(G2LE)(ObjectClass *oc, void *data)
4391 DeviceClass *dc = DEVICE_CLASS(oc);
4392 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4394 dc->desc = "PowerPC G2LE";
4395 pcc->init_proc = init_proc_G2LE;
4396 pcc->check_pow = check_pow_hid0;
4397 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
4398 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
4400 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
4401 PPC_MEM_SYNC | PPC_MEM_EIEIO |
4402 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
4403 PPC_SEGMENT | PPC_EXTERN;
4404 pcc->msr_mask = (1ull << MSR_POW) |
4405 (1ull << MSR_TGPR) |
4421 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
4422 pcc->excp_model = POWERPC_EXCP_G2;
4423 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
4424 pcc->bfd_mach = bfd_mach_ppc_ec603e;
4425 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
4426 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
4429 static void init_proc_e200 (CPUPPCState *env)
4433 gen_spr_BookE(env, 0x000000070000FFFFULL);
4434 /* XXX : not implemented */
4435 spr_register(env, SPR_BOOKE_SPEFSCR, "SPEFSCR",
4436 &spr_read_spefscr, &spr_write_spefscr,
4437 &spr_read_spefscr, &spr_write_spefscr,
4439 /* Memory management */
4440 gen_spr_BookE206(env, 0x0000005D, NULL);
4441 /* XXX : not implemented */
4442 spr_register(env, SPR_HID0, "HID0",
4443 SPR_NOACCESS, SPR_NOACCESS,
4444 &spr_read_generic, &spr_write_generic,
4446 /* XXX : not implemented */
4447 spr_register(env, SPR_HID1, "HID1",
4448 SPR_NOACCESS, SPR_NOACCESS,
4449 &spr_read_generic, &spr_write_generic,
4451 /* XXX : not implemented */
4452 spr_register(env, SPR_Exxx_ALTCTXCR, "ALTCTXCR",
4453 SPR_NOACCESS, SPR_NOACCESS,
4454 &spr_read_generic, &spr_write_generic,
4456 /* XXX : not implemented */
4457 spr_register(env, SPR_Exxx_BUCSR, "BUCSR",
4458 SPR_NOACCESS, SPR_NOACCESS,
4459 &spr_read_generic, &spr_write_generic,
4461 /* XXX : not implemented */
4462 spr_register(env, SPR_Exxx_CTXCR, "CTXCR",
4463 SPR_NOACCESS, SPR_NOACCESS,
4464 &spr_read_generic, &spr_write_generic,
4466 /* XXX : not implemented */
4467 spr_register(env, SPR_Exxx_DBCNT, "DBCNT",
4468 SPR_NOACCESS, SPR_NOACCESS,
4469 &spr_read_generic, &spr_write_generic,
4471 /* XXX : not implemented */
4472 spr_register(env, SPR_Exxx_DBCR3, "DBCR3",
4473 SPR_NOACCESS, SPR_NOACCESS,
4474 &spr_read_generic, &spr_write_generic,
4476 /* XXX : not implemented */
4477 spr_register(env, SPR_Exxx_L1CFG0, "L1CFG0",
4478 &spr_read_generic, SPR_NOACCESS,
4479 &spr_read_generic, SPR_NOACCESS,
4481 /* XXX : not implemented */
4482 spr_register(env, SPR_Exxx_L1CSR0, "L1CSR0",
4483 SPR_NOACCESS, SPR_NOACCESS,
4484 &spr_read_generic, &spr_write_generic,
4486 /* XXX : not implemented */
4487 spr_register(env, SPR_Exxx_L1FINV0, "L1FINV0",
4488 SPR_NOACCESS, SPR_NOACCESS,
4489 &spr_read_generic, &spr_write_generic,
4491 /* XXX : not implemented */
4492 spr_register(env, SPR_BOOKE_TLB0CFG, "TLB0CFG",
4493 SPR_NOACCESS, SPR_NOACCESS,
4494 &spr_read_generic, &spr_write_generic,
4496 /* XXX : not implemented */
4497 spr_register(env, SPR_BOOKE_TLB1CFG, "TLB1CFG",
4498 SPR_NOACCESS, SPR_NOACCESS,
4499 &spr_read_generic, &spr_write_generic,
4501 /* XXX : not implemented */
4502 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
4503 SPR_NOACCESS, SPR_NOACCESS,
4504 &spr_read_generic, &spr_write_generic,
4506 /* XXX : not implemented */
4507 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
4508 SPR_NOACCESS, SPR_NOACCESS,
4509 &spr_read_generic, &spr_write_generic,
4511 /* XXX : not implemented */
4512 spr_register(env, SPR_MMUCSR0, "MMUCSR0",
4513 SPR_NOACCESS, SPR_NOACCESS,
4514 &spr_read_generic, &spr_write_generic,
4515 0x00000000); /* TOFIX */
4516 spr_register(env, SPR_BOOKE_DSRR0, "DSRR0",
4517 SPR_NOACCESS, SPR_NOACCESS,
4518 &spr_read_generic, &spr_write_generic,
4520 spr_register(env, SPR_BOOKE_DSRR1, "DSRR1",
4521 SPR_NOACCESS, SPR_NOACCESS,
4522 &spr_read_generic, &spr_write_generic,
4524 #if !defined(CONFIG_USER_ONLY)
4528 env->tlb_type = TLB_EMB;
4530 init_excp_e200(env, 0xFFFF0000UL);
4531 env->dcache_line_size = 32;
4532 env->icache_line_size = 32;
4533 /* XXX: TODO: allocate internal IRQ controller */
4536 POWERPC_FAMILY(e200)(ObjectClass *oc, void *data)
4538 DeviceClass *dc = DEVICE_CLASS(oc);
4539 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4541 dc->desc = "e200 core";
4542 pcc->init_proc = init_proc_e200;
4543 pcc->check_pow = check_pow_hid0;
4544 /* XXX: unimplemented instructions:
4551 * all SPE multiply-accumulate instructions
4553 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL |
4554 PPC_SPE | PPC_SPE_SINGLE |
4555 PPC_WRTEE | PPC_RFDI |
4556 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
4557 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
4558 PPC_MEM_TLBSYNC | PPC_TLBIVAX |
4560 pcc->msr_mask = (1ull << MSR_UCLE) |
4574 pcc->mmu_model = POWERPC_MMU_BOOKE206;
4575 pcc->excp_model = POWERPC_EXCP_BOOKE;
4576 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
4577 pcc->bfd_mach = bfd_mach_ppc_860;
4578 pcc->flags = POWERPC_FLAG_SPE | POWERPC_FLAG_CE |
4579 POWERPC_FLAG_UBLE | POWERPC_FLAG_DE |
4580 POWERPC_FLAG_BUS_CLK;
4583 static void init_proc_e300 (CPUPPCState *env)
4585 gen_spr_ne_601(env);
4589 /* hardware implementation registers */
4590 /* XXX : not implemented */
4591 spr_register(env, SPR_HID0, "HID0",
4592 SPR_NOACCESS, SPR_NOACCESS,
4593 &spr_read_generic, &spr_write_generic,
4595 /* XXX : not implemented */
4596 spr_register(env, SPR_HID1, "HID1",
4597 SPR_NOACCESS, SPR_NOACCESS,
4598 &spr_read_generic, &spr_write_generic,
4600 /* XXX : not implemented */
4601 spr_register(env, SPR_HID2, "HID2",
4602 SPR_NOACCESS, SPR_NOACCESS,
4603 &spr_read_generic, &spr_write_generic,
4606 /* XXX : not implemented */
4607 spr_register(env, SPR_DABR, "DABR",
4608 SPR_NOACCESS, SPR_NOACCESS,
4609 &spr_read_generic, &spr_write_generic,
4611 /* XXX : not implemented */
4612 spr_register(env, SPR_DABR2, "DABR2",
4613 SPR_NOACCESS, SPR_NOACCESS,
4614 &spr_read_generic, &spr_write_generic,
4616 /* XXX : not implemented */
4617 spr_register(env, SPR_IABR2, "IABR2",
4618 SPR_NOACCESS, SPR_NOACCESS,
4619 &spr_read_generic, &spr_write_generic,
4621 /* XXX : not implemented */
4622 spr_register(env, SPR_IBCR, "IBCR",
4623 SPR_NOACCESS, SPR_NOACCESS,
4624 &spr_read_generic, &spr_write_generic,
4626 /* XXX : not implemented */
4627 spr_register(env, SPR_DBCR, "DBCR",
4628 SPR_NOACCESS, SPR_NOACCESS,
4629 &spr_read_generic, &spr_write_generic,
4631 /* Memory management */
4634 gen_6xx_7xx_soft_tlb(env, 64, 2);
4636 env->dcache_line_size = 32;
4637 env->icache_line_size = 32;
4638 /* Allocate hardware IRQ controller */
4639 ppc6xx_irq_init(env);
4642 POWERPC_FAMILY(e300)(ObjectClass *oc, void *data)
4644 DeviceClass *dc = DEVICE_CLASS(oc);
4645 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4647 dc->desc = "e300 core";
4648 pcc->init_proc = init_proc_e300;
4649 pcc->check_pow = check_pow_hid0;
4650 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
4651 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
4653 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
4654 PPC_MEM_SYNC | PPC_MEM_EIEIO |
4655 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
4656 PPC_SEGMENT | PPC_EXTERN;
4657 pcc->msr_mask = (1ull << MSR_POW) |
4658 (1ull << MSR_TGPR) |
4674 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
4675 pcc->excp_model = POWERPC_EXCP_603;
4676 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
4677 pcc->bfd_mach = bfd_mach_ppc_603;
4678 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
4679 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
4682 #if !defined(CONFIG_USER_ONLY)
4683 static void spr_write_mas73(void *opaque, int sprn, int gprn)
4685 TCGv val = tcg_temp_new();
4686 tcg_gen_ext32u_tl(val, cpu_gpr[gprn]);
4687 gen_store_spr(SPR_BOOKE_MAS3, val);
4688 tcg_gen_shri_tl(val, cpu_gpr[gprn], 32);
4689 gen_store_spr(SPR_BOOKE_MAS7, val);
4693 static void spr_read_mas73(void *opaque, int gprn, int sprn)
4695 TCGv mas7 = tcg_temp_new();
4696 TCGv mas3 = tcg_temp_new();
4697 gen_load_spr(mas7, SPR_BOOKE_MAS7);
4698 tcg_gen_shli_tl(mas7, mas7, 32);
4699 gen_load_spr(mas3, SPR_BOOKE_MAS3);
4700 tcg_gen_or_tl(cpu_gpr[gprn], mas3, mas7);
4701 tcg_temp_free(mas3);
4702 tcg_temp_free(mas7);
4707 enum fsl_e500_version {
4714 static void init_proc_e500 (CPUPPCState *env, int version)
4716 PowerPCCPU *cpu = ppc_env_get_cpu(env);
4717 uint32_t tlbncfg[2];
4719 uint64_t ivpr_mask = 0xFFFF0000ULL;
4720 uint32_t l1cfg0 = 0x3800 /* 8 ways */
4721 | 0x0020; /* 32 kb */
4722 uint32_t l1cfg1 = 0x3800 /* 8 ways */
4723 | 0x0020; /* 32 kb */
4724 #if !defined(CONFIG_USER_ONLY)
4731 * XXX The e500 doesn't implement IVOR7 and IVOR9, but doesn't
4732 * complain when accessing them.
4733 * gen_spr_BookE(env, 0x0000000F0000FD7FULL);
4739 ivor_mask = 0x0000000F0000FFFFULL;
4743 ivor_mask = 0x000003FE0000FFFFULL;
4746 gen_spr_BookE(env, ivor_mask);
4747 /* Processor identification */
4748 spr_register(env, SPR_BOOKE_PIR, "PIR",
4749 SPR_NOACCESS, SPR_NOACCESS,
4750 &spr_read_generic, &spr_write_pir,
4752 /* XXX : not implemented */
4753 spr_register(env, SPR_BOOKE_SPEFSCR, "SPEFSCR",
4754 &spr_read_spefscr, &spr_write_spefscr,
4755 &spr_read_spefscr, &spr_write_spefscr,
4757 #if !defined(CONFIG_USER_ONLY)
4758 /* Memory management */
4764 tlbncfg[0] = gen_tlbncfg(2, 1, 1, 0, 256);
4765 tlbncfg[1] = gen_tlbncfg(16, 1, 9, TLBnCFG_AVAIL | TLBnCFG_IPROT, 16);
4768 tlbncfg[0] = gen_tlbncfg(4, 1, 1, 0, 512);
4769 tlbncfg[1] = gen_tlbncfg(16, 1, 12, TLBnCFG_AVAIL | TLBnCFG_IPROT, 16);
4773 tlbncfg[0] = gen_tlbncfg(4, 1, 1, 0, 512);
4774 tlbncfg[1] = gen_tlbncfg(64, 1, 12, TLBnCFG_AVAIL | TLBnCFG_IPROT, 64);
4777 cpu_abort(CPU(cpu), "Unknown CPU: " TARGET_FMT_lx "\n", env->spr[SPR_PVR]);
4784 env->dcache_line_size = 32;
4785 env->icache_line_size = 32;
4789 env->dcache_line_size = 64;
4790 env->icache_line_size = 64;
4791 l1cfg0 |= 0x1000000; /* 64 byte cache block size */
4792 l1cfg1 |= 0x1000000; /* 64 byte cache block size */
4795 cpu_abort(CPU(cpu), "Unknown CPU: " TARGET_FMT_lx "\n", env->spr[SPR_PVR]);
4797 gen_spr_BookE206(env, 0x000000DF, tlbncfg);
4798 /* XXX : not implemented */
4799 spr_register(env, SPR_HID0, "HID0",
4800 SPR_NOACCESS, SPR_NOACCESS,
4801 &spr_read_generic, &spr_write_generic,
4803 /* XXX : not implemented */
4804 spr_register(env, SPR_HID1, "HID1",
4805 SPR_NOACCESS, SPR_NOACCESS,
4806 &spr_read_generic, &spr_write_generic,
4808 /* XXX : not implemented */
4809 spr_register(env, SPR_Exxx_BBEAR, "BBEAR",
4810 SPR_NOACCESS, SPR_NOACCESS,
4811 &spr_read_generic, &spr_write_generic,
4813 /* XXX : not implemented */
4814 spr_register(env, SPR_Exxx_BBTAR, "BBTAR",
4815 SPR_NOACCESS, SPR_NOACCESS,
4816 &spr_read_generic, &spr_write_generic,
4818 /* XXX : not implemented */
4819 spr_register(env, SPR_Exxx_MCAR, "MCAR",
4820 SPR_NOACCESS, SPR_NOACCESS,
4821 &spr_read_generic, &spr_write_generic,
4823 /* XXX : not implemented */
4824 spr_register(env, SPR_BOOKE_MCSR, "MCSR",
4825 SPR_NOACCESS, SPR_NOACCESS,
4826 &spr_read_generic, &spr_write_generic,
4828 /* XXX : not implemented */
4829 spr_register(env, SPR_Exxx_NPIDR, "NPIDR",
4830 SPR_NOACCESS, SPR_NOACCESS,
4831 &spr_read_generic, &spr_write_generic,
4833 /* XXX : not implemented */
4834 spr_register(env, SPR_Exxx_BUCSR, "BUCSR",
4835 SPR_NOACCESS, SPR_NOACCESS,
4836 &spr_read_generic, &spr_write_generic,
4838 /* XXX : not implemented */
4839 spr_register(env, SPR_Exxx_L1CFG0, "L1CFG0",
4840 &spr_read_generic, SPR_NOACCESS,
4841 &spr_read_generic, SPR_NOACCESS,
4843 spr_register(env, SPR_Exxx_L1CFG1, "L1CFG1",
4844 &spr_read_generic, SPR_NOACCESS,
4845 &spr_read_generic, SPR_NOACCESS,
4847 spr_register(env, SPR_Exxx_L1CSR0, "L1CSR0",
4848 SPR_NOACCESS, SPR_NOACCESS,
4849 &spr_read_generic, &spr_write_e500_l1csr0,
4851 spr_register(env, SPR_Exxx_L1CSR1, "L1CSR1",
4852 SPR_NOACCESS, SPR_NOACCESS,
4853 &spr_read_generic, &spr_write_e500_l1csr1,
4855 spr_register(env, SPR_BOOKE_MCSRR0, "MCSRR0",
4856 SPR_NOACCESS, SPR_NOACCESS,
4857 &spr_read_generic, &spr_write_generic,
4859 spr_register(env, SPR_BOOKE_MCSRR1, "MCSRR1",
4860 SPR_NOACCESS, SPR_NOACCESS,
4861 &spr_read_generic, &spr_write_generic,
4863 spr_register(env, SPR_MMUCSR0, "MMUCSR0",
4864 SPR_NOACCESS, SPR_NOACCESS,
4865 &spr_read_generic, &spr_write_booke206_mmucsr0,
4867 spr_register(env, SPR_BOOKE_EPR, "EPR",
4868 SPR_NOACCESS, SPR_NOACCESS,
4869 &spr_read_generic, SPR_NOACCESS,
4871 /* XXX better abstract into Emb.xxx features */
4872 if (version == fsl_e5500) {
4873 spr_register(env, SPR_BOOKE_EPCR, "EPCR",
4874 SPR_NOACCESS, SPR_NOACCESS,
4875 &spr_read_generic, &spr_write_generic,
4877 spr_register(env, SPR_BOOKE_MAS7_MAS3, "MAS7_MAS3",
4878 SPR_NOACCESS, SPR_NOACCESS,
4879 &spr_read_mas73, &spr_write_mas73,
4881 ivpr_mask = (target_ulong)~0xFFFFULL;
4884 #if !defined(CONFIG_USER_ONLY)
4886 env->tlb_type = TLB_MAS;
4887 for (i = 0; i < BOOKE206_MAX_TLBN; i++) {
4888 env->nb_tlb += booke206_tlb_size(env, i);
4892 init_excp_e200(env, ivpr_mask);
4893 /* Allocate hardware IRQ controller */
4894 ppce500_irq_init(env);
4897 static void init_proc_e500v1(CPUPPCState *env)
4899 init_proc_e500(env, fsl_e500v1);
4902 POWERPC_FAMILY(e500v1)(ObjectClass *oc, void *data)
4904 DeviceClass *dc = DEVICE_CLASS(oc);
4905 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4907 dc->desc = "e500v1 core";
4908 pcc->init_proc = init_proc_e500v1;
4909 pcc->check_pow = check_pow_hid0;
4910 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL |
4911 PPC_SPE | PPC_SPE_SINGLE |
4912 PPC_WRTEE | PPC_RFDI |
4913 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
4914 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
4915 PPC_MEM_TLBSYNC | PPC_TLBIVAX | PPC_MEM_SYNC;
4916 pcc->insns_flags2 = PPC2_BOOKE206;
4917 pcc->msr_mask = (1ull << MSR_UCLE) |
4931 pcc->mmu_model = POWERPC_MMU_BOOKE206;
4932 pcc->excp_model = POWERPC_EXCP_BOOKE;
4933 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
4934 pcc->bfd_mach = bfd_mach_ppc_860;
4935 pcc->flags = POWERPC_FLAG_SPE | POWERPC_FLAG_CE |
4936 POWERPC_FLAG_UBLE | POWERPC_FLAG_DE |
4937 POWERPC_FLAG_BUS_CLK;
4940 static void init_proc_e500v2(CPUPPCState *env)
4942 init_proc_e500(env, fsl_e500v2);
4945 POWERPC_FAMILY(e500v2)(ObjectClass *oc, void *data)
4947 DeviceClass *dc = DEVICE_CLASS(oc);
4948 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4950 dc->desc = "e500v2 core";
4951 pcc->init_proc = init_proc_e500v2;
4952 pcc->check_pow = check_pow_hid0;
4953 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL |
4954 PPC_SPE | PPC_SPE_SINGLE | PPC_SPE_DOUBLE |
4955 PPC_WRTEE | PPC_RFDI |
4956 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
4957 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
4958 PPC_MEM_TLBSYNC | PPC_TLBIVAX | PPC_MEM_SYNC;
4959 pcc->insns_flags2 = PPC2_BOOKE206;
4960 pcc->msr_mask = (1ull << MSR_UCLE) |
4974 pcc->mmu_model = POWERPC_MMU_BOOKE206;
4975 pcc->excp_model = POWERPC_EXCP_BOOKE;
4976 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
4977 pcc->bfd_mach = bfd_mach_ppc_860;
4978 pcc->flags = POWERPC_FLAG_SPE | POWERPC_FLAG_CE |
4979 POWERPC_FLAG_UBLE | POWERPC_FLAG_DE |
4980 POWERPC_FLAG_BUS_CLK;
4983 static void init_proc_e500mc(CPUPPCState *env)
4985 init_proc_e500(env, fsl_e500mc);
4988 POWERPC_FAMILY(e500mc)(ObjectClass *oc, void *data)
4990 DeviceClass *dc = DEVICE_CLASS(oc);
4991 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4993 dc->desc = "e500mc core";
4994 pcc->init_proc = init_proc_e500mc;
4995 pcc->check_pow = check_pow_none;
4996 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL |
4997 PPC_WRTEE | PPC_RFDI | PPC_RFMCI |
4998 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
4999 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
5000 PPC_FLOAT | PPC_FLOAT_FRES |
5001 PPC_FLOAT_FRSQRTE | PPC_FLOAT_FSEL |
5002 PPC_FLOAT_STFIWX | PPC_WAIT |
5003 PPC_MEM_TLBSYNC | PPC_TLBIVAX | PPC_MEM_SYNC;
5004 pcc->insns_flags2 = PPC2_BOOKE206 | PPC2_PRCNTL;
5005 pcc->msr_mask = (1ull << MSR_GS) |
5006 (1ull << MSR_UCLE) |
5019 pcc->mmu_model = POWERPC_MMU_BOOKE206;
5020 pcc->excp_model = POWERPC_EXCP_BOOKE;
5021 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
5022 /* FIXME: figure out the correct flag for e500mc */
5023 pcc->bfd_mach = bfd_mach_ppc_e500;
5024 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
5025 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5029 static void init_proc_e5500(CPUPPCState *env)
5031 init_proc_e500(env, fsl_e5500);
5034 POWERPC_FAMILY(e5500)(ObjectClass *oc, void *data)
5036 DeviceClass *dc = DEVICE_CLASS(oc);
5037 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5039 dc->desc = "e5500 core";
5040 pcc->init_proc = init_proc_e5500;
5041 pcc->check_pow = check_pow_none;
5042 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL |
5043 PPC_WRTEE | PPC_RFDI | PPC_RFMCI |
5044 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
5045 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
5046 PPC_FLOAT | PPC_FLOAT_FRES |
5047 PPC_FLOAT_FRSQRTE | PPC_FLOAT_FSEL |
5048 PPC_FLOAT_STFIWX | PPC_WAIT |
5049 PPC_MEM_TLBSYNC | PPC_TLBIVAX | PPC_MEM_SYNC |
5050 PPC_64B | PPC_POPCNTB | PPC_POPCNTWD;
5051 pcc->insns_flags2 = PPC2_BOOKE206 | PPC2_PRCNTL | PPC2_PERM_ISA206 | \
5053 pcc->msr_mask = (1ull << MSR_CM) |
5055 (1ull << MSR_UCLE) |
5068 pcc->mmu_model = POWERPC_MMU_BOOKE206;
5069 pcc->excp_model = POWERPC_EXCP_BOOKE;
5070 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
5071 /* FIXME: figure out the correct flag for e5500 */
5072 pcc->bfd_mach = bfd_mach_ppc_e500;
5073 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
5074 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5078 /* Non-embedded PowerPC */
5080 /* POWER : same as 601, without mfmsr, mfsr */
5081 POWERPC_FAMILY(POWER)(ObjectClass *oc, void *data)
5083 DeviceClass *dc = DEVICE_CLASS(oc);
5084 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5087 /* pcc->insns_flags = XXX_TODO; */
5088 /* POWER RSC (from RAD6000) */
5089 pcc->msr_mask = (1ull << MSR_EE) |
5102 #define POWERPC_MSRR_601 (0x0000000000001040ULL)
5104 static void init_proc_601 (CPUPPCState *env)
5106 gen_spr_ne_601(env);
5108 /* Hardware implementation registers */
5109 /* XXX : not implemented */
5110 spr_register(env, SPR_HID0, "HID0",
5111 SPR_NOACCESS, SPR_NOACCESS,
5112 &spr_read_generic, &spr_write_hid0_601,
5114 /* XXX : not implemented */
5115 spr_register(env, SPR_HID1, "HID1",
5116 SPR_NOACCESS, SPR_NOACCESS,
5117 &spr_read_generic, &spr_write_generic,
5119 /* XXX : not implemented */
5120 spr_register(env, SPR_601_HID2, "HID2",
5121 SPR_NOACCESS, SPR_NOACCESS,
5122 &spr_read_generic, &spr_write_generic,
5124 /* XXX : not implemented */
5125 spr_register(env, SPR_601_HID5, "HID5",
5126 SPR_NOACCESS, SPR_NOACCESS,
5127 &spr_read_generic, &spr_write_generic,
5129 /* Memory management */
5131 /* XXX: beware that dcache line size is 64
5132 * but dcbz uses 32 bytes "sectors"
5133 * XXX: this breaks clcs instruction !
5135 env->dcache_line_size = 32;
5136 env->icache_line_size = 64;
5137 /* Allocate hardware IRQ controller */
5138 ppc6xx_irq_init(env);
5141 POWERPC_FAMILY(601)(ObjectClass *oc, void *data)
5143 DeviceClass *dc = DEVICE_CLASS(oc);
5144 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5146 dc->desc = "PowerPC 601";
5147 pcc->init_proc = init_proc_601;
5148 pcc->check_pow = check_pow_none;
5149 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_POWER_BR |
5151 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5152 PPC_MEM_SYNC | PPC_MEM_EIEIO | PPC_MEM_TLBIE |
5153 PPC_SEGMENT | PPC_EXTERN;
5154 pcc->msr_mask = (1ull << MSR_EE) |
5164 pcc->mmu_model = POWERPC_MMU_601;
5165 #if defined(CONFIG_SOFTMMU)
5166 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5168 pcc->excp_model = POWERPC_EXCP_601;
5169 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5170 pcc->bfd_mach = bfd_mach_ppc_601;
5171 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_RTC_CLK;
5174 #define POWERPC_MSRR_601v (0x0000000000001040ULL)
5176 static void init_proc_601v (CPUPPCState *env)
5179 /* XXX : not implemented */
5180 spr_register(env, SPR_601_HID15, "HID15",
5181 SPR_NOACCESS, SPR_NOACCESS,
5182 &spr_read_generic, &spr_write_generic,
5186 POWERPC_FAMILY(601v)(ObjectClass *oc, void *data)
5188 DeviceClass *dc = DEVICE_CLASS(oc);
5189 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5191 dc->desc = "PowerPC 601v";
5192 pcc->init_proc = init_proc_601v;
5193 pcc->check_pow = check_pow_none;
5194 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_POWER_BR |
5196 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5197 PPC_MEM_SYNC | PPC_MEM_EIEIO | PPC_MEM_TLBIE |
5198 PPC_SEGMENT | PPC_EXTERN;
5199 pcc->msr_mask = (1ull << MSR_EE) |
5209 pcc->mmu_model = POWERPC_MMU_601;
5210 #if defined(CONFIG_SOFTMMU)
5211 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5213 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5214 pcc->bfd_mach = bfd_mach_ppc_601;
5215 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_RTC_CLK;
5218 static void init_proc_602 (CPUPPCState *env)
5220 gen_spr_ne_601(env);
5224 /* hardware implementation registers */
5225 /* XXX : not implemented */
5226 spr_register(env, SPR_HID0, "HID0",
5227 SPR_NOACCESS, SPR_NOACCESS,
5228 &spr_read_generic, &spr_write_generic,
5230 /* XXX : not implemented */
5231 spr_register(env, SPR_HID1, "HID1",
5232 SPR_NOACCESS, SPR_NOACCESS,
5233 &spr_read_generic, &spr_write_generic,
5235 /* Memory management */
5237 gen_6xx_7xx_soft_tlb(env, 64, 2);
5239 env->dcache_line_size = 32;
5240 env->icache_line_size = 32;
5241 /* Allocate hardware IRQ controller */
5242 ppc6xx_irq_init(env);
5245 POWERPC_FAMILY(602)(ObjectClass *oc, void *data)
5247 DeviceClass *dc = DEVICE_CLASS(oc);
5248 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5250 dc->desc = "PowerPC 602";
5251 pcc->init_proc = init_proc_602;
5252 pcc->check_pow = check_pow_hid0;
5253 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5254 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5255 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5256 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5257 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5258 PPC_MEM_TLBIE | PPC_6xx_TLB | PPC_MEM_TLBSYNC |
5259 PPC_SEGMENT | PPC_602_SPEC;
5260 pcc->msr_mask = (1ull << MSR_VSX) |
5263 (1ull << MSR_TGPR) |
5278 /* XXX: 602 MMU is quite specific. Should add a special case */
5279 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
5280 pcc->excp_model = POWERPC_EXCP_602;
5281 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5282 pcc->bfd_mach = bfd_mach_ppc_602;
5283 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
5284 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
5287 static void init_proc_603 (CPUPPCState *env)
5289 gen_spr_ne_601(env);
5293 /* hardware implementation registers */
5294 /* XXX : not implemented */
5295 spr_register(env, SPR_HID0, "HID0",
5296 SPR_NOACCESS, SPR_NOACCESS,
5297 &spr_read_generic, &spr_write_generic,
5299 /* XXX : not implemented */
5300 spr_register(env, SPR_HID1, "HID1",
5301 SPR_NOACCESS, SPR_NOACCESS,
5302 &spr_read_generic, &spr_write_generic,
5304 /* Memory management */
5306 gen_6xx_7xx_soft_tlb(env, 64, 2);
5308 env->dcache_line_size = 32;
5309 env->icache_line_size = 32;
5310 /* Allocate hardware IRQ controller */
5311 ppc6xx_irq_init(env);
5314 POWERPC_FAMILY(603)(ObjectClass *oc, void *data)
5316 DeviceClass *dc = DEVICE_CLASS(oc);
5317 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5319 dc->desc = "PowerPC 603";
5320 pcc->init_proc = init_proc_603;
5321 pcc->check_pow = check_pow_hid0;
5322 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5323 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5324 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5325 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5326 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5327 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
5328 PPC_SEGMENT | PPC_EXTERN;
5329 pcc->msr_mask = (1ull << MSR_POW) |
5330 (1ull << MSR_TGPR) |
5345 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
5346 pcc->excp_model = POWERPC_EXCP_603;
5347 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5348 pcc->bfd_mach = bfd_mach_ppc_603;
5349 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
5350 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
5353 static void init_proc_603E (CPUPPCState *env)
5355 gen_spr_ne_601(env);
5359 /* hardware implementation registers */
5360 /* XXX : not implemented */
5361 spr_register(env, SPR_HID0, "HID0",
5362 SPR_NOACCESS, SPR_NOACCESS,
5363 &spr_read_generic, &spr_write_generic,
5365 /* XXX : not implemented */
5366 spr_register(env, SPR_HID1, "HID1",
5367 SPR_NOACCESS, SPR_NOACCESS,
5368 &spr_read_generic, &spr_write_generic,
5370 /* Memory management */
5372 gen_6xx_7xx_soft_tlb(env, 64, 2);
5374 env->dcache_line_size = 32;
5375 env->icache_line_size = 32;
5376 /* Allocate hardware IRQ controller */
5377 ppc6xx_irq_init(env);
5380 POWERPC_FAMILY(603E)(ObjectClass *oc, void *data)
5382 DeviceClass *dc = DEVICE_CLASS(oc);
5383 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5385 dc->desc = "PowerPC 603e";
5386 pcc->init_proc = init_proc_603E;
5387 pcc->check_pow = check_pow_hid0;
5388 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5389 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5390 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5391 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5392 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5393 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
5394 PPC_SEGMENT | PPC_EXTERN;
5395 pcc->msr_mask = (1ull << MSR_POW) |
5396 (1ull << MSR_TGPR) |
5411 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
5412 pcc->excp_model = POWERPC_EXCP_603E;
5413 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5414 pcc->bfd_mach = bfd_mach_ppc_ec603e;
5415 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
5416 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
5419 static void init_proc_604 (CPUPPCState *env)
5421 gen_spr_ne_601(env);
5425 /* Hardware implementation registers */
5426 /* XXX : not implemented */
5427 spr_register(env, SPR_HID0, "HID0",
5428 SPR_NOACCESS, SPR_NOACCESS,
5429 &spr_read_generic, &spr_write_generic,
5431 /* Memory management */
5434 env->dcache_line_size = 32;
5435 env->icache_line_size = 32;
5436 /* Allocate hardware IRQ controller */
5437 ppc6xx_irq_init(env);
5440 POWERPC_FAMILY(604)(ObjectClass *oc, void *data)
5442 DeviceClass *dc = DEVICE_CLASS(oc);
5443 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5445 dc->desc = "PowerPC 604";
5446 pcc->init_proc = init_proc_604;
5447 pcc->check_pow = check_pow_nocheck;
5448 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5449 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5450 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5451 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5452 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5453 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5454 PPC_SEGMENT | PPC_EXTERN;
5455 pcc->msr_mask = (1ull << MSR_POW) |
5471 pcc->mmu_model = POWERPC_MMU_32B;
5472 #if defined(CONFIG_SOFTMMU)
5473 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5475 pcc->excp_model = POWERPC_EXCP_604;
5476 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5477 pcc->bfd_mach = bfd_mach_ppc_604;
5478 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
5479 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5482 static void init_proc_604E (CPUPPCState *env)
5484 gen_spr_ne_601(env);
5486 /* XXX : not implemented */
5487 spr_register(env, SPR_7XX_MMCR1, "MMCR1",
5488 SPR_NOACCESS, SPR_NOACCESS,
5489 &spr_read_generic, &spr_write_generic,
5491 /* XXX : not implemented */
5492 spr_register(env, SPR_7XX_PMC3, "PMC3",
5493 SPR_NOACCESS, SPR_NOACCESS,
5494 &spr_read_generic, &spr_write_generic,
5496 /* XXX : not implemented */
5497 spr_register(env, SPR_7XX_PMC4, "PMC4",
5498 SPR_NOACCESS, SPR_NOACCESS,
5499 &spr_read_generic, &spr_write_generic,
5503 /* Hardware implementation registers */
5504 /* XXX : not implemented */
5505 spr_register(env, SPR_HID0, "HID0",
5506 SPR_NOACCESS, SPR_NOACCESS,
5507 &spr_read_generic, &spr_write_generic,
5509 /* XXX : not implemented */
5510 spr_register(env, SPR_HID1, "HID1",
5511 SPR_NOACCESS, SPR_NOACCESS,
5512 &spr_read_generic, &spr_write_generic,
5514 /* Memory management */
5517 env->dcache_line_size = 32;
5518 env->icache_line_size = 32;
5519 /* Allocate hardware IRQ controller */
5520 ppc6xx_irq_init(env);
5523 POWERPC_FAMILY(604E)(ObjectClass *oc, void *data)
5525 DeviceClass *dc = DEVICE_CLASS(oc);
5526 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5528 dc->desc = "PowerPC 604E";
5529 pcc->init_proc = init_proc_604E;
5530 pcc->check_pow = check_pow_nocheck;
5531 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5532 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5533 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5534 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5535 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5536 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5537 PPC_SEGMENT | PPC_EXTERN;
5538 pcc->msr_mask = (1ull << MSR_POW) |
5554 pcc->mmu_model = POWERPC_MMU_32B;
5555 #if defined(CONFIG_SOFTMMU)
5556 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5558 pcc->excp_model = POWERPC_EXCP_604;
5559 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5560 pcc->bfd_mach = bfd_mach_ppc_604;
5561 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
5562 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5565 static void init_proc_740 (CPUPPCState *env)
5567 gen_spr_ne_601(env);
5571 /* Thermal management */
5573 /* Hardware implementation registers */
5574 /* XXX : not implemented */
5575 spr_register(env, SPR_HID0, "HID0",
5576 SPR_NOACCESS, SPR_NOACCESS,
5577 &spr_read_generic, &spr_write_generic,
5579 /* XXX : not implemented */
5580 spr_register(env, SPR_HID1, "HID1",
5581 SPR_NOACCESS, SPR_NOACCESS,
5582 &spr_read_generic, &spr_write_generic,
5584 /* Memory management */
5587 env->dcache_line_size = 32;
5588 env->icache_line_size = 32;
5589 /* Allocate hardware IRQ controller */
5590 ppc6xx_irq_init(env);
5593 POWERPC_FAMILY(740)(ObjectClass *oc, void *data)
5595 DeviceClass *dc = DEVICE_CLASS(oc);
5596 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5598 dc->desc = "PowerPC 740";
5599 pcc->init_proc = init_proc_740;
5600 pcc->check_pow = check_pow_hid0;
5601 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5602 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5603 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5604 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5605 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5606 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5607 PPC_SEGMENT | PPC_EXTERN;
5608 pcc->msr_mask = (1ull << MSR_POW) |
5624 pcc->mmu_model = POWERPC_MMU_32B;
5625 #if defined(CONFIG_SOFTMMU)
5626 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5628 pcc->excp_model = POWERPC_EXCP_7x0;
5629 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5630 pcc->bfd_mach = bfd_mach_ppc_750;
5631 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
5632 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5635 static void init_proc_750 (CPUPPCState *env)
5637 gen_spr_ne_601(env);
5639 /* XXX : not implemented */
5640 spr_register(env, SPR_L2CR, "L2CR",
5641 SPR_NOACCESS, SPR_NOACCESS,
5642 &spr_read_generic, spr_access_nop,
5646 /* Thermal management */
5648 /* Hardware implementation registers */
5649 /* XXX : not implemented */
5650 spr_register(env, SPR_HID0, "HID0",
5651 SPR_NOACCESS, SPR_NOACCESS,
5652 &spr_read_generic, &spr_write_generic,
5654 /* XXX : not implemented */
5655 spr_register(env, SPR_HID1, "HID1",
5656 SPR_NOACCESS, SPR_NOACCESS,
5657 &spr_read_generic, &spr_write_generic,
5659 /* Memory management */
5661 /* XXX: high BATs are also present but are known to be bugged on
5665 env->dcache_line_size = 32;
5666 env->icache_line_size = 32;
5667 /* Allocate hardware IRQ controller */
5668 ppc6xx_irq_init(env);
5671 POWERPC_FAMILY(750)(ObjectClass *oc, void *data)
5673 DeviceClass *dc = DEVICE_CLASS(oc);
5674 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5676 dc->desc = "PowerPC 750";
5677 pcc->init_proc = init_proc_750;
5678 pcc->check_pow = check_pow_hid0;
5679 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5680 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5681 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5682 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5683 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5684 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5685 PPC_SEGMENT | PPC_EXTERN;
5686 pcc->msr_mask = (1ull << MSR_POW) |
5702 pcc->mmu_model = POWERPC_MMU_32B;
5703 #if defined(CONFIG_SOFTMMU)
5704 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5706 pcc->excp_model = POWERPC_EXCP_7x0;
5707 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5708 pcc->bfd_mach = bfd_mach_ppc_750;
5709 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
5710 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5713 static void init_proc_750cl (CPUPPCState *env)
5715 gen_spr_ne_601(env);
5717 /* XXX : not implemented */
5718 spr_register(env, SPR_L2CR, "L2CR",
5719 SPR_NOACCESS, SPR_NOACCESS,
5720 &spr_read_generic, spr_access_nop,
5724 /* Thermal management */
5725 /* Those registers are fake on 750CL */
5726 spr_register(env, SPR_THRM1, "THRM1",
5727 SPR_NOACCESS, SPR_NOACCESS,
5728 &spr_read_generic, &spr_write_generic,
5730 spr_register(env, SPR_THRM2, "THRM2",
5731 SPR_NOACCESS, SPR_NOACCESS,
5732 &spr_read_generic, &spr_write_generic,
5734 spr_register(env, SPR_THRM3, "THRM3",
5735 SPR_NOACCESS, SPR_NOACCESS,
5736 &spr_read_generic, &spr_write_generic,
5738 /* XXX: not implemented */
5739 spr_register(env, SPR_750_TDCL, "TDCL",
5740 SPR_NOACCESS, SPR_NOACCESS,
5741 &spr_read_generic, &spr_write_generic,
5743 spr_register(env, SPR_750_TDCH, "TDCH",
5744 SPR_NOACCESS, SPR_NOACCESS,
5745 &spr_read_generic, &spr_write_generic,
5748 /* XXX : not implemented */
5749 spr_register(env, SPR_750_WPAR, "WPAR",
5750 SPR_NOACCESS, SPR_NOACCESS,
5751 &spr_read_generic, &spr_write_generic,
5753 spr_register(env, SPR_750_DMAL, "DMAL",
5754 SPR_NOACCESS, SPR_NOACCESS,
5755 &spr_read_generic, &spr_write_generic,
5757 spr_register(env, SPR_750_DMAU, "DMAU",
5758 SPR_NOACCESS, SPR_NOACCESS,
5759 &spr_read_generic, &spr_write_generic,
5761 /* Hardware implementation registers */
5762 /* XXX : not implemented */
5763 spr_register(env, SPR_HID0, "HID0",
5764 SPR_NOACCESS, SPR_NOACCESS,
5765 &spr_read_generic, &spr_write_generic,
5767 /* XXX : not implemented */
5768 spr_register(env, SPR_HID1, "HID1",
5769 SPR_NOACCESS, SPR_NOACCESS,
5770 &spr_read_generic, &spr_write_generic,
5772 /* XXX : not implemented */
5773 spr_register(env, SPR_750CL_HID2, "HID2",
5774 SPR_NOACCESS, SPR_NOACCESS,
5775 &spr_read_generic, &spr_write_generic,
5777 /* XXX : not implemented */
5778 spr_register(env, SPR_750CL_HID4, "HID4",
5779 SPR_NOACCESS, SPR_NOACCESS,
5780 &spr_read_generic, &spr_write_generic,
5782 /* Quantization registers */
5783 /* XXX : not implemented */
5784 spr_register(env, SPR_750_GQR0, "GQR0",
5785 SPR_NOACCESS, SPR_NOACCESS,
5786 &spr_read_generic, &spr_write_generic,
5788 /* XXX : not implemented */
5789 spr_register(env, SPR_750_GQR1, "GQR1",
5790 SPR_NOACCESS, SPR_NOACCESS,
5791 &spr_read_generic, &spr_write_generic,
5793 /* XXX : not implemented */
5794 spr_register(env, SPR_750_GQR2, "GQR2",
5795 SPR_NOACCESS, SPR_NOACCESS,
5796 &spr_read_generic, &spr_write_generic,
5798 /* XXX : not implemented */
5799 spr_register(env, SPR_750_GQR3, "GQR3",
5800 SPR_NOACCESS, SPR_NOACCESS,
5801 &spr_read_generic, &spr_write_generic,
5803 /* XXX : not implemented */
5804 spr_register(env, SPR_750_GQR4, "GQR4",
5805 SPR_NOACCESS, SPR_NOACCESS,
5806 &spr_read_generic, &spr_write_generic,
5808 /* XXX : not implemented */
5809 spr_register(env, SPR_750_GQR5, "GQR5",
5810 SPR_NOACCESS, SPR_NOACCESS,
5811 &spr_read_generic, &spr_write_generic,
5813 /* XXX : not implemented */
5814 spr_register(env, SPR_750_GQR6, "GQR6",
5815 SPR_NOACCESS, SPR_NOACCESS,
5816 &spr_read_generic, &spr_write_generic,
5818 /* XXX : not implemented */
5819 spr_register(env, SPR_750_GQR7, "GQR7",
5820 SPR_NOACCESS, SPR_NOACCESS,
5821 &spr_read_generic, &spr_write_generic,
5823 /* Memory management */
5825 /* PowerPC 750cl has 8 DBATs and 8 IBATs */
5827 init_excp_750cl(env);
5828 env->dcache_line_size = 32;
5829 env->icache_line_size = 32;
5830 /* Allocate hardware IRQ controller */
5831 ppc6xx_irq_init(env);
5834 POWERPC_FAMILY(750cl)(ObjectClass *oc, void *data)
5836 DeviceClass *dc = DEVICE_CLASS(oc);
5837 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5839 dc->desc = "PowerPC 750 CL";
5840 pcc->init_proc = init_proc_750cl;
5841 pcc->check_pow = check_pow_hid0;
5842 /* XXX: not implemented:
5843 * cache lock instructions:
5845 * floating point paired instructions
5880 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5881 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5882 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5883 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5884 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5885 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5886 PPC_SEGMENT | PPC_EXTERN;
5887 pcc->msr_mask = (1ull << MSR_POW) |
5903 pcc->mmu_model = POWERPC_MMU_32B;
5904 #if defined(CONFIG_SOFTMMU)
5905 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5907 pcc->excp_model = POWERPC_EXCP_7x0;
5908 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5909 pcc->bfd_mach = bfd_mach_ppc_750;
5910 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
5911 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5914 static void init_proc_750cx (CPUPPCState *env)
5916 gen_spr_ne_601(env);
5918 /* XXX : not implemented */
5919 spr_register(env, SPR_L2CR, "L2CR",
5920 SPR_NOACCESS, SPR_NOACCESS,
5921 &spr_read_generic, spr_access_nop,
5925 /* Thermal management */
5927 /* This register is not implemented but is present for compatibility */
5928 spr_register(env, SPR_SDA, "SDA",
5929 SPR_NOACCESS, SPR_NOACCESS,
5930 &spr_read_generic, &spr_write_generic,
5932 /* Hardware implementation registers */
5933 /* XXX : not implemented */
5934 spr_register(env, SPR_HID0, "HID0",
5935 SPR_NOACCESS, SPR_NOACCESS,
5936 &spr_read_generic, &spr_write_generic,
5938 /* XXX : not implemented */
5939 spr_register(env, SPR_HID1, "HID1",
5940 SPR_NOACCESS, SPR_NOACCESS,
5941 &spr_read_generic, &spr_write_generic,
5943 /* Memory management */
5945 /* PowerPC 750cx has 8 DBATs and 8 IBATs */
5947 init_excp_750cx(env);
5948 env->dcache_line_size = 32;
5949 env->icache_line_size = 32;
5950 /* Allocate hardware IRQ controller */
5951 ppc6xx_irq_init(env);
5954 POWERPC_FAMILY(750cx)(ObjectClass *oc, void *data)
5956 DeviceClass *dc = DEVICE_CLASS(oc);
5957 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5959 dc->desc = "PowerPC 750CX";
5960 pcc->init_proc = init_proc_750cx;
5961 pcc->check_pow = check_pow_hid0;
5962 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5963 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5964 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5965 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5966 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5967 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5968 PPC_SEGMENT | PPC_EXTERN;
5969 pcc->msr_mask = (1ull << MSR_POW) |
5985 pcc->mmu_model = POWERPC_MMU_32B;
5986 #if defined(CONFIG_SOFTMMU)
5987 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5989 pcc->excp_model = POWERPC_EXCP_7x0;
5990 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5991 pcc->bfd_mach = bfd_mach_ppc_750;
5992 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
5993 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5996 static void init_proc_750fx (CPUPPCState *env)
5998 gen_spr_ne_601(env);
6000 /* XXX : not implemented */
6001 spr_register(env, SPR_L2CR, "L2CR",
6002 SPR_NOACCESS, SPR_NOACCESS,
6003 &spr_read_generic, spr_access_nop,
6007 /* Thermal management */
6009 /* XXX : not implemented */
6010 spr_register(env, SPR_750_THRM4, "THRM4",
6011 SPR_NOACCESS, SPR_NOACCESS,
6012 &spr_read_generic, &spr_write_generic,
6014 /* Hardware implementation registers */
6015 /* XXX : not implemented */
6016 spr_register(env, SPR_HID0, "HID0",
6017 SPR_NOACCESS, SPR_NOACCESS,
6018 &spr_read_generic, &spr_write_generic,
6020 /* XXX : not implemented */
6021 spr_register(env, SPR_HID1, "HID1",
6022 SPR_NOACCESS, SPR_NOACCESS,
6023 &spr_read_generic, &spr_write_generic,
6025 /* XXX : not implemented */
6026 spr_register(env, SPR_750FX_HID2, "HID2",
6027 SPR_NOACCESS, SPR_NOACCESS,
6028 &spr_read_generic, &spr_write_generic,
6030 /* Memory management */
6032 /* PowerPC 750fx & 750gx has 8 DBATs and 8 IBATs */
6035 env->dcache_line_size = 32;
6036 env->icache_line_size = 32;
6037 /* Allocate hardware IRQ controller */
6038 ppc6xx_irq_init(env);
6041 POWERPC_FAMILY(750fx)(ObjectClass *oc, void *data)
6043 DeviceClass *dc = DEVICE_CLASS(oc);
6044 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6046 dc->desc = "PowerPC 750FX";
6047 pcc->init_proc = init_proc_750fx;
6048 pcc->check_pow = check_pow_hid0;
6049 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6050 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6051 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
6052 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
6053 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6054 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6055 PPC_SEGMENT | PPC_EXTERN;
6056 pcc->msr_mask = (1ull << MSR_POW) |
6072 pcc->mmu_model = POWERPC_MMU_32B;
6073 #if defined(CONFIG_SOFTMMU)
6074 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
6076 pcc->excp_model = POWERPC_EXCP_7x0;
6077 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6078 pcc->bfd_mach = bfd_mach_ppc_750;
6079 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
6080 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
6083 static void init_proc_750gx (CPUPPCState *env)
6085 gen_spr_ne_601(env);
6087 /* XXX : not implemented (XXX: different from 750fx) */
6088 spr_register(env, SPR_L2CR, "L2CR",
6089 SPR_NOACCESS, SPR_NOACCESS,
6090 &spr_read_generic, spr_access_nop,
6094 /* Thermal management */
6096 /* XXX : not implemented */
6097 spr_register(env, SPR_750_THRM4, "THRM4",
6098 SPR_NOACCESS, SPR_NOACCESS,
6099 &spr_read_generic, &spr_write_generic,
6101 /* Hardware implementation registers */
6102 /* XXX : not implemented (XXX: different from 750fx) */
6103 spr_register(env, SPR_HID0, "HID0",
6104 SPR_NOACCESS, SPR_NOACCESS,
6105 &spr_read_generic, &spr_write_generic,
6107 /* XXX : not implemented */
6108 spr_register(env, SPR_HID1, "HID1",
6109 SPR_NOACCESS, SPR_NOACCESS,
6110 &spr_read_generic, &spr_write_generic,
6112 /* XXX : not implemented (XXX: different from 750fx) */
6113 spr_register(env, SPR_750FX_HID2, "HID2",
6114 SPR_NOACCESS, SPR_NOACCESS,
6115 &spr_read_generic, &spr_write_generic,
6117 /* Memory management */
6119 /* PowerPC 750fx & 750gx has 8 DBATs and 8 IBATs */
6122 env->dcache_line_size = 32;
6123 env->icache_line_size = 32;
6124 /* Allocate hardware IRQ controller */
6125 ppc6xx_irq_init(env);
6128 POWERPC_FAMILY(750gx)(ObjectClass *oc, void *data)
6130 DeviceClass *dc = DEVICE_CLASS(oc);
6131 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6133 dc->desc = "PowerPC 750GX";
6134 pcc->init_proc = init_proc_750gx;
6135 pcc->check_pow = check_pow_hid0;
6136 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6137 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6138 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
6139 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
6140 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6141 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6142 PPC_SEGMENT | PPC_EXTERN;
6143 pcc->msr_mask = (1ull << MSR_POW) |
6159 pcc->mmu_model = POWERPC_MMU_32B;
6160 #if defined(CONFIG_SOFTMMU)
6161 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
6163 pcc->excp_model = POWERPC_EXCP_7x0;
6164 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6165 pcc->bfd_mach = bfd_mach_ppc_750;
6166 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
6167 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
6170 static void init_proc_745 (CPUPPCState *env)
6172 gen_spr_ne_601(env);
6174 gen_spr_G2_755(env);
6177 /* Thermal management */
6179 /* Hardware implementation registers */
6180 /* XXX : not implemented */
6181 spr_register(env, SPR_HID0, "HID0",
6182 SPR_NOACCESS, SPR_NOACCESS,
6183 &spr_read_generic, &spr_write_generic,
6185 /* XXX : not implemented */
6186 spr_register(env, SPR_HID1, "HID1",
6187 SPR_NOACCESS, SPR_NOACCESS,
6188 &spr_read_generic, &spr_write_generic,
6190 /* XXX : not implemented */
6191 spr_register(env, SPR_HID2, "HID2",
6192 SPR_NOACCESS, SPR_NOACCESS,
6193 &spr_read_generic, &spr_write_generic,
6195 /* Memory management */
6198 gen_6xx_7xx_soft_tlb(env, 64, 2);
6200 env->dcache_line_size = 32;
6201 env->icache_line_size = 32;
6202 /* Allocate hardware IRQ controller */
6203 ppc6xx_irq_init(env);
6206 POWERPC_FAMILY(745)(ObjectClass *oc, void *data)
6208 DeviceClass *dc = DEVICE_CLASS(oc);
6209 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6211 dc->desc = "PowerPC 745";
6212 pcc->init_proc = init_proc_745;
6213 pcc->check_pow = check_pow_hid0;
6214 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6215 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6216 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
6217 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
6218 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6219 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
6220 PPC_SEGMENT | PPC_EXTERN;
6221 pcc->msr_mask = (1ull << MSR_POW) |
6237 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
6238 pcc->excp_model = POWERPC_EXCP_7x5;
6239 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6240 pcc->bfd_mach = bfd_mach_ppc_750;
6241 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
6242 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
6245 static void init_proc_755 (CPUPPCState *env)
6247 gen_spr_ne_601(env);
6249 gen_spr_G2_755(env);
6252 /* L2 cache control */
6253 /* XXX : not implemented */
6254 spr_register(env, SPR_L2CR, "L2CR",
6255 SPR_NOACCESS, SPR_NOACCESS,
6256 &spr_read_generic, spr_access_nop,
6258 /* XXX : not implemented */
6259 spr_register(env, SPR_L2PMCR, "L2PMCR",
6260 SPR_NOACCESS, SPR_NOACCESS,
6261 &spr_read_generic, &spr_write_generic,
6263 /* Thermal management */
6265 /* Hardware implementation registers */
6266 /* XXX : not implemented */
6267 spr_register(env, SPR_HID0, "HID0",
6268 SPR_NOACCESS, SPR_NOACCESS,
6269 &spr_read_generic, &spr_write_generic,
6271 /* XXX : not implemented */
6272 spr_register(env, SPR_HID1, "HID1",
6273 SPR_NOACCESS, SPR_NOACCESS,
6274 &spr_read_generic, &spr_write_generic,
6276 /* XXX : not implemented */
6277 spr_register(env, SPR_HID2, "HID2",
6278 SPR_NOACCESS, SPR_NOACCESS,
6279 &spr_read_generic, &spr_write_generic,
6281 /* Memory management */
6284 gen_6xx_7xx_soft_tlb(env, 64, 2);
6286 env->dcache_line_size = 32;
6287 env->icache_line_size = 32;
6288 /* Allocate hardware IRQ controller */
6289 ppc6xx_irq_init(env);
6292 POWERPC_FAMILY(755)(ObjectClass *oc, void *data)
6294 DeviceClass *dc = DEVICE_CLASS(oc);
6295 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6297 dc->desc = "PowerPC 755";
6298 pcc->init_proc = init_proc_755;
6299 pcc->check_pow = check_pow_hid0;
6300 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6301 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6302 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
6303 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
6304 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6305 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
6306 PPC_SEGMENT | PPC_EXTERN;
6307 pcc->msr_mask = (1ull << MSR_POW) |
6323 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
6324 pcc->excp_model = POWERPC_EXCP_7x5;
6325 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6326 pcc->bfd_mach = bfd_mach_ppc_750;
6327 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
6328 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
6331 static void init_proc_7400 (CPUPPCState *env)
6333 gen_spr_ne_601(env);
6337 /* 74xx specific SPR */
6339 /* XXX : not implemented */
6340 spr_register(env, SPR_UBAMR, "UBAMR",
6341 &spr_read_ureg, SPR_NOACCESS,
6342 &spr_read_ureg, SPR_NOACCESS,
6344 /* XXX: this seems not implemented on all revisions. */
6345 /* XXX : not implemented */
6346 spr_register(env, SPR_MSSCR1, "MSSCR1",
6347 SPR_NOACCESS, SPR_NOACCESS,
6348 &spr_read_generic, &spr_write_generic,
6350 /* Thermal management */
6352 /* Memory management */
6354 init_excp_7400(env);
6355 env->dcache_line_size = 32;
6356 env->icache_line_size = 32;
6357 /* Allocate hardware IRQ controller */
6358 ppc6xx_irq_init(env);
6361 POWERPC_FAMILY(7400)(ObjectClass *oc, void *data)
6363 DeviceClass *dc = DEVICE_CLASS(oc);
6364 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6366 dc->desc = "PowerPC 7400 (aka G4)";
6367 pcc->init_proc = init_proc_7400;
6368 pcc->check_pow = check_pow_hid0;
6369 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6370 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6371 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6373 PPC_CACHE | PPC_CACHE_ICBI |
6374 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6375 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6376 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6378 PPC_SEGMENT | PPC_EXTERN |
6380 pcc->msr_mask = (1ull << MSR_VR) |
6397 pcc->mmu_model = POWERPC_MMU_32B;
6398 #if defined(CONFIG_SOFTMMU)
6399 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
6401 pcc->excp_model = POWERPC_EXCP_74xx;
6402 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6403 pcc->bfd_mach = bfd_mach_ppc_7400;
6404 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
6405 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
6406 POWERPC_FLAG_BUS_CLK;
6409 static void init_proc_7410 (CPUPPCState *env)
6411 gen_spr_ne_601(env);
6415 /* 74xx specific SPR */
6417 /* XXX : not implemented */
6418 spr_register(env, SPR_UBAMR, "UBAMR",
6419 &spr_read_ureg, SPR_NOACCESS,
6420 &spr_read_ureg, SPR_NOACCESS,
6422 /* Thermal management */
6425 /* XXX : not implemented */
6426 spr_register(env, SPR_L2PMCR, "L2PMCR",
6427 SPR_NOACCESS, SPR_NOACCESS,
6428 &spr_read_generic, &spr_write_generic,
6431 /* XXX : not implemented */
6432 spr_register(env, SPR_LDSTDB, "LDSTDB",
6433 SPR_NOACCESS, SPR_NOACCESS,
6434 &spr_read_generic, &spr_write_generic,
6436 /* Memory management */
6438 init_excp_7400(env);
6439 env->dcache_line_size = 32;
6440 env->icache_line_size = 32;
6441 /* Allocate hardware IRQ controller */
6442 ppc6xx_irq_init(env);
6445 POWERPC_FAMILY(7410)(ObjectClass *oc, void *data)
6447 DeviceClass *dc = DEVICE_CLASS(oc);
6448 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6450 dc->desc = "PowerPC 7410 (aka G4)";
6451 pcc->init_proc = init_proc_7410;
6452 pcc->check_pow = check_pow_hid0;
6453 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6454 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6455 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6457 PPC_CACHE | PPC_CACHE_ICBI |
6458 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6459 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6460 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6462 PPC_SEGMENT | PPC_EXTERN |
6464 pcc->msr_mask = (1ull << MSR_VR) |
6481 pcc->mmu_model = POWERPC_MMU_32B;
6482 #if defined(CONFIG_SOFTMMU)
6483 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
6485 pcc->excp_model = POWERPC_EXCP_74xx;
6486 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6487 pcc->bfd_mach = bfd_mach_ppc_7400;
6488 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
6489 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
6490 POWERPC_FLAG_BUS_CLK;
6493 static void init_proc_7440 (CPUPPCState *env)
6495 gen_spr_ne_601(env);
6499 /* 74xx specific SPR */
6501 /* XXX : not implemented */
6502 spr_register(env, SPR_UBAMR, "UBAMR",
6503 &spr_read_ureg, SPR_NOACCESS,
6504 &spr_read_ureg, SPR_NOACCESS,
6507 /* XXX : not implemented */
6508 spr_register(env, SPR_LDSTCR, "LDSTCR",
6509 SPR_NOACCESS, SPR_NOACCESS,
6510 &spr_read_generic, &spr_write_generic,
6513 /* XXX : not implemented */
6514 spr_register(env, SPR_ICTRL, "ICTRL",
6515 SPR_NOACCESS, SPR_NOACCESS,
6516 &spr_read_generic, &spr_write_generic,
6519 /* XXX : not implemented */
6520 spr_register(env, SPR_MSSSR0, "MSSSR0",
6521 SPR_NOACCESS, SPR_NOACCESS,
6522 &spr_read_generic, &spr_write_generic,
6525 /* XXX : not implemented */
6526 spr_register(env, SPR_7XX_PMC5, "PMC5",
6527 SPR_NOACCESS, SPR_NOACCESS,
6528 &spr_read_generic, &spr_write_generic,
6530 /* XXX : not implemented */
6531 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
6532 &spr_read_ureg, SPR_NOACCESS,
6533 &spr_read_ureg, SPR_NOACCESS,
6535 /* XXX : not implemented */
6536 spr_register(env, SPR_7XX_PMC6, "PMC6",
6537 SPR_NOACCESS, SPR_NOACCESS,
6538 &spr_read_generic, &spr_write_generic,
6540 /* XXX : not implemented */
6541 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
6542 &spr_read_ureg, SPR_NOACCESS,
6543 &spr_read_ureg, SPR_NOACCESS,
6545 /* Memory management */
6547 gen_74xx_soft_tlb(env, 128, 2);
6548 init_excp_7450(env);
6549 env->dcache_line_size = 32;
6550 env->icache_line_size = 32;
6551 /* Allocate hardware IRQ controller */
6552 ppc6xx_irq_init(env);
6555 POWERPC_FAMILY(7440)(ObjectClass *oc, void *data)
6557 DeviceClass *dc = DEVICE_CLASS(oc);
6558 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6560 dc->desc = "PowerPC 7440 (aka G4)";
6561 pcc->init_proc = init_proc_7440;
6562 pcc->check_pow = check_pow_hid0_74xx;
6563 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6564 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6565 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6567 PPC_CACHE | PPC_CACHE_ICBI |
6568 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6569 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6570 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6571 PPC_MEM_TLBIA | PPC_74xx_TLB |
6572 PPC_SEGMENT | PPC_EXTERN |
6574 pcc->msr_mask = (1ull << MSR_VR) |
6591 pcc->mmu_model = POWERPC_MMU_SOFT_74xx;
6592 pcc->excp_model = POWERPC_EXCP_74xx;
6593 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6594 pcc->bfd_mach = bfd_mach_ppc_7400;
6595 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
6596 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
6597 POWERPC_FLAG_BUS_CLK;
6600 static void init_proc_7450 (CPUPPCState *env)
6602 gen_spr_ne_601(env);
6606 /* 74xx specific SPR */
6608 /* Level 3 cache control */
6611 /* XXX : not implemented */
6612 spr_register(env, SPR_L3ITCR1, "L3ITCR1",
6613 SPR_NOACCESS, SPR_NOACCESS,
6614 &spr_read_generic, &spr_write_generic,
6617 /* XXX : not implemented */
6618 spr_register(env, SPR_L3ITCR2, "L3ITCR2",
6619 SPR_NOACCESS, SPR_NOACCESS,
6620 &spr_read_generic, &spr_write_generic,
6623 /* XXX : not implemented */
6624 spr_register(env, SPR_L3ITCR3, "L3ITCR3",
6625 SPR_NOACCESS, SPR_NOACCESS,
6626 &spr_read_generic, &spr_write_generic,
6629 /* XXX : not implemented */
6630 spr_register(env, SPR_L3OHCR, "L3OHCR",
6631 SPR_NOACCESS, SPR_NOACCESS,
6632 &spr_read_generic, &spr_write_generic,
6634 /* XXX : not implemented */
6635 spr_register(env, SPR_UBAMR, "UBAMR",
6636 &spr_read_ureg, SPR_NOACCESS,
6637 &spr_read_ureg, SPR_NOACCESS,
6640 /* XXX : not implemented */
6641 spr_register(env, SPR_LDSTCR, "LDSTCR",
6642 SPR_NOACCESS, SPR_NOACCESS,
6643 &spr_read_generic, &spr_write_generic,
6646 /* XXX : not implemented */
6647 spr_register(env, SPR_ICTRL, "ICTRL",
6648 SPR_NOACCESS, SPR_NOACCESS,
6649 &spr_read_generic, &spr_write_generic,
6652 /* XXX : not implemented */
6653 spr_register(env, SPR_MSSSR0, "MSSSR0",
6654 SPR_NOACCESS, SPR_NOACCESS,
6655 &spr_read_generic, &spr_write_generic,
6658 /* XXX : not implemented */
6659 spr_register(env, SPR_7XX_PMC5, "PMC5",
6660 SPR_NOACCESS, SPR_NOACCESS,
6661 &spr_read_generic, &spr_write_generic,
6663 /* XXX : not implemented */
6664 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
6665 &spr_read_ureg, SPR_NOACCESS,
6666 &spr_read_ureg, SPR_NOACCESS,
6668 /* XXX : not implemented */
6669 spr_register(env, SPR_7XX_PMC6, "PMC6",
6670 SPR_NOACCESS, SPR_NOACCESS,
6671 &spr_read_generic, &spr_write_generic,
6673 /* XXX : not implemented */
6674 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
6675 &spr_read_ureg, SPR_NOACCESS,
6676 &spr_read_ureg, SPR_NOACCESS,
6678 /* Memory management */
6680 gen_74xx_soft_tlb(env, 128, 2);
6681 init_excp_7450(env);
6682 env->dcache_line_size = 32;
6683 env->icache_line_size = 32;
6684 /* Allocate hardware IRQ controller */
6685 ppc6xx_irq_init(env);
6688 POWERPC_FAMILY(7450)(ObjectClass *oc, void *data)
6690 DeviceClass *dc = DEVICE_CLASS(oc);
6691 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6693 dc->desc = "PowerPC 7450 (aka G4)";
6694 pcc->init_proc = init_proc_7450;
6695 pcc->check_pow = check_pow_hid0_74xx;
6696 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6697 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6698 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6700 PPC_CACHE | PPC_CACHE_ICBI |
6701 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6702 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6703 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6704 PPC_MEM_TLBIA | PPC_74xx_TLB |
6705 PPC_SEGMENT | PPC_EXTERN |
6707 pcc->msr_mask = (1ull << MSR_VR) |
6724 pcc->mmu_model = POWERPC_MMU_SOFT_74xx;
6725 pcc->excp_model = POWERPC_EXCP_74xx;
6726 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6727 pcc->bfd_mach = bfd_mach_ppc_7400;
6728 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
6729 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
6730 POWERPC_FLAG_BUS_CLK;
6733 static void init_proc_7445 (CPUPPCState *env)
6735 gen_spr_ne_601(env);
6739 /* 74xx specific SPR */
6742 /* XXX : not implemented */
6743 spr_register(env, SPR_LDSTCR, "LDSTCR",
6744 SPR_NOACCESS, SPR_NOACCESS,
6745 &spr_read_generic, &spr_write_generic,
6748 /* XXX : not implemented */
6749 spr_register(env, SPR_ICTRL, "ICTRL",
6750 SPR_NOACCESS, SPR_NOACCESS,
6751 &spr_read_generic, &spr_write_generic,
6754 /* XXX : not implemented */
6755 spr_register(env, SPR_MSSSR0, "MSSSR0",
6756 SPR_NOACCESS, SPR_NOACCESS,
6757 &spr_read_generic, &spr_write_generic,
6760 /* XXX : not implemented */
6761 spr_register(env, SPR_7XX_PMC5, "PMC5",
6762 SPR_NOACCESS, SPR_NOACCESS,
6763 &spr_read_generic, &spr_write_generic,
6765 /* XXX : not implemented */
6766 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
6767 &spr_read_ureg, SPR_NOACCESS,
6768 &spr_read_ureg, SPR_NOACCESS,
6770 /* XXX : not implemented */
6771 spr_register(env, SPR_7XX_PMC6, "PMC6",
6772 SPR_NOACCESS, SPR_NOACCESS,
6773 &spr_read_generic, &spr_write_generic,
6775 /* XXX : not implemented */
6776 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
6777 &spr_read_ureg, SPR_NOACCESS,
6778 &spr_read_ureg, SPR_NOACCESS,
6781 spr_register(env, SPR_SPRG4, "SPRG4",
6782 SPR_NOACCESS, SPR_NOACCESS,
6783 &spr_read_generic, &spr_write_generic,
6785 spr_register(env, SPR_USPRG4, "USPRG4",
6786 &spr_read_ureg, SPR_NOACCESS,
6787 &spr_read_ureg, SPR_NOACCESS,
6789 spr_register(env, SPR_SPRG5, "SPRG5",
6790 SPR_NOACCESS, SPR_NOACCESS,
6791 &spr_read_generic, &spr_write_generic,
6793 spr_register(env, SPR_USPRG5, "USPRG5",
6794 &spr_read_ureg, SPR_NOACCESS,
6795 &spr_read_ureg, SPR_NOACCESS,
6797 spr_register(env, SPR_SPRG6, "SPRG6",
6798 SPR_NOACCESS, SPR_NOACCESS,
6799 &spr_read_generic, &spr_write_generic,
6801 spr_register(env, SPR_USPRG6, "USPRG6",
6802 &spr_read_ureg, SPR_NOACCESS,
6803 &spr_read_ureg, SPR_NOACCESS,
6805 spr_register(env, SPR_SPRG7, "SPRG7",
6806 SPR_NOACCESS, SPR_NOACCESS,
6807 &spr_read_generic, &spr_write_generic,
6809 spr_register(env, SPR_USPRG7, "USPRG7",
6810 &spr_read_ureg, SPR_NOACCESS,
6811 &spr_read_ureg, SPR_NOACCESS,
6813 /* Memory management */
6816 gen_74xx_soft_tlb(env, 128, 2);
6817 init_excp_7450(env);
6818 env->dcache_line_size = 32;
6819 env->icache_line_size = 32;
6820 /* Allocate hardware IRQ controller */
6821 ppc6xx_irq_init(env);
6824 POWERPC_FAMILY(7445)(ObjectClass *oc, void *data)
6826 DeviceClass *dc = DEVICE_CLASS(oc);
6827 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6829 dc->desc = "PowerPC 7445 (aka G4)";
6830 pcc->init_proc = init_proc_7445;
6831 pcc->check_pow = check_pow_hid0_74xx;
6832 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6833 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6834 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6836 PPC_CACHE | PPC_CACHE_ICBI |
6837 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6838 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6839 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6840 PPC_MEM_TLBIA | PPC_74xx_TLB |
6841 PPC_SEGMENT | PPC_EXTERN |
6843 pcc->msr_mask = (1ull << MSR_VR) |
6860 pcc->mmu_model = POWERPC_MMU_SOFT_74xx;
6861 pcc->excp_model = POWERPC_EXCP_74xx;
6862 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6863 pcc->bfd_mach = bfd_mach_ppc_7400;
6864 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
6865 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
6866 POWERPC_FLAG_BUS_CLK;
6869 static void init_proc_7455 (CPUPPCState *env)
6871 gen_spr_ne_601(env);
6875 /* 74xx specific SPR */
6877 /* Level 3 cache control */
6880 /* XXX : not implemented */
6881 spr_register(env, SPR_LDSTCR, "LDSTCR",
6882 SPR_NOACCESS, SPR_NOACCESS,
6883 &spr_read_generic, &spr_write_generic,
6886 /* XXX : not implemented */
6887 spr_register(env, SPR_ICTRL, "ICTRL",
6888 SPR_NOACCESS, SPR_NOACCESS,
6889 &spr_read_generic, &spr_write_generic,
6892 /* XXX : not implemented */
6893 spr_register(env, SPR_MSSSR0, "MSSSR0",
6894 SPR_NOACCESS, SPR_NOACCESS,
6895 &spr_read_generic, &spr_write_generic,
6898 /* XXX : not implemented */
6899 spr_register(env, SPR_7XX_PMC5, "PMC5",
6900 SPR_NOACCESS, SPR_NOACCESS,
6901 &spr_read_generic, &spr_write_generic,
6903 /* XXX : not implemented */
6904 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
6905 &spr_read_ureg, SPR_NOACCESS,
6906 &spr_read_ureg, SPR_NOACCESS,
6908 /* XXX : not implemented */
6909 spr_register(env, SPR_7XX_PMC6, "PMC6",
6910 SPR_NOACCESS, SPR_NOACCESS,
6911 &spr_read_generic, &spr_write_generic,
6913 /* XXX : not implemented */
6914 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
6915 &spr_read_ureg, SPR_NOACCESS,
6916 &spr_read_ureg, SPR_NOACCESS,
6919 spr_register(env, SPR_SPRG4, "SPRG4",
6920 SPR_NOACCESS, SPR_NOACCESS,
6921 &spr_read_generic, &spr_write_generic,
6923 spr_register(env, SPR_USPRG4, "USPRG4",
6924 &spr_read_ureg, SPR_NOACCESS,
6925 &spr_read_ureg, SPR_NOACCESS,
6927 spr_register(env, SPR_SPRG5, "SPRG5",
6928 SPR_NOACCESS, SPR_NOACCESS,
6929 &spr_read_generic, &spr_write_generic,
6931 spr_register(env, SPR_USPRG5, "USPRG5",
6932 &spr_read_ureg, SPR_NOACCESS,
6933 &spr_read_ureg, SPR_NOACCESS,
6935 spr_register(env, SPR_SPRG6, "SPRG6",
6936 SPR_NOACCESS, SPR_NOACCESS,
6937 &spr_read_generic, &spr_write_generic,
6939 spr_register(env, SPR_USPRG6, "USPRG6",
6940 &spr_read_ureg, SPR_NOACCESS,
6941 &spr_read_ureg, SPR_NOACCESS,
6943 spr_register(env, SPR_SPRG7, "SPRG7",
6944 SPR_NOACCESS, SPR_NOACCESS,
6945 &spr_read_generic, &spr_write_generic,
6947 spr_register(env, SPR_USPRG7, "USPRG7",
6948 &spr_read_ureg, SPR_NOACCESS,
6949 &spr_read_ureg, SPR_NOACCESS,
6951 /* Memory management */
6954 gen_74xx_soft_tlb(env, 128, 2);
6955 init_excp_7450(env);
6956 env->dcache_line_size = 32;
6957 env->icache_line_size = 32;
6958 /* Allocate hardware IRQ controller */
6959 ppc6xx_irq_init(env);
6962 POWERPC_FAMILY(7455)(ObjectClass *oc, void *data)
6964 DeviceClass *dc = DEVICE_CLASS(oc);
6965 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6967 dc->desc = "PowerPC 7455 (aka G4)";
6968 pcc->init_proc = init_proc_7455;
6969 pcc->check_pow = check_pow_hid0_74xx;
6970 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6971 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6972 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6974 PPC_CACHE | PPC_CACHE_ICBI |
6975 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6976 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6977 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6978 PPC_MEM_TLBIA | PPC_74xx_TLB |
6979 PPC_SEGMENT | PPC_EXTERN |
6981 pcc->msr_mask = (1ull << MSR_VR) |
6998 pcc->mmu_model = POWERPC_MMU_SOFT_74xx;
6999 pcc->excp_model = POWERPC_EXCP_74xx;
7000 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
7001 pcc->bfd_mach = bfd_mach_ppc_7400;
7002 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
7003 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
7004 POWERPC_FLAG_BUS_CLK;
7007 static void init_proc_7457 (CPUPPCState *env)
7009 gen_spr_ne_601(env);
7013 /* 74xx specific SPR */
7015 /* Level 3 cache control */
7018 /* XXX : not implemented */
7019 spr_register(env, SPR_L3ITCR1, "L3ITCR1",
7020 SPR_NOACCESS, SPR_NOACCESS,
7021 &spr_read_generic, &spr_write_generic,
7024 /* XXX : not implemented */
7025 spr_register(env, SPR_L3ITCR2, "L3ITCR2",
7026 SPR_NOACCESS, SPR_NOACCESS,
7027 &spr_read_generic, &spr_write_generic,
7030 /* XXX : not implemented */
7031 spr_register(env, SPR_L3ITCR3, "L3ITCR3",
7032 SPR_NOACCESS, SPR_NOACCESS,
7033 &spr_read_generic, &spr_write_generic,
7036 /* XXX : not implemented */
7037 spr_register(env, SPR_L3OHCR, "L3OHCR",
7038 SPR_NOACCESS, SPR_NOACCESS,
7039 &spr_read_generic, &spr_write_generic,
7042 /* XXX : not implemented */
7043 spr_register(env, SPR_LDSTCR, "LDSTCR",
7044 SPR_NOACCESS, SPR_NOACCESS,
7045 &spr_read_generic, &spr_write_generic,
7048 /* XXX : not implemented */
7049 spr_register(env, SPR_ICTRL, "ICTRL",
7050 SPR_NOACCESS, SPR_NOACCESS,
7051 &spr_read_generic, &spr_write_generic,
7054 /* XXX : not implemented */
7055 spr_register(env, SPR_MSSSR0, "MSSSR0",
7056 SPR_NOACCESS, SPR_NOACCESS,
7057 &spr_read_generic, &spr_write_generic,
7060 /* XXX : not implemented */
7061 spr_register(env, SPR_7XX_PMC5, "PMC5",
7062 SPR_NOACCESS, SPR_NOACCESS,
7063 &spr_read_generic, &spr_write_generic,
7065 /* XXX : not implemented */
7066 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
7067 &spr_read_ureg, SPR_NOACCESS,
7068 &spr_read_ureg, SPR_NOACCESS,
7070 /* XXX : not implemented */
7071 spr_register(env, SPR_7XX_PMC6, "PMC6",
7072 SPR_NOACCESS, SPR_NOACCESS,
7073 &spr_read_generic, &spr_write_generic,
7075 /* XXX : not implemented */
7076 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
7077 &spr_read_ureg, SPR_NOACCESS,
7078 &spr_read_ureg, SPR_NOACCESS,
7081 spr_register(env, SPR_SPRG4, "SPRG4",
7082 SPR_NOACCESS, SPR_NOACCESS,
7083 &spr_read_generic, &spr_write_generic,
7085 spr_register(env, SPR_USPRG4, "USPRG4",
7086 &spr_read_ureg, SPR_NOACCESS,
7087 &spr_read_ureg, SPR_NOACCESS,
7089 spr_register(env, SPR_SPRG5, "SPRG5",
7090 SPR_NOACCESS, SPR_NOACCESS,
7091 &spr_read_generic, &spr_write_generic,
7093 spr_register(env, SPR_USPRG5, "USPRG5",
7094 &spr_read_ureg, SPR_NOACCESS,
7095 &spr_read_ureg, SPR_NOACCESS,
7097 spr_register(env, SPR_SPRG6, "SPRG6",
7098 SPR_NOACCESS, SPR_NOACCESS,
7099 &spr_read_generic, &spr_write_generic,
7101 spr_register(env, SPR_USPRG6, "USPRG6",
7102 &spr_read_ureg, SPR_NOACCESS,
7103 &spr_read_ureg, SPR_NOACCESS,
7105 spr_register(env, SPR_SPRG7, "SPRG7",
7106 SPR_NOACCESS, SPR_NOACCESS,
7107 &spr_read_generic, &spr_write_generic,
7109 spr_register(env, SPR_USPRG7, "USPRG7",
7110 &spr_read_ureg, SPR_NOACCESS,
7111 &spr_read_ureg, SPR_NOACCESS,
7113 /* Memory management */
7116 gen_74xx_soft_tlb(env, 128, 2);
7117 init_excp_7450(env);
7118 env->dcache_line_size = 32;
7119 env->icache_line_size = 32;
7120 /* Allocate hardware IRQ controller */
7121 ppc6xx_irq_init(env);
7124 POWERPC_FAMILY(7457)(ObjectClass *oc, void *data)
7126 DeviceClass *dc = DEVICE_CLASS(oc);
7127 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
7129 dc->desc = "PowerPC 7457 (aka G4)";
7130 pcc->init_proc = init_proc_7457;
7131 pcc->check_pow = check_pow_hid0_74xx;
7132 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
7133 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
7134 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
7136 PPC_CACHE | PPC_CACHE_ICBI |
7137 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
7138 PPC_MEM_SYNC | PPC_MEM_EIEIO |
7139 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
7140 PPC_MEM_TLBIA | PPC_74xx_TLB |
7141 PPC_SEGMENT | PPC_EXTERN |
7143 pcc->msr_mask = (1ull << MSR_VR) |
7160 pcc->mmu_model = POWERPC_MMU_SOFT_74xx;
7161 pcc->excp_model = POWERPC_EXCP_74xx;
7162 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
7163 pcc->bfd_mach = bfd_mach_ppc_7400;
7164 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
7165 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
7166 POWERPC_FLAG_BUS_CLK;
7169 static void init_proc_e600 (CPUPPCState *env)
7171 gen_spr_ne_601(env);
7175 /* 74xx specific SPR */
7177 /* XXX : not implemented */
7178 spr_register(env, SPR_UBAMR, "UBAMR",
7179 &spr_read_ureg, SPR_NOACCESS,
7180 &spr_read_ureg, SPR_NOACCESS,
7182 /* XXX : not implemented */
7183 spr_register(env, SPR_LDSTCR, "LDSTCR",
7184 SPR_NOACCESS, SPR_NOACCESS,
7185 &spr_read_generic, &spr_write_generic,
7187 /* XXX : not implemented */
7188 spr_register(env, SPR_ICTRL, "ICTRL",
7189 SPR_NOACCESS, SPR_NOACCESS,
7190 &spr_read_generic, &spr_write_generic,
7192 /* XXX : not implemented */
7193 spr_register(env, SPR_MSSSR0, "MSSSR0",
7194 SPR_NOACCESS, SPR_NOACCESS,
7195 &spr_read_generic, &spr_write_generic,
7197 /* XXX : not implemented */
7198 spr_register(env, SPR_7XX_PMC5, "PMC5",
7199 SPR_NOACCESS, SPR_NOACCESS,
7200 &spr_read_generic, &spr_write_generic,
7202 /* XXX : not implemented */
7203 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
7204 &spr_read_ureg, SPR_NOACCESS,
7205 &spr_read_ureg, SPR_NOACCESS,
7207 /* XXX : not implemented */
7208 spr_register(env, SPR_7XX_PMC6, "PMC6",
7209 SPR_NOACCESS, SPR_NOACCESS,
7210 &spr_read_generic, &spr_write_generic,
7212 /* XXX : not implemented */
7213 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
7214 &spr_read_ureg, SPR_NOACCESS,
7215 &spr_read_ureg, SPR_NOACCESS,
7218 spr_register(env, SPR_SPRG4, "SPRG4",
7219 SPR_NOACCESS, SPR_NOACCESS,
7220 &spr_read_generic, &spr_write_generic,
7222 spr_register(env, SPR_USPRG4, "USPRG4",
7223 &spr_read_ureg, SPR_NOACCESS,
7224 &spr_read_ureg, SPR_NOACCESS,
7226 spr_register(env, SPR_SPRG5, "SPRG5",
7227 SPR_NOACCESS, SPR_NOACCESS,
7228 &spr_read_generic, &spr_write_generic,
7230 spr_register(env, SPR_USPRG5, "USPRG5",
7231 &spr_read_ureg, SPR_NOACCESS,
7232 &spr_read_ureg, SPR_NOACCESS,
7234 spr_register(env, SPR_SPRG6, "SPRG6",
7235 SPR_NOACCESS, SPR_NOACCESS,
7236 &spr_read_generic, &spr_write_generic,
7238 spr_register(env, SPR_USPRG6, "USPRG6",
7239 &spr_read_ureg, SPR_NOACCESS,
7240 &spr_read_ureg, SPR_NOACCESS,
7242 spr_register(env, SPR_SPRG7, "SPRG7",
7243 SPR_NOACCESS, SPR_NOACCESS,
7244 &spr_read_generic, &spr_write_generic,
7246 spr_register(env, SPR_USPRG7, "USPRG7",
7247 &spr_read_ureg, SPR_NOACCESS,
7248 &spr_read_ureg, SPR_NOACCESS,
7250 /* Memory management */
7253 gen_74xx_soft_tlb(env, 128, 2);
7254 init_excp_7450(env);
7255 env->dcache_line_size = 32;
7256 env->icache_line_size = 32;
7257 /* Allocate hardware IRQ controller */
7258 ppc6xx_irq_init(env);
7261 POWERPC_FAMILY(e600)(ObjectClass *oc, void *data)
7263 DeviceClass *dc = DEVICE_CLASS(oc);
7264 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
7266 dc->desc = "PowerPC e600";
7267 pcc->init_proc = init_proc_e600;
7268 pcc->check_pow = check_pow_hid0_74xx;
7269 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
7270 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
7271 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
7273 PPC_CACHE | PPC_CACHE_ICBI |
7274 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
7275 PPC_MEM_SYNC | PPC_MEM_EIEIO |
7276 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
7277 PPC_MEM_TLBIA | PPC_74xx_TLB |
7278 PPC_SEGMENT | PPC_EXTERN |
7280 pcc->insns_flags2 = PPC_NONE;
7281 pcc->msr_mask = (1ull << MSR_VR) |
7298 pcc->mmu_model = POWERPC_MMU_32B;
7299 #if defined(CONFIG_SOFTMMU)
7300 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
7302 pcc->excp_model = POWERPC_EXCP_74xx;
7303 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
7304 pcc->bfd_mach = bfd_mach_ppc_7400;
7305 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
7306 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
7307 POWERPC_FLAG_BUS_CLK;
7310 #if defined (TARGET_PPC64)
7311 #if defined(CONFIG_USER_ONLY)
7312 #define POWERPC970_HID5_INIT 0x00000080
7314 #define POWERPC970_HID5_INIT 0x00000000
7317 enum BOOK3S_CPU_TYPE {
7319 BOOK3S_CPU_POWER5PLUS,
7325 static void gen_fscr_facility_check(void *opaque, int facility_sprn, int bit,
7326 int sprn, int cause)
7328 TCGv_i32 t1 = tcg_const_i32(bit);
7329 TCGv_i32 t2 = tcg_const_i32(sprn);
7330 TCGv_i32 t3 = tcg_const_i32(cause);
7332 gen_update_current_nip(opaque);
7333 gen_helper_fscr_facility_check(cpu_env, t1, t2, t3);
7335 tcg_temp_free_i32(t3);
7336 tcg_temp_free_i32(t2);
7337 tcg_temp_free_i32(t1);
7340 static void gen_msr_facility_check(void *opaque, int facility_sprn, int bit,
7341 int sprn, int cause)
7343 TCGv_i32 t1 = tcg_const_i32(bit);
7344 TCGv_i32 t2 = tcg_const_i32(sprn);
7345 TCGv_i32 t3 = tcg_const_i32(cause);
7347 gen_update_current_nip(opaque);
7348 gen_helper_msr_facility_check(cpu_env, t1, t2, t3);
7350 tcg_temp_free_i32(t3);
7351 tcg_temp_free_i32(t2);
7352 tcg_temp_free_i32(t1);
7355 static void spr_read_prev_upper32(void *opaque, int gprn, int sprn)
7357 TCGv spr_up = tcg_temp_new();
7358 TCGv spr = tcg_temp_new();
7360 gen_load_spr(spr, sprn - 1);
7361 tcg_gen_shri_tl(spr_up, spr, 32);
7362 tcg_gen_ext32u_tl(cpu_gpr[gprn], spr_up);
7365 tcg_temp_free(spr_up);
7368 static void spr_write_prev_upper32(void *opaque, int sprn, int gprn)
7370 TCGv spr = tcg_temp_new();
7372 gen_load_spr(spr, sprn - 1);
7373 tcg_gen_deposit_tl(spr, spr, cpu_gpr[gprn], 32, 32);
7374 gen_store_spr(sprn - 1, spr);
7379 static int check_pow_970 (CPUPPCState *env)
7381 if (env->spr[SPR_HID0] & (HID0_DEEPNAP | HID0_DOZE | HID0_NAP)) {
7388 static void gen_spr_970_hid(CPUPPCState *env)
7390 /* Hardware implementation registers */
7391 /* XXX : not implemented */
7392 spr_register(env, SPR_HID0, "HID0",
7393 SPR_NOACCESS, SPR_NOACCESS,
7394 &spr_read_generic, &spr_write_clear,
7396 spr_register(env, SPR_HID1, "HID1",
7397 SPR_NOACCESS, SPR_NOACCESS,
7398 &spr_read_generic, &spr_write_generic,
7400 spr_register(env, SPR_970_HID5, "HID5",
7401 SPR_NOACCESS, SPR_NOACCESS,
7402 &spr_read_generic, &spr_write_generic,
7403 POWERPC970_HID5_INIT);
7406 static void gen_spr_970_hior(CPUPPCState *env)
7408 spr_register(env, SPR_HIOR, "SPR_HIOR",
7409 SPR_NOACCESS, SPR_NOACCESS,
7410 &spr_read_hior, &spr_write_hior,
7414 static void gen_spr_970_lpar(CPUPPCState *env)
7416 /* Logical partitionning */
7417 /* PPC970: HID4 is effectively the LPCR */
7418 spr_register(env, SPR_970_HID4, "HID4",
7419 SPR_NOACCESS, SPR_NOACCESS,
7420 &spr_read_generic, &spr_write_generic,
7424 static void gen_spr_book3s_common(CPUPPCState *env)
7426 spr_register(env, SPR_CTRL, "SPR_CTRL",
7427 SPR_NOACCESS, SPR_NOACCESS,
7428 SPR_NOACCESS, &spr_write_generic,
7430 spr_register(env, SPR_UCTRL, "SPR_UCTRL",
7431 &spr_read_ureg, SPR_NOACCESS,
7432 &spr_read_ureg, SPR_NOACCESS,
7436 static void gen_spr_book3s_altivec(CPUPPCState *env)
7438 if (!(env->insns_flags & PPC_ALTIVEC)) {
7442 spr_register_kvm(env, SPR_VRSAVE, "VRSAVE",
7443 &spr_read_generic, &spr_write_generic,
7444 &spr_read_generic, &spr_write_generic,
7445 KVM_REG_PPC_VRSAVE, 0x00000000);
7447 /* Can't find information on what this should be on reset. This
7448 * value is the one used by 74xx processors. */
7449 vscr_init(env, 0x00010000);
7452 static void gen_spr_book3s_dbg(CPUPPCState *env)
7455 * TODO: different specs define different scopes for these,
7456 * will have to address this:
7457 * 970: super/write and super/read
7458 * powerisa 2.03..2.04: hypv/write and super/read.
7459 * powerisa 2.05 and newer: hypv/write and hypv/read.
7461 spr_register_kvm(env, SPR_DABR, "DABR",
7462 SPR_NOACCESS, SPR_NOACCESS,
7463 &spr_read_generic, &spr_write_generic,
7464 KVM_REG_PPC_DABR, 0x00000000);
7465 spr_register_kvm(env, SPR_DABRX, "DABRX",
7466 SPR_NOACCESS, SPR_NOACCESS,
7467 &spr_read_generic, &spr_write_generic,
7468 KVM_REG_PPC_DABRX, 0x00000000);
7471 static void gen_spr_970_dbg(CPUPPCState *env)
7474 spr_register(env, SPR_IABR, "IABR",
7475 SPR_NOACCESS, SPR_NOACCESS,
7476 &spr_read_generic, &spr_write_generic,
7480 static void gen_spr_book3s_pmu_sup(CPUPPCState *env)
7482 spr_register_kvm(env, SPR_POWER_MMCR0, "MMCR0",
7483 SPR_NOACCESS, SPR_NOACCESS,
7484 &spr_read_generic, &spr_write_generic,
7485 KVM_REG_PPC_MMCR0, 0x00000000);
7486 spr_register_kvm(env, SPR_POWER_MMCR1, "MMCR1",
7487 SPR_NOACCESS, SPR_NOACCESS,
7488 &spr_read_generic, &spr_write_generic,
7489 KVM_REG_PPC_MMCR1, 0x00000000);
7490 spr_register_kvm(env, SPR_POWER_MMCRA, "MMCRA",
7491 SPR_NOACCESS, SPR_NOACCESS,
7492 &spr_read_generic, &spr_write_generic,
7493 KVM_REG_PPC_MMCRA, 0x00000000);
7494 spr_register_kvm(env, SPR_POWER_PMC1, "PMC1",
7495 SPR_NOACCESS, SPR_NOACCESS,
7496 &spr_read_generic, &spr_write_generic,
7497 KVM_REG_PPC_PMC1, 0x00000000);
7498 spr_register_kvm(env, SPR_POWER_PMC2, "PMC2",
7499 SPR_NOACCESS, SPR_NOACCESS,
7500 &spr_read_generic, &spr_write_generic,
7501 KVM_REG_PPC_PMC2, 0x00000000);
7502 spr_register_kvm(env, SPR_POWER_PMC3, "PMC3",
7503 SPR_NOACCESS, SPR_NOACCESS,
7504 &spr_read_generic, &spr_write_generic,
7505 KVM_REG_PPC_PMC3, 0x00000000);
7506 spr_register_kvm(env, SPR_POWER_PMC4, "PMC4",
7507 SPR_NOACCESS, SPR_NOACCESS,
7508 &spr_read_generic, &spr_write_generic,
7509 KVM_REG_PPC_PMC4, 0x00000000);
7510 spr_register_kvm(env, SPR_POWER_PMC5, "PMC5",
7511 SPR_NOACCESS, SPR_NOACCESS,
7512 &spr_read_generic, &spr_write_generic,
7513 KVM_REG_PPC_PMC5, 0x00000000);
7514 spr_register_kvm(env, SPR_POWER_PMC6, "PMC6",
7515 SPR_NOACCESS, SPR_NOACCESS,
7516 &spr_read_generic, &spr_write_generic,
7517 KVM_REG_PPC_PMC6, 0x00000000);
7518 spr_register_kvm(env, SPR_POWER_SIAR, "SIAR",
7519 SPR_NOACCESS, SPR_NOACCESS,
7520 &spr_read_generic, &spr_write_generic,
7521 KVM_REG_PPC_SIAR, 0x00000000);
7522 spr_register_kvm(env, SPR_POWER_SDAR, "SDAR",
7523 SPR_NOACCESS, SPR_NOACCESS,
7524 &spr_read_generic, &spr_write_generic,
7525 KVM_REG_PPC_SDAR, 0x00000000);
7528 static void gen_spr_book3s_pmu_user(CPUPPCState *env)
7530 spr_register(env, SPR_POWER_UMMCR0, "UMMCR0",
7531 &spr_read_ureg, SPR_NOACCESS,
7532 &spr_read_ureg, &spr_write_ureg,
7534 spr_register(env, SPR_POWER_UMMCR1, "UMMCR1",
7535 &spr_read_ureg, SPR_NOACCESS,
7536 &spr_read_ureg, &spr_write_ureg,
7538 spr_register(env, SPR_POWER_UMMCRA, "UMMCRA",
7539 &spr_read_ureg, SPR_NOACCESS,
7540 &spr_read_ureg, &spr_write_ureg,
7542 spr_register(env, SPR_POWER_UPMC1, "UPMC1",
7543 &spr_read_ureg, SPR_NOACCESS,
7544 &spr_read_ureg, &spr_write_ureg,
7546 spr_register(env, SPR_POWER_UPMC2, "UPMC2",
7547 &spr_read_ureg, SPR_NOACCESS,
7548 &spr_read_ureg, &spr_write_ureg,
7550 spr_register(env, SPR_POWER_UPMC3, "UPMC3",
7551 &spr_read_ureg, SPR_NOACCESS,
7552 &spr_read_ureg, &spr_write_ureg,
7554 spr_register(env, SPR_POWER_UPMC4, "UPMC4",
7555 &spr_read_ureg, SPR_NOACCESS,
7556 &spr_read_ureg, &spr_write_ureg,
7558 spr_register(env, SPR_POWER_UPMC5, "UPMC5",
7559 &spr_read_ureg, SPR_NOACCESS,
7560 &spr_read_ureg, &spr_write_ureg,
7562 spr_register(env, SPR_POWER_UPMC6, "UPMC6",
7563 &spr_read_ureg, SPR_NOACCESS,
7564 &spr_read_ureg, &spr_write_ureg,
7566 spr_register(env, SPR_POWER_USIAR, "USIAR",
7567 &spr_read_ureg, SPR_NOACCESS,
7568 &spr_read_ureg, &spr_write_ureg,
7570 spr_register(env, SPR_POWER_USDAR, "USDAR",
7571 &spr_read_ureg, SPR_NOACCESS,
7572 &spr_read_ureg, &spr_write_ureg,
7576 static void gen_spr_970_pmu_sup(CPUPPCState *env)
7578 spr_register_kvm(env, SPR_970_PMC7, "PMC7",
7579 SPR_NOACCESS, SPR_NOACCESS,
7580 &spr_read_generic, &spr_write_generic,
7581 KVM_REG_PPC_PMC7, 0x00000000);
7582 spr_register_kvm(env, SPR_970_PMC8, "PMC8",
7583 SPR_NOACCESS, SPR_NOACCESS,
7584 &spr_read_generic, &spr_write_generic,
7585 KVM_REG_PPC_PMC8, 0x00000000);
7588 static void gen_spr_970_pmu_user(CPUPPCState *env)
7590 spr_register(env, SPR_970_UPMC7, "UPMC7",
7591 &spr_read_ureg, SPR_NOACCESS,
7592 &spr_read_ureg, &spr_write_ureg,
7594 spr_register(env, SPR_970_UPMC8, "UPMC8",
7595 &spr_read_ureg, SPR_NOACCESS,
7596 &spr_read_ureg, &spr_write_ureg,
7600 static void gen_spr_power8_pmu_sup(CPUPPCState *env)
7602 spr_register_kvm(env, SPR_POWER_MMCR2, "MMCR2",
7603 SPR_NOACCESS, SPR_NOACCESS,
7604 &spr_read_generic, &spr_write_generic,
7605 KVM_REG_PPC_MMCR2, 0x00000000);
7606 spr_register_kvm(env, SPR_POWER_MMCRS, "MMCRS",
7607 SPR_NOACCESS, SPR_NOACCESS,
7608 &spr_read_generic, &spr_write_generic,
7609 KVM_REG_PPC_MMCRS, 0x00000000);
7612 static void gen_spr_power8_pmu_user(CPUPPCState *env)
7614 spr_register(env, SPR_POWER_UMMCR2, "UMMCR2",
7615 &spr_read_ureg, SPR_NOACCESS,
7616 &spr_read_ureg, &spr_write_ureg,
7620 static void gen_spr_power5p_ear(CPUPPCState *env)
7622 /* External access control */
7623 spr_register(env, SPR_EAR, "EAR",
7624 SPR_NOACCESS, SPR_NOACCESS,
7625 &spr_read_generic, &spr_write_generic,
7629 static void gen_spr_power5p_lpar(CPUPPCState *env)
7631 /* Logical partitionning */
7632 spr_register_kvm(env, SPR_LPCR, "LPCR",
7633 SPR_NOACCESS, SPR_NOACCESS,
7634 &spr_read_generic, &spr_write_generic,
7635 KVM_REG_PPC_LPCR, 0x00000000);
7638 static void gen_spr_book3s_ids(CPUPPCState *env)
7640 /* Processor identification */
7641 spr_register(env, SPR_PIR, "PIR",
7642 SPR_NOACCESS, SPR_NOACCESS,
7643 &spr_read_generic, &spr_write_pir,
7647 static void gen_spr_power8_ids(CPUPPCState *env)
7649 /* Thread identification */
7650 spr_register(env, SPR_TIR, "TIR",
7651 SPR_NOACCESS, SPR_NOACCESS,
7652 &spr_read_generic, SPR_NOACCESS,
7656 static void gen_spr_book3s_purr(CPUPPCState *env)
7658 #if !defined(CONFIG_USER_ONLY)
7659 /* PURR & SPURR: Hack - treat these as aliases for the TB for now */
7660 spr_register_kvm(env, SPR_PURR, "PURR",
7661 &spr_read_purr, SPR_NOACCESS,
7662 &spr_read_purr, SPR_NOACCESS,
7663 KVM_REG_PPC_PURR, 0x00000000);
7664 spr_register_kvm(env, SPR_SPURR, "SPURR",
7665 &spr_read_purr, SPR_NOACCESS,
7666 &spr_read_purr, SPR_NOACCESS,
7667 KVM_REG_PPC_SPURR, 0x00000000);
7671 static void gen_spr_power6_dbg(CPUPPCState *env)
7673 #if !defined(CONFIG_USER_ONLY)
7674 spr_register(env, SPR_CFAR, "SPR_CFAR",
7675 SPR_NOACCESS, SPR_NOACCESS,
7676 &spr_read_cfar, &spr_write_cfar,
7681 static void gen_spr_power5p_common(CPUPPCState *env)
7683 spr_register_kvm(env, SPR_PPR, "PPR",
7684 &spr_read_generic, &spr_write_generic,
7685 &spr_read_generic, &spr_write_generic,
7686 KVM_REG_PPC_PPR, 0x00000000);
7689 static void gen_spr_power6_common(CPUPPCState *env)
7691 #if !defined(CONFIG_USER_ONLY)
7692 spr_register_kvm(env, SPR_DSCR, "SPR_DSCR",
7693 SPR_NOACCESS, SPR_NOACCESS,
7694 &spr_read_generic, &spr_write_generic,
7695 KVM_REG_PPC_DSCR, 0x00000000);
7698 * Register PCR to report POWERPC_EXCP_PRIV_REG instead of
7699 * POWERPC_EXCP_INVAL_SPR.
7701 spr_register(env, SPR_PCR, "PCR",
7702 SPR_NOACCESS, SPR_NOACCESS,
7703 SPR_NOACCESS, SPR_NOACCESS,
7707 static void spr_read_tar(void *opaque, int gprn, int sprn)
7709 gen_fscr_facility_check(opaque, SPR_FSCR, FSCR_TAR, sprn, FSCR_IC_TAR);
7710 spr_read_generic(opaque, gprn, sprn);
7713 static void spr_write_tar(void *opaque, int sprn, int gprn)
7715 gen_fscr_facility_check(opaque, SPR_FSCR, FSCR_TAR, sprn, FSCR_IC_TAR);
7716 spr_write_generic(opaque, sprn, gprn);
7719 static void gen_spr_power8_tce_address_control(CPUPPCState *env)
7721 spr_register(env, SPR_TAR, "TAR",
7722 &spr_read_tar, &spr_write_tar,
7723 &spr_read_generic, &spr_write_generic,
7727 static void spr_read_tm(void *opaque, int gprn, int sprn)
7729 gen_msr_facility_check(opaque, SPR_FSCR, MSR_TM, sprn, FSCR_IC_TM);
7730 spr_read_generic(opaque, gprn, sprn);
7733 static void spr_write_tm(void *opaque, int sprn, int gprn)
7735 gen_msr_facility_check(opaque, SPR_FSCR, MSR_TM, sprn, FSCR_IC_TM);
7736 spr_write_generic(opaque, sprn, gprn);
7739 static void spr_read_tm_upper32(void *opaque, int gprn, int sprn)
7741 gen_msr_facility_check(opaque, SPR_FSCR, MSR_TM, sprn, FSCR_IC_TM);
7742 spr_read_prev_upper32(opaque, gprn, sprn);
7745 static void spr_write_tm_upper32(void *opaque, int sprn, int gprn)
7747 gen_msr_facility_check(opaque, SPR_FSCR, MSR_TM, sprn, FSCR_IC_TM);
7748 spr_write_prev_upper32(opaque, sprn, gprn);
7751 static void gen_spr_power8_tm(CPUPPCState *env)
7753 spr_register_kvm(env, SPR_TFHAR, "TFHAR",
7754 &spr_read_tm, &spr_write_tm,
7755 &spr_read_tm, &spr_write_tm,
7756 KVM_REG_PPC_TFHAR, 0x00000000);
7757 spr_register_kvm(env, SPR_TFIAR, "TFIAR",
7758 &spr_read_tm, &spr_write_tm,
7759 &spr_read_tm, &spr_write_tm,
7760 KVM_REG_PPC_TFIAR, 0x00000000);
7761 spr_register_kvm(env, SPR_TEXASR, "TEXASR",
7762 &spr_read_tm, &spr_write_tm,
7763 &spr_read_tm, &spr_write_tm,
7764 KVM_REG_PPC_TEXASR, 0x00000000);
7765 spr_register(env, SPR_TEXASRU, "TEXASRU",
7766 &spr_read_tm_upper32, &spr_write_tm_upper32,
7767 &spr_read_tm_upper32, &spr_write_tm_upper32,
7771 static void spr_read_ebb(void *opaque, int gprn, int sprn)
7773 gen_fscr_facility_check(opaque, SPR_FSCR, FSCR_EBB, sprn, FSCR_IC_EBB);
7774 spr_read_generic(opaque, gprn, sprn);
7777 static void spr_write_ebb(void *opaque, int sprn, int gprn)
7779 gen_fscr_facility_check(opaque, SPR_FSCR, FSCR_EBB, sprn, FSCR_IC_EBB);
7780 spr_write_generic(opaque, sprn, gprn);
7783 static void spr_read_ebb_upper32(void *opaque, int gprn, int sprn)
7785 gen_fscr_facility_check(opaque, SPR_FSCR, FSCR_EBB, sprn, FSCR_IC_EBB);
7786 spr_read_prev_upper32(opaque, gprn, sprn);
7789 static void spr_write_ebb_upper32(void *opaque, int sprn, int gprn)
7791 gen_fscr_facility_check(opaque, SPR_FSCR, FSCR_EBB, sprn, FSCR_IC_EBB);
7792 spr_write_prev_upper32(opaque, sprn, gprn);
7795 static void gen_spr_power8_ebb(CPUPPCState *env)
7797 spr_register(env, SPR_BESCRS, "BESCRS",
7798 &spr_read_ebb, &spr_write_ebb,
7799 &spr_read_generic, &spr_write_generic,
7801 spr_register(env, SPR_BESCRSU, "BESCRSU",
7802 &spr_read_ebb_upper32, &spr_write_ebb_upper32,
7803 &spr_read_prev_upper32, &spr_write_prev_upper32,
7805 spr_register(env, SPR_BESCRR, "BESCRR",
7806 &spr_read_ebb, &spr_write_ebb,
7807 &spr_read_generic, &spr_write_generic,
7809 spr_register(env, SPR_BESCRRU, "BESCRRU",
7810 &spr_read_ebb_upper32, &spr_write_ebb_upper32,
7811 &spr_read_prev_upper32, &spr_write_prev_upper32,
7813 spr_register_kvm(env, SPR_EBBHR, "EBBHR",
7814 &spr_read_ebb, &spr_write_ebb,
7815 &spr_read_generic, &spr_write_generic,
7816 KVM_REG_PPC_EBBHR, 0x00000000);
7817 spr_register_kvm(env, SPR_EBBRR, "EBBRR",
7818 &spr_read_ebb, &spr_write_ebb,
7819 &spr_read_generic, &spr_write_generic,
7820 KVM_REG_PPC_EBBRR, 0x00000000);
7821 spr_register_kvm(env, SPR_BESCR, "BESCR",
7822 &spr_read_ebb, &spr_write_ebb,
7823 &spr_read_generic, &spr_write_generic,
7824 KVM_REG_PPC_BESCR, 0x00000000);
7827 static void gen_spr_power8_fscr(CPUPPCState *env)
7829 #if defined(CONFIG_USER_ONLY)
7830 target_ulong initval = 1ULL << FSCR_TAR;
7832 target_ulong initval = 0;
7834 spr_register_kvm(env, SPR_FSCR, "FSCR",
7835 SPR_NOACCESS, SPR_NOACCESS,
7836 &spr_read_generic, &spr_write_generic,
7837 KVM_REG_PPC_FSCR, initval);
7840 static void init_proc_book3s_64(CPUPPCState *env, int version)
7842 gen_spr_ne_601(env);
7844 gen_spr_book3s_altivec(env);
7845 gen_spr_book3s_pmu_sup(env);
7846 gen_spr_book3s_pmu_user(env);
7847 gen_spr_book3s_common(env);
7850 case BOOK3S_CPU_970:
7851 case BOOK3S_CPU_POWER5PLUS:
7852 gen_spr_970_hid(env);
7853 gen_spr_970_hior(env);
7855 gen_spr_970_pmu_sup(env);
7856 gen_spr_970_pmu_user(env);
7858 case BOOK3S_CPU_POWER7:
7859 case BOOK3S_CPU_POWER8:
7860 gen_spr_book3s_ids(env);
7862 gen_spr_book3s_purr(env);
7865 g_assert_not_reached();
7867 if (version >= BOOK3S_CPU_POWER5PLUS) {
7868 gen_spr_power5p_common(env);
7869 gen_spr_power5p_lpar(env);
7870 gen_spr_power5p_ear(env);
7872 gen_spr_970_lpar(env);
7874 if (version == BOOK3S_CPU_970) {
7875 gen_spr_970_dbg(env);
7877 if (version >= BOOK3S_CPU_POWER6) {
7878 gen_spr_power6_common(env);
7879 gen_spr_power6_dbg(env);
7881 if (version >= BOOK3S_CPU_POWER8) {
7882 gen_spr_power8_tce_address_control(env);
7883 gen_spr_power8_ids(env);
7884 gen_spr_power8_ebb(env);
7885 gen_spr_power8_fscr(env);
7886 gen_spr_power8_pmu_sup(env);
7887 gen_spr_power8_pmu_user(env);
7888 gen_spr_power8_tm(env);
7890 if (version < BOOK3S_CPU_POWER8) {
7891 gen_spr_book3s_dbg(env);
7893 #if !defined(CONFIG_USER_ONLY)
7895 case BOOK3S_CPU_970:
7896 case BOOK3S_CPU_POWER5PLUS:
7899 case BOOK3S_CPU_POWER7:
7900 case BOOK3S_CPU_POWER8:
7906 /* Allocate hardware IRQ controller */
7908 case BOOK3S_CPU_970:
7909 case BOOK3S_CPU_POWER5PLUS:
7911 ppc970_irq_init(env);
7913 case BOOK3S_CPU_POWER7:
7914 case BOOK3S_CPU_POWER8:
7915 init_excp_POWER7(env);
7916 ppcPOWER7_irq_init(env);
7919 g_assert_not_reached();
7922 env->dcache_line_size = 128;
7923 env->icache_line_size = 128;
7926 static void init_proc_970(CPUPPCState *env)
7928 init_proc_book3s_64(env, BOOK3S_CPU_970);
7931 POWERPC_FAMILY(970)(ObjectClass *oc, void *data)
7933 DeviceClass *dc = DEVICE_CLASS(oc);
7934 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
7936 dc->desc = "PowerPC 970";
7937 pcc->init_proc = init_proc_970;
7938 pcc->check_pow = check_pow_970;
7939 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
7940 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
7941 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
7943 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
7944 PPC_MEM_SYNC | PPC_MEM_EIEIO |
7945 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
7946 PPC_64B | PPC_ALTIVEC |
7947 PPC_SEGMENT_64B | PPC_SLBI;
7948 pcc->insns_flags2 = PPC2_FP_CVT_S64;
7949 pcc->msr_mask = (1ull << MSR_SF) |
7964 pcc->mmu_model = POWERPC_MMU_64B;
7965 #if defined(CONFIG_SOFTMMU)
7966 pcc->handle_mmu_fault = ppc_hash64_handle_mmu_fault;
7968 pcc->excp_model = POWERPC_EXCP_970;
7969 pcc->bus_model = PPC_FLAGS_INPUT_970;
7970 pcc->bfd_mach = bfd_mach_ppc64;
7971 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
7972 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
7973 POWERPC_FLAG_BUS_CLK;
7974 pcc->l1_dcache_size = 0x8000;
7975 pcc->l1_icache_size = 0x10000;
7978 static void init_proc_power5plus(CPUPPCState *env)
7980 init_proc_book3s_64(env, BOOK3S_CPU_POWER5PLUS);
7983 POWERPC_FAMILY(POWER5P)(ObjectClass *oc, void *data)
7985 DeviceClass *dc = DEVICE_CLASS(oc);
7986 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
7988 dc->fw_name = "PowerPC,POWER5";
7989 dc->desc = "POWER5+";
7990 pcc->init_proc = init_proc_power5plus;
7991 pcc->check_pow = check_pow_970;
7992 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
7993 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
7994 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
7996 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
7997 PPC_MEM_SYNC | PPC_MEM_EIEIO |
7998 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
8000 PPC_SEGMENT_64B | PPC_SLBI;
8001 pcc->insns_flags2 = PPC2_FP_CVT_S64;
8002 pcc->msr_mask = (1ull << MSR_SF) |
8017 pcc->mmu_model = POWERPC_MMU_64B;
8018 #if defined(CONFIG_SOFTMMU)
8019 pcc->handle_mmu_fault = ppc_hash64_handle_mmu_fault;
8021 pcc->excp_model = POWERPC_EXCP_970;
8022 pcc->bus_model = PPC_FLAGS_INPUT_970;
8023 pcc->bfd_mach = bfd_mach_ppc64;
8024 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
8025 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
8026 POWERPC_FLAG_BUS_CLK;
8027 pcc->l1_dcache_size = 0x8000;
8028 pcc->l1_icache_size = 0x10000;
8031 static void powerpc_get_compat(Object *obj, Visitor *v,
8032 void *opaque, const char *name, Error **errp)
8034 char *value = (char *)"";
8035 Property *prop = opaque;
8036 uint32_t *max_compat = qdev_get_prop_ptr(DEVICE(obj), prop);
8038 switch (*max_compat) {
8039 case CPU_POWERPC_LOGICAL_2_05:
8040 value = (char *)"power6";
8042 case CPU_POWERPC_LOGICAL_2_06:
8043 value = (char *)"power7";
8045 case CPU_POWERPC_LOGICAL_2_07:
8046 value = (char *)"power8";
8051 error_setg(errp, "Internal error: compat is set to %x",
8052 max_compat ? *max_compat : -1);
8056 visit_type_str(v, &value, name, errp);
8059 static void powerpc_set_compat(Object *obj, Visitor *v,
8060 void *opaque, const char *name, Error **errp)
8062 Error *error = NULL;
8064 Property *prop = opaque;
8065 uint32_t *max_compat = qdev_get_prop_ptr(DEVICE(obj), prop);
8067 visit_type_str(v, &value, name, &error);
8069 error_propagate(errp, error);
8073 if (strcmp(value, "power6") == 0) {
8074 *max_compat = CPU_POWERPC_LOGICAL_2_05;
8075 } else if (strcmp(value, "power7") == 0) {
8076 *max_compat = CPU_POWERPC_LOGICAL_2_06;
8077 } else if (strcmp(value, "power8") == 0) {
8078 *max_compat = CPU_POWERPC_LOGICAL_2_07;
8080 error_setg(errp, "Invalid compatibility mode \"%s\"", value);
8086 static PropertyInfo powerpc_compat_propinfo = {
8088 .description = "compatibility mode, power6/power7/power8",
8089 .get = powerpc_get_compat,
8090 .set = powerpc_set_compat,
8093 #define DEFINE_PROP_POWERPC_COMPAT(_n, _s, _f) \
8094 DEFINE_PROP(_n, _s, _f, powerpc_compat_propinfo, uint32_t)
8096 static Property powerpc_servercpu_properties[] = {
8097 DEFINE_PROP_POWERPC_COMPAT("compat", PowerPCCPU, max_compat),
8098 DEFINE_PROP_END_OF_LIST(),
8101 static void init_proc_POWER7 (CPUPPCState *env)
8103 init_proc_book3s_64(env, BOOK3S_CPU_POWER7);
8106 static bool ppc_pvr_match_power7(PowerPCCPUClass *pcc, uint32_t pvr)
8108 if ((pvr & CPU_POWERPC_POWER_SERVER_MASK) == CPU_POWERPC_POWER7P_BASE) {
8111 if ((pvr & CPU_POWERPC_POWER_SERVER_MASK) == CPU_POWERPC_POWER7_BASE) {
8117 POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data)
8119 DeviceClass *dc = DEVICE_CLASS(oc);
8120 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
8122 dc->fw_name = "PowerPC,POWER7";
8123 dc->desc = "POWER7";
8124 dc->props = powerpc_servercpu_properties;
8125 pcc->pvr_match = ppc_pvr_match_power7;
8126 pcc->pcr_mask = PCR_COMPAT_2_05 | PCR_COMPAT_2_06;
8127 pcc->init_proc = init_proc_POWER7;
8128 pcc->check_pow = check_pow_nocheck;
8129 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
8130 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
8131 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
8132 PPC_FLOAT_FRSQRTES |
8135 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
8136 PPC_MEM_SYNC | PPC_MEM_EIEIO |
8137 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
8138 PPC_64B | PPC_ALTIVEC |
8139 PPC_SEGMENT_64B | PPC_SLBI |
8140 PPC_POPCNTB | PPC_POPCNTWD;
8141 pcc->insns_flags2 = PPC2_VSX | PPC2_DFP | PPC2_DBRX | PPC2_ISA205 |
8142 PPC2_PERM_ISA206 | PPC2_DIVE_ISA206 |
8143 PPC2_ATOMIC_ISA206 | PPC2_FP_CVT_ISA206 |
8144 PPC2_FP_TST_ISA206 | PPC2_FP_CVT_S64;
8145 pcc->msr_mask = (1ull << MSR_SF) |
8161 pcc->mmu_model = POWERPC_MMU_2_06;
8162 #if defined(CONFIG_SOFTMMU)
8163 pcc->handle_mmu_fault = ppc_hash64_handle_mmu_fault;
8165 pcc->excp_model = POWERPC_EXCP_POWER7;
8166 pcc->bus_model = PPC_FLAGS_INPUT_POWER7;
8167 pcc->bfd_mach = bfd_mach_ppc64;
8168 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
8169 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
8170 POWERPC_FLAG_BUS_CLK | POWERPC_FLAG_CFAR |
8172 pcc->l1_dcache_size = 0x8000;
8173 pcc->l1_icache_size = 0x8000;
8174 pcc->interrupts_big_endian = ppc_cpu_interrupts_big_endian_lpcr;
8177 static void init_proc_POWER8(CPUPPCState *env)
8179 init_proc_book3s_64(env, BOOK3S_CPU_POWER8);
8182 static bool ppc_pvr_match_power8(PowerPCCPUClass *pcc, uint32_t pvr)
8184 if ((pvr & CPU_POWERPC_POWER_SERVER_MASK) == CPU_POWERPC_POWER8E_BASE) {
8187 if ((pvr & CPU_POWERPC_POWER_SERVER_MASK) == CPU_POWERPC_POWER8_BASE) {
8193 POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data)
8195 DeviceClass *dc = DEVICE_CLASS(oc);
8196 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
8198 dc->fw_name = "PowerPC,POWER8";
8199 dc->desc = "POWER8";
8200 dc->props = powerpc_servercpu_properties;
8201 pcc->pvr_match = ppc_pvr_match_power8;
8202 pcc->pcr_mask = PCR_COMPAT_2_05 | PCR_COMPAT_2_06;
8203 pcc->init_proc = init_proc_POWER8;
8204 pcc->check_pow = check_pow_nocheck;
8205 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
8206 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
8207 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
8208 PPC_FLOAT_FRSQRTES |
8211 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
8212 PPC_MEM_SYNC | PPC_MEM_EIEIO |
8213 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
8214 PPC_64B | PPC_64BX | PPC_ALTIVEC |
8215 PPC_SEGMENT_64B | PPC_SLBI |
8216 PPC_POPCNTB | PPC_POPCNTWD;
8217 pcc->insns_flags2 = PPC2_VSX | PPC2_VSX207 | PPC2_DFP | PPC2_DBRX |
8218 PPC2_PERM_ISA206 | PPC2_DIVE_ISA206 |
8219 PPC2_ATOMIC_ISA206 | PPC2_FP_CVT_ISA206 |
8220 PPC2_FP_TST_ISA206 | PPC2_BCTAR_ISA207 |
8221 PPC2_LSQ_ISA207 | PPC2_ALTIVEC_207 |
8222 PPC2_ISA205 | PPC2_ISA207S | PPC2_FP_CVT_S64;
8223 pcc->msr_mask = (1ull << MSR_SF) |
8240 pcc->mmu_model = POWERPC_MMU_2_06;
8241 #if defined(CONFIG_SOFTMMU)
8242 pcc->handle_mmu_fault = ppc_hash64_handle_mmu_fault;
8244 pcc->excp_model = POWERPC_EXCP_POWER7;
8245 pcc->bus_model = PPC_FLAGS_INPUT_POWER7;
8246 pcc->bfd_mach = bfd_mach_ppc64;
8247 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
8248 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
8249 POWERPC_FLAG_BUS_CLK | POWERPC_FLAG_CFAR |
8251 pcc->l1_dcache_size = 0x8000;
8252 pcc->l1_icache_size = 0x8000;
8253 pcc->interrupts_big_endian = ppc_cpu_interrupts_big_endian_lpcr;
8255 #endif /* defined (TARGET_PPC64) */
8258 /*****************************************************************************/
8259 /* Generic CPU instantiation routine */
8260 static void init_ppc_proc(PowerPCCPU *cpu)
8262 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
8263 CPUPPCState *env = &cpu->env;
8264 #if !defined(CONFIG_USER_ONLY)
8267 env->irq_inputs = NULL;
8268 /* Set all exception vectors to an invalid address */
8269 for (i = 0; i < POWERPC_EXCP_NB; i++)
8270 env->excp_vectors[i] = (target_ulong)(-1ULL);
8271 env->ivor_mask = 0x00000000;
8272 env->ivpr_mask = 0x00000000;
8273 /* Default MMU definitions */
8277 env->tlb_type = TLB_NONE;
8279 /* Register SPR common to all PowerPC implementations */
8280 gen_spr_generic(env);
8281 spr_register(env, SPR_PVR, "PVR",
8282 /* Linux permits userspace to read PVR */
8283 #if defined(CONFIG_LINUX_USER)
8289 &spr_read_generic, SPR_NOACCESS,
8291 /* Register SVR if it's defined to anything else than POWERPC_SVR_NONE */
8292 if (pcc->svr != POWERPC_SVR_NONE) {
8293 if (pcc->svr & POWERPC_SVR_E500) {
8294 spr_register(env, SPR_E500_SVR, "SVR",
8295 SPR_NOACCESS, SPR_NOACCESS,
8296 &spr_read_generic, SPR_NOACCESS,
8297 pcc->svr & ~POWERPC_SVR_E500);
8299 spr_register(env, SPR_SVR, "SVR",
8300 SPR_NOACCESS, SPR_NOACCESS,
8301 &spr_read_generic, SPR_NOACCESS,
8305 /* PowerPC implementation specific initialisations (SPRs, timers, ...) */
8306 (*pcc->init_proc)(env);
8308 /* MSR bits & flags consistency checks */
8309 if (env->msr_mask & (1 << 25)) {
8310 switch (env->flags & (POWERPC_FLAG_SPE | POWERPC_FLAG_VRE)) {
8311 case POWERPC_FLAG_SPE:
8312 case POWERPC_FLAG_VRE:
8315 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8316 "Should define POWERPC_FLAG_SPE or POWERPC_FLAG_VRE\n");
8319 } else if (env->flags & (POWERPC_FLAG_SPE | POWERPC_FLAG_VRE)) {
8320 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8321 "Should not define POWERPC_FLAG_SPE nor POWERPC_FLAG_VRE\n");
8324 if (env->msr_mask & (1 << 17)) {
8325 switch (env->flags & (POWERPC_FLAG_TGPR | POWERPC_FLAG_CE)) {
8326 case POWERPC_FLAG_TGPR:
8327 case POWERPC_FLAG_CE:
8330 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8331 "Should define POWERPC_FLAG_TGPR or POWERPC_FLAG_CE\n");
8334 } else if (env->flags & (POWERPC_FLAG_TGPR | POWERPC_FLAG_CE)) {
8335 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8336 "Should not define POWERPC_FLAG_TGPR nor POWERPC_FLAG_CE\n");
8339 if (env->msr_mask & (1 << 10)) {
8340 switch (env->flags & (POWERPC_FLAG_SE | POWERPC_FLAG_DWE |
8341 POWERPC_FLAG_UBLE)) {
8342 case POWERPC_FLAG_SE:
8343 case POWERPC_FLAG_DWE:
8344 case POWERPC_FLAG_UBLE:
8347 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8348 "Should define POWERPC_FLAG_SE or POWERPC_FLAG_DWE or "
8349 "POWERPC_FLAG_UBLE\n");
8352 } else if (env->flags & (POWERPC_FLAG_SE | POWERPC_FLAG_DWE |
8353 POWERPC_FLAG_UBLE)) {
8354 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8355 "Should not define POWERPC_FLAG_SE nor POWERPC_FLAG_DWE nor "
8356 "POWERPC_FLAG_UBLE\n");
8359 if (env->msr_mask & (1 << 9)) {
8360 switch (env->flags & (POWERPC_FLAG_BE | POWERPC_FLAG_DE)) {
8361 case POWERPC_FLAG_BE:
8362 case POWERPC_FLAG_DE:
8365 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8366 "Should define POWERPC_FLAG_BE or POWERPC_FLAG_DE\n");
8369 } else if (env->flags & (POWERPC_FLAG_BE | POWERPC_FLAG_DE)) {
8370 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8371 "Should not define POWERPC_FLAG_BE nor POWERPC_FLAG_DE\n");
8374 if (env->msr_mask & (1 << 2)) {
8375 switch (env->flags & (POWERPC_FLAG_PX | POWERPC_FLAG_PMM)) {
8376 case POWERPC_FLAG_PX:
8377 case POWERPC_FLAG_PMM:
8380 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8381 "Should define POWERPC_FLAG_PX or POWERPC_FLAG_PMM\n");
8384 } else if (env->flags & (POWERPC_FLAG_PX | POWERPC_FLAG_PMM)) {
8385 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8386 "Should not define POWERPC_FLAG_PX nor POWERPC_FLAG_PMM\n");
8389 if ((env->flags & (POWERPC_FLAG_RTC_CLK | POWERPC_FLAG_BUS_CLK)) == 0) {
8390 fprintf(stderr, "PowerPC flags inconsistency\n"
8391 "Should define the time-base and decrementer clock source\n");
8394 /* Allocate TLBs buffer when needed */
8395 #if !defined(CONFIG_USER_ONLY)
8396 if (env->nb_tlb != 0) {
8397 int nb_tlb = env->nb_tlb;
8398 if (env->id_tlbs != 0)
8400 switch (env->tlb_type) {
8402 env->tlb.tlb6 = g_malloc0(nb_tlb * sizeof(ppc6xx_tlb_t));
8405 env->tlb.tlbe = g_malloc0(nb_tlb * sizeof(ppcemb_tlb_t));
8408 env->tlb.tlbm = g_malloc0(nb_tlb * sizeof(ppcmas_tlb_t));
8411 /* Pre-compute some useful values */
8412 env->tlb_per_way = env->nb_tlb / env->nb_ways;
8414 if (env->irq_inputs == NULL) {
8415 fprintf(stderr, "WARNING: no internal IRQ controller registered.\n"
8416 " Attempt QEMU to crash very soon !\n");
8419 if (env->check_pow == NULL) {
8420 fprintf(stderr, "WARNING: no power management check handler "
8422 " Attempt QEMU to crash very soon !\n");
8426 #if defined(PPC_DUMP_CPU)
8427 static void dump_ppc_sprs (CPUPPCState *env)
8430 #if !defined(CONFIG_USER_ONLY)
8436 printf("Special purpose registers:\n");
8437 for (i = 0; i < 32; i++) {
8438 for (j = 0; j < 32; j++) {
8440 spr = &env->spr_cb[n];
8441 uw = spr->uea_write != NULL && spr->uea_write != SPR_NOACCESS;
8442 ur = spr->uea_read != NULL && spr->uea_read != SPR_NOACCESS;
8443 #if !defined(CONFIG_USER_ONLY)
8444 sw = spr->oea_write != NULL && spr->oea_write != SPR_NOACCESS;
8445 sr = spr->oea_read != NULL && spr->oea_read != SPR_NOACCESS;
8446 if (sw || sr || uw || ur) {
8447 printf("SPR: %4d (%03x) %-8s s%c%c u%c%c\n",
8448 (i << 5) | j, (i << 5) | j, spr->name,
8449 sw ? 'w' : '-', sr ? 'r' : '-',
8450 uw ? 'w' : '-', ur ? 'r' : '-');
8454 printf("SPR: %4d (%03x) %-8s u%c%c\n",
8455 (i << 5) | j, (i << 5) | j, spr->name,
8456 uw ? 'w' : '-', ur ? 'r' : '-');
8466 /*****************************************************************************/
8472 PPC_DIRECT = 0, /* Opcode routine */
8473 PPC_INDIRECT = 1, /* Indirect opcode table */
8476 #define PPC_OPCODE_MASK 0x3
8478 static inline int is_indirect_opcode (void *handler)
8480 return ((uintptr_t)handler & PPC_OPCODE_MASK) == PPC_INDIRECT;
8483 static inline opc_handler_t **ind_table(void *handler)
8485 return (opc_handler_t **)((uintptr_t)handler & ~PPC_OPCODE_MASK);
8488 /* Instruction table creation */
8489 /* Opcodes tables creation */
8490 static void fill_new_table (opc_handler_t **table, int len)
8494 for (i = 0; i < len; i++)
8495 table[i] = &invalid_handler;
8498 static int create_new_table (opc_handler_t **table, unsigned char idx)
8500 opc_handler_t **tmp;
8502 tmp = g_new(opc_handler_t *, PPC_CPU_INDIRECT_OPCODES_LEN);
8503 fill_new_table(tmp, PPC_CPU_INDIRECT_OPCODES_LEN);
8504 table[idx] = (opc_handler_t *)((uintptr_t)tmp | PPC_INDIRECT);
8509 static int insert_in_table (opc_handler_t **table, unsigned char idx,
8510 opc_handler_t *handler)
8512 if (table[idx] != &invalid_handler)
8514 table[idx] = handler;
8519 static int register_direct_insn (opc_handler_t **ppc_opcodes,
8520 unsigned char idx, opc_handler_t *handler)
8522 if (insert_in_table(ppc_opcodes, idx, handler) < 0) {
8523 printf("*** ERROR: opcode %02x already assigned in main "
8524 "opcode table\n", idx);
8525 #if defined(DO_PPC_STATISTICS) || defined(PPC_DUMP_CPU)
8526 printf(" Registered handler '%s' - new handler '%s'\n",
8527 ppc_opcodes[idx]->oname, handler->oname);
8535 static int register_ind_in_table (opc_handler_t **table,
8536 unsigned char idx1, unsigned char idx2,
8537 opc_handler_t *handler)
8539 if (table[idx1] == &invalid_handler) {
8540 if (create_new_table(table, idx1) < 0) {
8541 printf("*** ERROR: unable to create indirect table "
8542 "idx=%02x\n", idx1);
8546 if (!is_indirect_opcode(table[idx1])) {
8547 printf("*** ERROR: idx %02x already assigned to a direct "
8549 #if defined(DO_PPC_STATISTICS) || defined(PPC_DUMP_CPU)
8550 printf(" Registered handler '%s' - new handler '%s'\n",
8551 ind_table(table[idx1])[idx2]->oname, handler->oname);
8556 if (handler != NULL &&
8557 insert_in_table(ind_table(table[idx1]), idx2, handler) < 0) {
8558 printf("*** ERROR: opcode %02x already assigned in "
8559 "opcode table %02x\n", idx2, idx1);
8560 #if defined(DO_PPC_STATISTICS) || defined(PPC_DUMP_CPU)
8561 printf(" Registered handler '%s' - new handler '%s'\n",
8562 ind_table(table[idx1])[idx2]->oname, handler->oname);
8570 static int register_ind_insn (opc_handler_t **ppc_opcodes,
8571 unsigned char idx1, unsigned char idx2,
8572 opc_handler_t *handler)
8576 ret = register_ind_in_table(ppc_opcodes, idx1, idx2, handler);
8581 static int register_dblind_insn (opc_handler_t **ppc_opcodes,
8582 unsigned char idx1, unsigned char idx2,
8583 unsigned char idx3, opc_handler_t *handler)
8585 if (register_ind_in_table(ppc_opcodes, idx1, idx2, NULL) < 0) {
8586 printf("*** ERROR: unable to join indirect table idx "
8587 "[%02x-%02x]\n", idx1, idx2);
8590 if (register_ind_in_table(ind_table(ppc_opcodes[idx1]), idx2, idx3,
8592 printf("*** ERROR: unable to insert opcode "
8593 "[%02x-%02x-%02x]\n", idx1, idx2, idx3);
8600 static int register_insn (opc_handler_t **ppc_opcodes, opcode_t *insn)
8602 if (insn->opc2 != 0xFF) {
8603 if (insn->opc3 != 0xFF) {
8604 if (register_dblind_insn(ppc_opcodes, insn->opc1, insn->opc2,
8605 insn->opc3, &insn->handler) < 0)
8608 if (register_ind_insn(ppc_opcodes, insn->opc1,
8609 insn->opc2, &insn->handler) < 0)
8613 if (register_direct_insn(ppc_opcodes, insn->opc1, &insn->handler) < 0)
8620 static int test_opcode_table (opc_handler_t **table, int len)
8624 for (i = 0, count = 0; i < len; i++) {
8625 /* Consistency fixup */
8626 if (table[i] == NULL)
8627 table[i] = &invalid_handler;
8628 if (table[i] != &invalid_handler) {
8629 if (is_indirect_opcode(table[i])) {
8630 tmp = test_opcode_table(ind_table(table[i]),
8631 PPC_CPU_INDIRECT_OPCODES_LEN);
8634 table[i] = &invalid_handler;
8647 static void fix_opcode_tables (opc_handler_t **ppc_opcodes)
8649 if (test_opcode_table(ppc_opcodes, PPC_CPU_OPCODES_LEN) == 0)
8650 printf("*** WARNING: no opcode defined !\n");
8653 /*****************************************************************************/
8654 static void create_ppc_opcodes(PowerPCCPU *cpu, Error **errp)
8656 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
8657 CPUPPCState *env = &cpu->env;
8660 fill_new_table(env->opcodes, PPC_CPU_OPCODES_LEN);
8661 for (opc = opcodes; opc < &opcodes[ARRAY_SIZE(opcodes)]; opc++) {
8662 if (((opc->handler.type & pcc->insns_flags) != 0) ||
8663 ((opc->handler.type2 & pcc->insns_flags2) != 0)) {
8664 if (register_insn(env->opcodes, opc) < 0) {
8665 error_setg(errp, "ERROR initializing PowerPC instruction "
8666 "0x%02x 0x%02x 0x%02x", opc->opc1, opc->opc2,
8672 fix_opcode_tables(env->opcodes);
8677 #if defined(PPC_DUMP_CPU)
8678 static void dump_ppc_insns (CPUPPCState *env)
8680 opc_handler_t **table, *handler;
8682 uint8_t opc1, opc2, opc3;
8684 printf("Instructions set:\n");
8685 /* opc1 is 6 bits long */
8686 for (opc1 = 0x00; opc1 < PPC_CPU_OPCODES_LEN; opc1++) {
8687 table = env->opcodes;
8688 handler = table[opc1];
8689 if (is_indirect_opcode(handler)) {
8690 /* opc2 is 5 bits long */
8691 for (opc2 = 0; opc2 < PPC_CPU_INDIRECT_OPCODES_LEN; opc2++) {
8692 table = env->opcodes;
8693 handler = env->opcodes[opc1];
8694 table = ind_table(handler);
8695 handler = table[opc2];
8696 if (is_indirect_opcode(handler)) {
8697 table = ind_table(handler);
8698 /* opc3 is 5 bits long */
8699 for (opc3 = 0; opc3 < PPC_CPU_INDIRECT_OPCODES_LEN;
8701 handler = table[opc3];
8702 if (handler->handler != &gen_invalid) {
8703 /* Special hack to properly dump SPE insns */
8704 p = strchr(handler->oname, '_');
8706 printf("INSN: %02x %02x %02x (%02d %04d) : "
8708 opc1, opc2, opc3, opc1,
8713 if ((p - handler->oname) != strlen(q) ||
8714 memcmp(handler->oname, q, strlen(q)) != 0) {
8715 /* First instruction */
8716 printf("INSN: %02x %02x %02x (%02d %04d) : "
8718 opc1, opc2 << 1, opc3, opc1,
8719 (opc3 << 6) | (opc2 << 1),
8720 (int)(p - handler->oname),
8723 if (strcmp(p + 1, q) != 0) {
8724 /* Second instruction */
8725 printf("INSN: %02x %02x %02x (%02d %04d) : "
8727 opc1, (opc2 << 1) | 1, opc3, opc1,
8728 (opc3 << 6) | (opc2 << 1) | 1,
8735 if (handler->handler != &gen_invalid) {
8736 printf("INSN: %02x %02x -- (%02d %04d) : %s\n",
8737 opc1, opc2, opc1, opc2, handler->oname);
8742 if (handler->handler != &gen_invalid) {
8743 printf("INSN: %02x -- -- (%02d ----) : %s\n",
8744 opc1, opc1, handler->oname);
8751 static int gdb_get_float_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
8754 stfq_p(mem_buf, env->fpr[n]);
8758 stl_p(mem_buf, env->fpscr);
8764 static int gdb_set_float_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
8767 env->fpr[n] = ldfq_p(mem_buf);
8771 helper_store_fpscr(env, ldl_p(mem_buf), 0xffffffff);
8777 static int gdb_get_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
8780 #ifdef HOST_WORDS_BIGENDIAN
8781 stq_p(mem_buf, env->avr[n].u64[0]);
8782 stq_p(mem_buf+8, env->avr[n].u64[1]);
8784 stq_p(mem_buf, env->avr[n].u64[1]);
8785 stq_p(mem_buf+8, env->avr[n].u64[0]);
8790 stl_p(mem_buf, env->vscr);
8794 stl_p(mem_buf, (uint32_t)env->spr[SPR_VRSAVE]);
8800 static int gdb_set_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
8803 #ifdef HOST_WORDS_BIGENDIAN
8804 env->avr[n].u64[0] = ldq_p(mem_buf);
8805 env->avr[n].u64[1] = ldq_p(mem_buf+8);
8807 env->avr[n].u64[1] = ldq_p(mem_buf);
8808 env->avr[n].u64[0] = ldq_p(mem_buf+8);
8813 env->vscr = ldl_p(mem_buf);
8817 env->spr[SPR_VRSAVE] = (target_ulong)ldl_p(mem_buf);
8823 static int gdb_get_spe_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
8826 #if defined(TARGET_PPC64)
8827 stl_p(mem_buf, env->gpr[n] >> 32);
8829 stl_p(mem_buf, env->gprh[n]);
8834 stq_p(mem_buf, env->spe_acc);
8838 stl_p(mem_buf, env->spe_fscr);
8844 static int gdb_set_spe_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
8847 #if defined(TARGET_PPC64)
8848 target_ulong lo = (uint32_t)env->gpr[n];
8849 target_ulong hi = (target_ulong)ldl_p(mem_buf) << 32;
8850 env->gpr[n] = lo | hi;
8852 env->gprh[n] = ldl_p(mem_buf);
8857 env->spe_acc = ldq_p(mem_buf);
8861 env->spe_fscr = ldl_p(mem_buf);
8867 static int ppc_fixup_cpu(PowerPCCPU *cpu)
8869 CPUPPCState *env = &cpu->env;
8871 /* TCG doesn't (yet) emulate some groups of instructions that
8872 * are implemented on some otherwise supported CPUs (e.g. VSX
8873 * and decimal floating point instructions on POWER7). We
8874 * remove unsupported instruction groups from the cpu state's
8875 * instruction masks and hope the guest can cope. For at
8876 * least the pseries machine, the unavailability of these
8877 * instructions can be advertised to the guest via the device
8879 if ((env->insns_flags & ~PPC_TCG_INSNS)
8880 || (env->insns_flags2 & ~PPC_TCG_INSNS2)) {
8881 fprintf(stderr, "Warning: Disabling some instructions which are not "
8882 "emulated by TCG (0x%" PRIx64 ", 0x%" PRIx64 ")\n",
8883 env->insns_flags & ~PPC_TCG_INSNS,
8884 env->insns_flags2 & ~PPC_TCG_INSNS2);
8886 env->insns_flags &= PPC_TCG_INSNS;
8887 env->insns_flags2 &= PPC_TCG_INSNS2;
8891 static inline bool ppc_cpu_is_valid(PowerPCCPUClass *pcc)
8893 #ifdef TARGET_PPCEMB
8894 return pcc->mmu_model == POWERPC_MMU_BOOKE ||
8895 pcc->mmu_model == POWERPC_MMU_SOFT_4xx ||
8896 pcc->mmu_model == POWERPC_MMU_SOFT_4xx_Z;
8902 static void ppc_cpu_realizefn(DeviceState *dev, Error **errp)
8904 CPUState *cs = CPU(dev);
8905 PowerPCCPU *cpu = POWERPC_CPU(dev);
8906 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
8907 Error *local_err = NULL;
8908 #if !defined(CONFIG_USER_ONLY)
8909 int max_smt = kvm_enabled() ? kvmppc_smt_threads() : 1;
8912 #if !defined(CONFIG_USER_ONLY)
8913 if (smp_threads > max_smt) {
8914 error_setg(errp, "Cannot support more than %d threads on PPC with %s",
8915 max_smt, kvm_enabled() ? "KVM" : "TCG");
8918 if (!is_power_of_2(smp_threads)) {
8919 error_setg(errp, "Cannot support %d threads on PPC with %s, "
8920 "threads count must be a power of 2.",
8921 smp_threads, kvm_enabled() ? "KVM" : "TCG");
8925 cpu->cpu_dt_id = (cs->cpu_index / smp_threads) * max_smt
8926 + (cs->cpu_index % smp_threads);
8929 if (tcg_enabled()) {
8930 if (ppc_fixup_cpu(cpu) != 0) {
8931 error_setg(errp, "Unable to emulate selected CPU with TCG");
8936 #if defined(TARGET_PPCEMB)
8937 if (!ppc_cpu_is_valid(pcc)) {
8938 error_setg(errp, "CPU does not possess a BookE or 4xx MMU. "
8939 "Please use qemu-system-ppc or qemu-system-ppc64 instead "
8940 "or choose another CPU model.");
8945 create_ppc_opcodes(cpu, &local_err);
8946 if (local_err != NULL) {
8947 error_propagate(errp, local_err);
8952 if (pcc->insns_flags & PPC_FLOAT) {
8953 gdb_register_coprocessor(cs, gdb_get_float_reg, gdb_set_float_reg,
8954 33, "power-fpu.xml", 0);
8956 if (pcc->insns_flags & PPC_ALTIVEC) {
8957 gdb_register_coprocessor(cs, gdb_get_avr_reg, gdb_set_avr_reg,
8958 34, "power-altivec.xml", 0);
8960 if (pcc->insns_flags & PPC_SPE) {
8961 gdb_register_coprocessor(cs, gdb_get_spe_reg, gdb_set_spe_reg,
8962 34, "power-spe.xml", 0);
8967 pcc->parent_realize(dev, errp);
8969 #if defined(PPC_DUMP_CPU)
8971 CPUPPCState *env = &cpu->env;
8972 const char *mmu_model, *excp_model, *bus_model;
8973 switch (env->mmu_model) {
8974 case POWERPC_MMU_32B:
8975 mmu_model = "PowerPC 32";
8977 case POWERPC_MMU_SOFT_6xx:
8978 mmu_model = "PowerPC 6xx/7xx with software driven TLBs";
8980 case POWERPC_MMU_SOFT_74xx:
8981 mmu_model = "PowerPC 74xx with software driven TLBs";
8983 case POWERPC_MMU_SOFT_4xx:
8984 mmu_model = "PowerPC 4xx with software driven TLBs";
8986 case POWERPC_MMU_SOFT_4xx_Z:
8987 mmu_model = "PowerPC 4xx with software driven TLBs "
8988 "and zones protections";
8990 case POWERPC_MMU_REAL:
8991 mmu_model = "PowerPC real mode only";
8993 case POWERPC_MMU_MPC8xx:
8994 mmu_model = "PowerPC MPC8xx";
8996 case POWERPC_MMU_BOOKE:
8997 mmu_model = "PowerPC BookE";
8999 case POWERPC_MMU_BOOKE206:
9000 mmu_model = "PowerPC BookE 2.06";
9002 case POWERPC_MMU_601:
9003 mmu_model = "PowerPC 601";
9005 #if defined (TARGET_PPC64)
9006 case POWERPC_MMU_64B:
9007 mmu_model = "PowerPC 64";
9011 mmu_model = "Unknown or invalid";
9014 switch (env->excp_model) {
9015 case POWERPC_EXCP_STD:
9016 excp_model = "PowerPC";
9018 case POWERPC_EXCP_40x:
9019 excp_model = "PowerPC 40x";
9021 case POWERPC_EXCP_601:
9022 excp_model = "PowerPC 601";
9024 case POWERPC_EXCP_602:
9025 excp_model = "PowerPC 602";
9027 case POWERPC_EXCP_603:
9028 excp_model = "PowerPC 603";
9030 case POWERPC_EXCP_603E:
9031 excp_model = "PowerPC 603e";
9033 case POWERPC_EXCP_604:
9034 excp_model = "PowerPC 604";
9036 case POWERPC_EXCP_7x0:
9037 excp_model = "PowerPC 740/750";
9039 case POWERPC_EXCP_7x5:
9040 excp_model = "PowerPC 745/755";
9042 case POWERPC_EXCP_74xx:
9043 excp_model = "PowerPC 74xx";
9045 case POWERPC_EXCP_BOOKE:
9046 excp_model = "PowerPC BookE";
9048 #if defined (TARGET_PPC64)
9049 case POWERPC_EXCP_970:
9050 excp_model = "PowerPC 970";
9054 excp_model = "Unknown or invalid";
9057 switch (env->bus_model) {
9058 case PPC_FLAGS_INPUT_6xx:
9059 bus_model = "PowerPC 6xx";
9061 case PPC_FLAGS_INPUT_BookE:
9062 bus_model = "PowerPC BookE";
9064 case PPC_FLAGS_INPUT_405:
9065 bus_model = "PowerPC 405";
9067 case PPC_FLAGS_INPUT_401:
9068 bus_model = "PowerPC 401/403";
9070 case PPC_FLAGS_INPUT_RCPU:
9071 bus_model = "RCPU / MPC8xx";
9073 #if defined (TARGET_PPC64)
9074 case PPC_FLAGS_INPUT_970:
9075 bus_model = "PowerPC 970";
9079 bus_model = "Unknown or invalid";
9082 printf("PowerPC %-12s : PVR %08x MSR %016" PRIx64 "\n"
9083 " MMU model : %s\n",
9084 object_class_get_name(OBJECT_CLASS(pcc)),
9085 pcc->pvr, pcc->msr_mask, mmu_model);
9086 #if !defined(CONFIG_USER_ONLY)
9087 if (env->tlb.tlb6) {
9088 printf(" %d %s TLB in %d ways\n",
9089 env->nb_tlb, env->id_tlbs ? "splitted" : "merged",
9093 printf(" Exceptions model : %s\n"
9094 " Bus model : %s\n",
9095 excp_model, bus_model);
9096 printf(" MSR features :\n");
9097 if (env->flags & POWERPC_FLAG_SPE)
9098 printf(" signal processing engine enable"
9100 else if (env->flags & POWERPC_FLAG_VRE)
9101 printf(" vector processor enable\n");
9102 if (env->flags & POWERPC_FLAG_TGPR)
9103 printf(" temporary GPRs\n");
9104 else if (env->flags & POWERPC_FLAG_CE)
9105 printf(" critical input enable\n");
9106 if (env->flags & POWERPC_FLAG_SE)
9107 printf(" single-step trace mode\n");
9108 else if (env->flags & POWERPC_FLAG_DWE)
9109 printf(" debug wait enable\n");
9110 else if (env->flags & POWERPC_FLAG_UBLE)
9111 printf(" user BTB lock enable\n");
9112 if (env->flags & POWERPC_FLAG_BE)
9113 printf(" branch-step trace mode\n");
9114 else if (env->flags & POWERPC_FLAG_DE)
9115 printf(" debug interrupt enable\n");
9116 if (env->flags & POWERPC_FLAG_PX)
9117 printf(" inclusive protection\n");
9118 else if (env->flags & POWERPC_FLAG_PMM)
9119 printf(" performance monitor mark\n");
9120 if (env->flags == POWERPC_FLAG_NONE)
9122 printf(" Time-base/decrementer clock source: %s\n",
9123 env->flags & POWERPC_FLAG_RTC_CLK ? "RTC clock" : "bus clock");
9124 dump_ppc_insns(env);
9131 static void ppc_cpu_unrealizefn(DeviceState *dev, Error **errp)
9133 PowerPCCPU *cpu = POWERPC_CPU(dev);
9134 CPUPPCState *env = &cpu->env;
9135 opc_handler_t **table;
9138 for (i = 0; i < PPC_CPU_OPCODES_LEN; i++) {
9139 if (env->opcodes[i] == &invalid_handler) {
9142 if (is_indirect_opcode(env->opcodes[i])) {
9143 table = ind_table(env->opcodes[i]);
9144 for (j = 0; j < PPC_CPU_INDIRECT_OPCODES_LEN; j++) {
9145 if (table[j] != &invalid_handler &&
9146 is_indirect_opcode(table[j])) {
9147 g_free((opc_handler_t *)((uintptr_t)table[j] &
9151 g_free((opc_handler_t *)((uintptr_t)env->opcodes[i] &
9157 int ppc_get_compat_smt_threads(PowerPCCPU *cpu)
9159 int ret = MIN(smp_threads, kvmppc_smt_threads());
9161 switch (cpu->cpu_version) {
9162 case CPU_POWERPC_LOGICAL_2_05:
9165 case CPU_POWERPC_LOGICAL_2_06:
9168 case CPU_POWERPC_LOGICAL_2_07:
9176 int ppc_set_compat(PowerPCCPU *cpu, uint32_t cpu_version)
9179 CPUPPCState *env = &cpu->env;
9181 cpu->cpu_version = cpu_version;
9183 switch (cpu_version) {
9184 case CPU_POWERPC_LOGICAL_2_05:
9185 env->spr[SPR_PCR] = PCR_COMPAT_2_05;
9187 case CPU_POWERPC_LOGICAL_2_06:
9188 env->spr[SPR_PCR] = PCR_COMPAT_2_06;
9190 case CPU_POWERPC_LOGICAL_2_06_PLUS:
9191 env->spr[SPR_PCR] = PCR_COMPAT_2_06;
9194 env->spr[SPR_PCR] = 0;
9198 if (kvm_enabled() && kvmppc_set_compat(cpu, cpu->cpu_version) < 0) {
9199 error_report("Unable to set compatibility mode in KVM");
9206 static gint ppc_cpu_compare_class_pvr(gconstpointer a, gconstpointer b)
9208 ObjectClass *oc = (ObjectClass *)a;
9209 uint32_t pvr = *(uint32_t *)b;
9210 PowerPCCPUClass *pcc = (PowerPCCPUClass *)a;
9212 /* -cpu host does a PVR lookup during construction */
9213 if (unlikely(strcmp(object_class_get_name(oc),
9214 TYPE_HOST_POWERPC_CPU) == 0)) {
9218 if (!ppc_cpu_is_valid(pcc)) {
9222 return pcc->pvr == pvr ? 0 : -1;
9225 PowerPCCPUClass *ppc_cpu_class_by_pvr(uint32_t pvr)
9227 GSList *list, *item;
9228 PowerPCCPUClass *pcc = NULL;
9230 list = object_class_get_list(TYPE_POWERPC_CPU, false);
9231 item = g_slist_find_custom(list, &pvr, ppc_cpu_compare_class_pvr);
9233 pcc = POWERPC_CPU_CLASS(item->data);
9240 static gint ppc_cpu_compare_class_pvr_mask(gconstpointer a, gconstpointer b)
9242 ObjectClass *oc = (ObjectClass *)a;
9243 uint32_t pvr = *(uint32_t *)b;
9244 PowerPCCPUClass *pcc = (PowerPCCPUClass *)a;
9246 /* -cpu host does a PVR lookup during construction */
9247 if (unlikely(strcmp(object_class_get_name(oc),
9248 TYPE_HOST_POWERPC_CPU) == 0)) {
9252 if (!ppc_cpu_is_valid(pcc)) {
9256 if (pcc->pvr_match(pcc, pvr)) {
9263 PowerPCCPUClass *ppc_cpu_class_by_pvr_mask(uint32_t pvr)
9265 GSList *list, *item;
9266 PowerPCCPUClass *pcc = NULL;
9268 list = object_class_get_list(TYPE_POWERPC_CPU, true);
9269 item = g_slist_find_custom(list, &pvr, ppc_cpu_compare_class_pvr_mask);
9271 pcc = POWERPC_CPU_CLASS(item->data);
9278 static gint ppc_cpu_compare_class_name(gconstpointer a, gconstpointer b)
9280 ObjectClass *oc = (ObjectClass *)a;
9281 const char *name = b;
9282 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
9284 if (strncasecmp(name, object_class_get_name(oc), strlen(name)) == 0 &&
9285 ppc_cpu_is_valid(pcc) &&
9286 strcmp(object_class_get_name(oc) + strlen(name),
9287 "-" TYPE_POWERPC_CPU) == 0) {
9295 static ObjectClass *ppc_cpu_class_by_name(const char *name);
9297 static ObjectClass *ppc_cpu_class_by_alias(PowerPCCPUAlias *alias)
9299 ObjectClass *invalid_class = (void*)ppc_cpu_class_by_alias;
9301 /* Cache target class lookups in the alias table */
9303 alias->oc = ppc_cpu_class_by_name(alias->model);
9305 /* Fast check for non-existing aliases */
9306 alias->oc = invalid_class;
9310 if (alias->oc == invalid_class) {
9317 static ObjectClass *ppc_cpu_class_by_name(const char *name)
9319 GSList *list, *item;
9320 ObjectClass *ret = NULL;
9324 /* Check if the given name is a PVR */
9326 if (len == 10 && name[0] == '0' && name[1] == 'x') {
9329 } else if (len == 8) {
9332 for (i = 0; i < 8; i++) {
9333 if (!qemu_isxdigit(*p++))
9337 ret = OBJECT_CLASS(ppc_cpu_class_by_pvr(strtoul(name, NULL, 16)));
9342 list = object_class_get_list(TYPE_POWERPC_CPU, false);
9343 item = g_slist_find_custom(list, name, ppc_cpu_compare_class_name);
9345 ret = OBJECT_CLASS(item->data);
9353 for (i = 0; ppc_cpu_aliases[i].alias != NULL; i++) {
9354 if (strcmp(ppc_cpu_aliases[i].alias, name) == 0) {
9355 return ppc_cpu_class_by_alias(&ppc_cpu_aliases[i]);
9362 PowerPCCPU *cpu_ppc_init(const char *cpu_model)
9364 return POWERPC_CPU(cpu_generic_init(TYPE_POWERPC_CPU, cpu_model));
9367 /* Sort by PVR, ordering special case "host" last. */
9368 static gint ppc_cpu_list_compare(gconstpointer a, gconstpointer b)
9370 ObjectClass *oc_a = (ObjectClass *)a;
9371 ObjectClass *oc_b = (ObjectClass *)b;
9372 PowerPCCPUClass *pcc_a = POWERPC_CPU_CLASS(oc_a);
9373 PowerPCCPUClass *pcc_b = POWERPC_CPU_CLASS(oc_b);
9374 const char *name_a = object_class_get_name(oc_a);
9375 const char *name_b = object_class_get_name(oc_b);
9377 if (strcmp(name_a, TYPE_HOST_POWERPC_CPU) == 0) {
9379 } else if (strcmp(name_b, TYPE_HOST_POWERPC_CPU) == 0) {
9382 /* Avoid an integer overflow during subtraction */
9383 if (pcc_a->pvr < pcc_b->pvr) {
9385 } else if (pcc_a->pvr > pcc_b->pvr) {
9393 static void ppc_cpu_list_entry(gpointer data, gpointer user_data)
9395 ObjectClass *oc = data;
9396 CPUListState *s = user_data;
9397 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
9398 const char *typename = object_class_get_name(oc);
9402 if (!ppc_cpu_is_valid(pcc)) {
9405 if (unlikely(strcmp(typename, TYPE_HOST_POWERPC_CPU) == 0)) {
9409 name = g_strndup(typename,
9410 strlen(typename) - strlen("-" TYPE_POWERPC_CPU));
9411 (*s->cpu_fprintf)(s->file, "PowerPC %-16s PVR %08x\n",
9413 for (i = 0; ppc_cpu_aliases[i].alias != NULL; i++) {
9414 PowerPCCPUAlias *alias = &ppc_cpu_aliases[i];
9415 ObjectClass *alias_oc = ppc_cpu_class_by_alias(alias);
9417 if (alias_oc != oc) {
9420 (*s->cpu_fprintf)(s->file, "PowerPC %-16s (alias for %s)\n",
9421 alias->alias, name);
9426 void ppc_cpu_list(FILE *f, fprintf_function cpu_fprintf)
9430 .cpu_fprintf = cpu_fprintf,
9434 list = object_class_get_list(TYPE_POWERPC_CPU, false);
9435 list = g_slist_sort(list, ppc_cpu_list_compare);
9436 g_slist_foreach(list, ppc_cpu_list_entry, &s);
9440 cpu_fprintf(f, "\n");
9441 cpu_fprintf(f, "PowerPC %-16s\n", "host");
9445 static void ppc_cpu_defs_entry(gpointer data, gpointer user_data)
9447 ObjectClass *oc = data;
9448 CpuDefinitionInfoList **first = user_data;
9449 const char *typename;
9450 CpuDefinitionInfoList *entry;
9451 CpuDefinitionInfo *info;
9452 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
9454 if (!ppc_cpu_is_valid(pcc)) {
9458 typename = object_class_get_name(oc);
9459 info = g_malloc0(sizeof(*info));
9460 info->name = g_strndup(typename,
9461 strlen(typename) - strlen("-" TYPE_POWERPC_CPU));
9463 entry = g_malloc0(sizeof(*entry));
9464 entry->value = info;
9465 entry->next = *first;
9469 CpuDefinitionInfoList *arch_query_cpu_definitions(Error **errp)
9471 CpuDefinitionInfoList *cpu_list = NULL;
9475 list = object_class_get_list(TYPE_POWERPC_CPU, false);
9476 g_slist_foreach(list, ppc_cpu_defs_entry, &cpu_list);
9479 for (i = 0; ppc_cpu_aliases[i].alias != NULL; i++) {
9480 PowerPCCPUAlias *alias = &ppc_cpu_aliases[i];
9482 CpuDefinitionInfoList *entry;
9483 CpuDefinitionInfo *info;
9485 oc = ppc_cpu_class_by_alias(alias);
9490 info = g_malloc0(sizeof(*info));
9491 info->name = g_strdup(alias->alias);
9493 entry = g_malloc0(sizeof(*entry));
9494 entry->value = info;
9495 entry->next = cpu_list;
9502 static void ppc_cpu_set_pc(CPUState *cs, vaddr value)
9504 PowerPCCPU *cpu = POWERPC_CPU(cs);
9506 cpu->env.nip = value;
9509 static bool ppc_cpu_has_work(CPUState *cs)
9511 PowerPCCPU *cpu = POWERPC_CPU(cs);
9512 CPUPPCState *env = &cpu->env;
9514 return msr_ee && (cs->interrupt_request & CPU_INTERRUPT_HARD);
9517 static void ppc_cpu_exec_enter(CPUState *cs)
9519 PowerPCCPU *cpu = POWERPC_CPU(cs);
9520 CPUPPCState *env = &cpu->env;
9522 env->reserve_addr = -1;
9525 /* CPUClass::reset() */
9526 static void ppc_cpu_reset(CPUState *s)
9528 PowerPCCPU *cpu = POWERPC_CPU(s);
9529 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
9530 CPUPPCState *env = &cpu->env;
9534 pcc->parent_reset(s);
9536 msr = (target_ulong)0;
9538 /* XXX: find a suitable condition to enable the hypervisor mode */
9539 msr |= (target_ulong)MSR_HVB;
9541 msr |= (target_ulong)0 << MSR_AP; /* TO BE CHECKED */
9542 msr |= (target_ulong)0 << MSR_SA; /* TO BE CHECKED */
9543 msr |= (target_ulong)1 << MSR_EP;
9544 #if defined(DO_SINGLE_STEP) && 0
9545 /* Single step trace mode */
9546 msr |= (target_ulong)1 << MSR_SE;
9547 msr |= (target_ulong)1 << MSR_BE;
9549 #if defined(CONFIG_USER_ONLY)
9550 msr |= (target_ulong)1 << MSR_FP; /* Allow floating point usage */
9551 msr |= (target_ulong)1 << MSR_VR; /* Allow altivec usage */
9552 msr |= (target_ulong)1 << MSR_VSX; /* Allow VSX usage */
9553 msr |= (target_ulong)1 << MSR_SPE; /* Allow SPE usage */
9554 msr |= (target_ulong)1 << MSR_PR;
9555 #if defined(TARGET_PPC64)
9556 msr |= (target_ulong)1 << MSR_TM; /* Transactional memory */
9558 #if !defined(TARGET_WORDS_BIGENDIAN)
9559 msr |= (target_ulong)1 << MSR_LE; /* Little-endian user mode */
9560 if (!((env->msr_mask >> MSR_LE) & 1)) {
9561 fprintf(stderr, "Selected CPU does not support little-endian.\n");
9567 #if defined(TARGET_PPC64)
9568 if (env->mmu_model & POWERPC_MMU_64) {
9569 env->msr |= (1ULL << MSR_SF);
9573 hreg_store_msr(env, msr, 1);
9575 #if !defined(CONFIG_USER_ONLY)
9576 env->nip = env->hreset_vector | env->excp_prefix;
9577 if (env->mmu_model != POWERPC_MMU_REAL) {
9578 ppc_tlb_invalidate_all(env);
9582 hreg_compute_hflags(env);
9583 env->reserve_addr = (target_ulong)-1ULL;
9584 /* Be sure no exception or interrupt is pending */
9585 env->pending_interrupts = 0;
9586 s->exception_index = POWERPC_EXCP_NONE;
9587 env->error_code = 0;
9589 #if defined(TARGET_PPC64) && !defined(CONFIG_USER_ONLY)
9591 env->slb_shadow_addr = 0;
9592 env->slb_shadow_size = 0;
9595 #endif /* TARGET_PPC64 */
9597 for (i = 0; i < ARRAY_SIZE(env->spr_cb); i++) {
9598 ppc_spr_t *spr = &env->spr_cb[i];
9603 env->spr[i] = spr->default_value;
9606 /* Flush all TLBs */
9610 #ifndef CONFIG_USER_ONLY
9611 static bool ppc_cpu_is_big_endian(CPUState *cs)
9613 PowerPCCPU *cpu = POWERPC_CPU(cs);
9614 CPUPPCState *env = &cpu->env;
9616 cpu_synchronize_state(cs);
9622 static void ppc_cpu_initfn(Object *obj)
9624 CPUState *cs = CPU(obj);
9625 PowerPCCPU *cpu = POWERPC_CPU(obj);
9626 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
9627 CPUPPCState *env = &cpu->env;
9631 cpu->cpu_dt_id = cs->cpu_index;
9633 env->msr_mask = pcc->msr_mask;
9634 env->mmu_model = pcc->mmu_model;
9635 env->excp_model = pcc->excp_model;
9636 env->bus_model = pcc->bus_model;
9637 env->insns_flags = pcc->insns_flags;
9638 env->insns_flags2 = pcc->insns_flags2;
9639 env->flags = pcc->flags;
9640 env->bfd_mach = pcc->bfd_mach;
9641 env->check_pow = pcc->check_pow;
9643 #if defined(TARGET_PPC64)
9645 env->sps = *pcc->sps;
9646 } else if (env->mmu_model & POWERPC_MMU_64) {
9647 /* Use default sets of page sizes */
9648 static const struct ppc_segment_page_sizes defsps = {
9650 { .page_shift = 12, /* 4K */
9652 .enc = { { .page_shift = 12, .pte_enc = 0 } }
9654 { .page_shift = 24, /* 16M */
9656 .enc = { { .page_shift = 24, .pte_enc = 0 } }
9662 #endif /* defined(TARGET_PPC64) */
9664 if (tcg_enabled()) {
9665 ppc_translate_init();
9669 static bool ppc_pvr_match_default(PowerPCCPUClass *pcc, uint32_t pvr)
9671 return pcc->pvr == pvr;
9674 static void ppc_cpu_class_init(ObjectClass *oc, void *data)
9676 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
9677 CPUClass *cc = CPU_CLASS(oc);
9678 DeviceClass *dc = DEVICE_CLASS(oc);
9680 pcc->parent_realize = dc->realize;
9681 pcc->pvr_match = ppc_pvr_match_default;
9682 pcc->interrupts_big_endian = ppc_cpu_interrupts_big_endian_always;
9683 dc->realize = ppc_cpu_realizefn;
9684 dc->unrealize = ppc_cpu_unrealizefn;
9686 pcc->parent_reset = cc->reset;
9687 cc->reset = ppc_cpu_reset;
9689 cc->class_by_name = ppc_cpu_class_by_name;
9690 cc->has_work = ppc_cpu_has_work;
9691 cc->do_interrupt = ppc_cpu_do_interrupt;
9692 cc->cpu_exec_interrupt = ppc_cpu_exec_interrupt;
9693 cc->dump_state = ppc_cpu_dump_state;
9694 cc->dump_statistics = ppc_cpu_dump_statistics;
9695 cc->set_pc = ppc_cpu_set_pc;
9696 cc->gdb_read_register = ppc_cpu_gdb_read_register;
9697 cc->gdb_write_register = ppc_cpu_gdb_write_register;
9698 #ifdef CONFIG_USER_ONLY
9699 cc->handle_mmu_fault = ppc_cpu_handle_mmu_fault;
9701 cc->get_phys_page_debug = ppc_cpu_get_phys_page_debug;
9702 cc->vmsd = &vmstate_ppc_cpu;
9703 #if defined(TARGET_PPC64)
9704 cc->write_elf64_note = ppc64_cpu_write_elf64_note;
9705 cc->write_elf64_qemunote = ppc64_cpu_write_elf64_qemunote;
9708 cc->cpu_exec_enter = ppc_cpu_exec_enter;
9710 cc->gdb_num_core_regs = 71;
9712 #ifdef USE_APPLE_GDB
9713 cc->gdb_read_register = ppc_cpu_gdb_read_register_apple;
9714 cc->gdb_write_register = ppc_cpu_gdb_write_register_apple;
9715 cc->gdb_num_core_regs = 71 + 32;
9718 #if defined(TARGET_PPC64)
9719 cc->gdb_core_xml_file = "power64-core.xml";
9721 cc->gdb_core_xml_file = "power-core.xml";
9723 #ifndef CONFIG_USER_ONLY
9724 cc->virtio_is_big_endian = ppc_cpu_is_big_endian;
9727 dc->fw_name = "PowerPC,UNKNOWN";
9730 static const TypeInfo ppc_cpu_type_info = {
9731 .name = TYPE_POWERPC_CPU,
9733 .instance_size = sizeof(PowerPCCPU),
9734 .instance_init = ppc_cpu_initfn,
9736 .class_size = sizeof(PowerPCCPUClass),
9737 .class_init = ppc_cpu_class_init,
9740 static void ppc_cpu_register_types(void)
9742 type_register_static(&ppc_cpu_type_info);
9745 type_init(ppc_cpu_register_types)