tests: Restore check-qdict unit test
[qemu/armbru.git] / target / ppc / translate_init.inc.c
blob263e63cb03509b79a1cde09e39c8fc1766f8ae04
1 /*
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 "kvm_ppc.h"
24 #include "sysemu/arch_init.h"
25 #include "sysemu/cpus.h"
26 #include "sysemu/hw_accel.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/error.h"
32 #include "qapi/qmp/qnull.h"
33 #include "qapi/visitor.h"
34 #include "hw/qdev-properties.h"
35 #include "hw/ppc/ppc.h"
36 #include "mmu-book3s-v3.h"
37 #include "sysemu/qtest.h"
38 #include "qemu/cutils.h"
39 #include "disas/capstone.h"
40 #include "fpu/softfloat.h"
42 //#define PPC_DUMP_CPU
43 //#define PPC_DEBUG_SPR
44 //#define PPC_DUMP_SPR_ACCESSES
45 /* #define USE_APPLE_GDB */
47 /* Generic callbacks:
48 * do nothing but store/retrieve spr value
50 static void spr_load_dump_spr(int sprn)
52 #ifdef PPC_DUMP_SPR_ACCESSES
53 TCGv_i32 t0 = tcg_const_i32(sprn);
54 gen_helper_load_dump_spr(cpu_env, t0);
55 tcg_temp_free_i32(t0);
56 #endif
59 static void spr_read_generic (DisasContext *ctx, int gprn, int sprn)
61 gen_load_spr(cpu_gpr[gprn], sprn);
62 spr_load_dump_spr(sprn);
65 static void spr_store_dump_spr(int sprn)
67 #ifdef PPC_DUMP_SPR_ACCESSES
68 TCGv_i32 t0 = tcg_const_i32(sprn);
69 gen_helper_store_dump_spr(cpu_env, t0);
70 tcg_temp_free_i32(t0);
71 #endif
74 static void spr_write_generic(DisasContext *ctx, int sprn, int gprn)
76 gen_store_spr(sprn, cpu_gpr[gprn]);
77 spr_store_dump_spr(sprn);
80 #if !defined(CONFIG_USER_ONLY)
81 static void spr_write_generic32(DisasContext *ctx, int sprn, int gprn)
83 #ifdef TARGET_PPC64
84 TCGv t0 = tcg_temp_new();
85 tcg_gen_ext32u_tl(t0, cpu_gpr[gprn]);
86 gen_store_spr(sprn, t0);
87 tcg_temp_free(t0);
88 spr_store_dump_spr(sprn);
89 #else
90 spr_write_generic(ctx, sprn, gprn);
91 #endif
94 static void spr_write_clear(DisasContext *ctx, int sprn, int gprn)
96 TCGv t0 = tcg_temp_new();
97 TCGv t1 = tcg_temp_new();
98 gen_load_spr(t0, sprn);
99 tcg_gen_neg_tl(t1, cpu_gpr[gprn]);
100 tcg_gen_and_tl(t0, t0, t1);
101 gen_store_spr(sprn, t0);
102 tcg_temp_free(t0);
103 tcg_temp_free(t1);
106 static void spr_access_nop(DisasContext *ctx, int sprn, int gprn)
110 #endif
112 /* SPR common to all PowerPC */
113 /* XER */
114 static void spr_read_xer(DisasContext *ctx, int gprn, int sprn)
116 gen_read_xer(ctx, cpu_gpr[gprn]);
119 static void spr_write_xer(DisasContext *ctx, int sprn, int gprn)
121 gen_write_xer(cpu_gpr[gprn]);
124 /* LR */
125 static void spr_read_lr(DisasContext *ctx, int gprn, int sprn)
127 tcg_gen_mov_tl(cpu_gpr[gprn], cpu_lr);
130 static void spr_write_lr(DisasContext *ctx, int sprn, int gprn)
132 tcg_gen_mov_tl(cpu_lr, cpu_gpr[gprn]);
135 /* CFAR */
136 #if defined(TARGET_PPC64) && !defined(CONFIG_USER_ONLY)
137 static void spr_read_cfar(DisasContext *ctx, int gprn, int sprn)
139 tcg_gen_mov_tl(cpu_gpr[gprn], cpu_cfar);
142 static void spr_write_cfar(DisasContext *ctx, int sprn, int gprn)
144 tcg_gen_mov_tl(cpu_cfar, cpu_gpr[gprn]);
146 #endif /* defined(TARGET_PPC64) && !defined(CONFIG_USER_ONLY) */
148 /* CTR */
149 static void spr_read_ctr(DisasContext *ctx, int gprn, int sprn)
151 tcg_gen_mov_tl(cpu_gpr[gprn], cpu_ctr);
154 static void spr_write_ctr(DisasContext *ctx, int sprn, int gprn)
156 tcg_gen_mov_tl(cpu_ctr, cpu_gpr[gprn]);
159 /* User read access to SPR */
160 /* USPRx */
161 /* UMMCRx */
162 /* UPMCx */
163 /* USIA */
164 /* UDECR */
165 static void spr_read_ureg(DisasContext *ctx, int gprn, int sprn)
167 gen_load_spr(cpu_gpr[gprn], sprn + 0x10);
170 #if defined(TARGET_PPC64) && !defined(CONFIG_USER_ONLY)
171 static void spr_write_ureg(DisasContext *ctx, int sprn, int gprn)
173 gen_store_spr(sprn + 0x10, cpu_gpr[gprn]);
175 #endif
177 /* SPR common to all non-embedded PowerPC */
178 /* DECR */
179 #if !defined(CONFIG_USER_ONLY)
180 static void spr_read_decr(DisasContext *ctx, int gprn, int sprn)
182 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
183 gen_io_start();
185 gen_helper_load_decr(cpu_gpr[gprn], cpu_env);
186 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
187 gen_io_end();
188 gen_stop_exception(ctx);
192 static void spr_write_decr(DisasContext *ctx, int sprn, int gprn)
194 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
195 gen_io_start();
197 gen_helper_store_decr(cpu_env, cpu_gpr[gprn]);
198 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
199 gen_io_end();
200 gen_stop_exception(ctx);
203 #endif
205 /* SPR common to all non-embedded PowerPC, except 601 */
206 /* Time base */
207 static void spr_read_tbl(DisasContext *ctx, int gprn, int sprn)
209 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
210 gen_io_start();
212 gen_helper_load_tbl(cpu_gpr[gprn], cpu_env);
213 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
214 gen_io_end();
215 gen_stop_exception(ctx);
219 static void spr_read_tbu(DisasContext *ctx, int gprn, int sprn)
221 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
222 gen_io_start();
224 gen_helper_load_tbu(cpu_gpr[gprn], cpu_env);
225 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
226 gen_io_end();
227 gen_stop_exception(ctx);
231 __attribute__ (( unused ))
232 static void spr_read_atbl(DisasContext *ctx, int gprn, int sprn)
234 gen_helper_load_atbl(cpu_gpr[gprn], cpu_env);
237 __attribute__ (( unused ))
238 static void spr_read_atbu(DisasContext *ctx, int gprn, int sprn)
240 gen_helper_load_atbu(cpu_gpr[gprn], cpu_env);
243 #if !defined(CONFIG_USER_ONLY)
244 static void spr_write_tbl(DisasContext *ctx, int sprn, int gprn)
246 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
247 gen_io_start();
249 gen_helper_store_tbl(cpu_env, cpu_gpr[gprn]);
250 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
251 gen_io_end();
252 gen_stop_exception(ctx);
256 static void spr_write_tbu(DisasContext *ctx, int sprn, int gprn)
258 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
259 gen_io_start();
261 gen_helper_store_tbu(cpu_env, cpu_gpr[gprn]);
262 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
263 gen_io_end();
264 gen_stop_exception(ctx);
268 __attribute__ (( unused ))
269 static void spr_write_atbl(DisasContext *ctx, int sprn, int gprn)
271 gen_helper_store_atbl(cpu_env, cpu_gpr[gprn]);
274 __attribute__ (( unused ))
275 static void spr_write_atbu(DisasContext *ctx, int sprn, int gprn)
277 gen_helper_store_atbu(cpu_env, cpu_gpr[gprn]);
280 #if defined(TARGET_PPC64)
281 __attribute__ (( unused ))
282 static void spr_read_purr(DisasContext *ctx, int gprn, int sprn)
284 gen_helper_load_purr(cpu_gpr[gprn], cpu_env);
287 /* HDECR */
288 static void spr_read_hdecr(DisasContext *ctx, int gprn, int sprn)
290 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
291 gen_io_start();
293 gen_helper_load_hdecr(cpu_gpr[gprn], cpu_env);
294 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
295 gen_io_end();
296 gen_stop_exception(ctx);
300 static void spr_write_hdecr(DisasContext *ctx, int sprn, int gprn)
302 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
303 gen_io_start();
305 gen_helper_store_hdecr(cpu_env, cpu_gpr[gprn]);
306 if (tb_cflags(ctx->base.tb) & CF_USE_ICOUNT) {
307 gen_io_end();
308 gen_stop_exception(ctx);
312 #endif
313 #endif
315 #if !defined(CONFIG_USER_ONLY)
316 /* IBAT0U...IBAT0U */
317 /* IBAT0L...IBAT7L */
318 static void spr_read_ibat(DisasContext *ctx, int gprn, int sprn)
320 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, IBAT[sprn & 1][(sprn - SPR_IBAT0U) / 2]));
323 static void spr_read_ibat_h(DisasContext *ctx, int gprn, int sprn)
325 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, IBAT[sprn & 1][((sprn - SPR_IBAT4U) / 2) + 4]));
328 static void spr_write_ibatu(DisasContext *ctx, int sprn, int gprn)
330 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_IBAT0U) / 2);
331 gen_helper_store_ibatu(cpu_env, t0, cpu_gpr[gprn]);
332 tcg_temp_free_i32(t0);
335 static void spr_write_ibatu_h(DisasContext *ctx, int sprn, int gprn)
337 TCGv_i32 t0 = tcg_const_i32(((sprn - SPR_IBAT4U) / 2) + 4);
338 gen_helper_store_ibatu(cpu_env, t0, cpu_gpr[gprn]);
339 tcg_temp_free_i32(t0);
342 static void spr_write_ibatl(DisasContext *ctx, int sprn, int gprn)
344 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_IBAT0L) / 2);
345 gen_helper_store_ibatl(cpu_env, t0, cpu_gpr[gprn]);
346 tcg_temp_free_i32(t0);
349 static void spr_write_ibatl_h(DisasContext *ctx, int sprn, int gprn)
351 TCGv_i32 t0 = tcg_const_i32(((sprn - SPR_IBAT4L) / 2) + 4);
352 gen_helper_store_ibatl(cpu_env, t0, cpu_gpr[gprn]);
353 tcg_temp_free_i32(t0);
356 /* DBAT0U...DBAT7U */
357 /* DBAT0L...DBAT7L */
358 static void spr_read_dbat(DisasContext *ctx, int gprn, int sprn)
360 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, DBAT[sprn & 1][(sprn - SPR_DBAT0U) / 2]));
363 static void spr_read_dbat_h(DisasContext *ctx, int gprn, int sprn)
365 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, DBAT[sprn & 1][((sprn - SPR_DBAT4U) / 2) + 4]));
368 static void spr_write_dbatu(DisasContext *ctx, int sprn, int gprn)
370 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_DBAT0U) / 2);
371 gen_helper_store_dbatu(cpu_env, t0, cpu_gpr[gprn]);
372 tcg_temp_free_i32(t0);
375 static void spr_write_dbatu_h(DisasContext *ctx, int sprn, int gprn)
377 TCGv_i32 t0 = tcg_const_i32(((sprn - SPR_DBAT4U) / 2) + 4);
378 gen_helper_store_dbatu(cpu_env, t0, cpu_gpr[gprn]);
379 tcg_temp_free_i32(t0);
382 static void spr_write_dbatl(DisasContext *ctx, int sprn, int gprn)
384 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_DBAT0L) / 2);
385 gen_helper_store_dbatl(cpu_env, t0, cpu_gpr[gprn]);
386 tcg_temp_free_i32(t0);
389 static void spr_write_dbatl_h(DisasContext *ctx, int sprn, int gprn)
391 TCGv_i32 t0 = tcg_const_i32(((sprn - SPR_DBAT4L) / 2) + 4);
392 gen_helper_store_dbatl(cpu_env, t0, cpu_gpr[gprn]);
393 tcg_temp_free_i32(t0);
396 /* SDR1 */
397 static void spr_write_sdr1(DisasContext *ctx, int sprn, int gprn)
399 gen_helper_store_sdr1(cpu_env, cpu_gpr[gprn]);
402 #if defined(TARGET_PPC64)
403 /* 64 bits PowerPC specific SPRs */
404 /* PIDR */
405 static void spr_write_pidr(DisasContext *ctx, int sprn, int gprn)
407 gen_helper_store_pidr(cpu_env, cpu_gpr[gprn]);
410 static void spr_read_hior(DisasContext *ctx, int gprn, int sprn)
412 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, excp_prefix));
415 static void spr_write_hior(DisasContext *ctx, int sprn, int gprn)
417 TCGv t0 = tcg_temp_new();
418 tcg_gen_andi_tl(t0, cpu_gpr[gprn], 0x3FFFFF00000ULL);
419 tcg_gen_st_tl(t0, cpu_env, offsetof(CPUPPCState, excp_prefix));
420 tcg_temp_free(t0);
422 static void spr_write_ptcr(DisasContext *ctx, int sprn, int gprn)
424 gen_helper_store_ptcr(cpu_env, cpu_gpr[gprn]);
427 static void spr_write_pcr(DisasContext *ctx, int sprn, int gprn)
429 gen_helper_store_pcr(cpu_env, cpu_gpr[gprn]);
431 #endif
432 #endif
434 /* PowerPC 601 specific registers */
435 /* RTC */
436 static void spr_read_601_rtcl(DisasContext *ctx, int gprn, int sprn)
438 gen_helper_load_601_rtcl(cpu_gpr[gprn], cpu_env);
441 static void spr_read_601_rtcu(DisasContext *ctx, int gprn, int sprn)
443 gen_helper_load_601_rtcu(cpu_gpr[gprn], cpu_env);
446 #if !defined(CONFIG_USER_ONLY)
447 static void spr_write_601_rtcu(DisasContext *ctx, int sprn, int gprn)
449 gen_helper_store_601_rtcu(cpu_env, cpu_gpr[gprn]);
452 static void spr_write_601_rtcl(DisasContext *ctx, int sprn, int gprn)
454 gen_helper_store_601_rtcl(cpu_env, cpu_gpr[gprn]);
457 static void spr_write_hid0_601(DisasContext *ctx, int sprn, int gprn)
459 gen_helper_store_hid0_601(cpu_env, cpu_gpr[gprn]);
460 /* Must stop the translation as endianness may have changed */
461 gen_stop_exception(ctx);
463 #endif
465 /* Unified bats */
466 #if !defined(CONFIG_USER_ONLY)
467 static void spr_read_601_ubat(DisasContext *ctx, int gprn, int sprn)
469 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, IBAT[sprn & 1][(sprn - SPR_IBAT0U) / 2]));
472 static void spr_write_601_ubatu(DisasContext *ctx, int sprn, int gprn)
474 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_IBAT0U) / 2);
475 gen_helper_store_601_batl(cpu_env, t0, cpu_gpr[gprn]);
476 tcg_temp_free_i32(t0);
479 static void spr_write_601_ubatl(DisasContext *ctx, int sprn, int gprn)
481 TCGv_i32 t0 = tcg_const_i32((sprn - SPR_IBAT0U) / 2);
482 gen_helper_store_601_batu(cpu_env, t0, cpu_gpr[gprn]);
483 tcg_temp_free_i32(t0);
485 #endif
487 /* PowerPC 40x specific registers */
488 #if !defined(CONFIG_USER_ONLY)
489 static void spr_read_40x_pit(DisasContext *ctx, int gprn, int sprn)
491 gen_helper_load_40x_pit(cpu_gpr[gprn], cpu_env);
494 static void spr_write_40x_pit(DisasContext *ctx, int sprn, int gprn)
496 gen_helper_store_40x_pit(cpu_env, cpu_gpr[gprn]);
499 static void spr_write_40x_dbcr0(DisasContext *ctx, int sprn, int gprn)
501 gen_store_spr(sprn, cpu_gpr[gprn]);
502 gen_helper_store_40x_dbcr0(cpu_env, cpu_gpr[gprn]);
503 /* We must stop translation as we may have rebooted */
504 gen_stop_exception(ctx);
507 static void spr_write_40x_sler(DisasContext *ctx, int sprn, int gprn)
509 gen_helper_store_40x_sler(cpu_env, cpu_gpr[gprn]);
512 static void spr_write_booke_tcr(DisasContext *ctx, int sprn, int gprn)
514 gen_helper_store_booke_tcr(cpu_env, cpu_gpr[gprn]);
517 static void spr_write_booke_tsr(DisasContext *ctx, int sprn, int gprn)
519 gen_helper_store_booke_tsr(cpu_env, cpu_gpr[gprn]);
521 #endif
523 /* PowerPC 403 specific registers */
524 /* PBL1 / PBU1 / PBL2 / PBU2 */
525 #if !defined(CONFIG_USER_ONLY)
526 static void spr_read_403_pbr(DisasContext *ctx, int gprn, int sprn)
528 tcg_gen_ld_tl(cpu_gpr[gprn], cpu_env, offsetof(CPUPPCState, pb[sprn - SPR_403_PBL1]));
531 static void spr_write_403_pbr(DisasContext *ctx, int sprn, int gprn)
533 TCGv_i32 t0 = tcg_const_i32(sprn - SPR_403_PBL1);
534 gen_helper_store_403_pbr(cpu_env, t0, cpu_gpr[gprn]);
535 tcg_temp_free_i32(t0);
538 static void spr_write_pir(DisasContext *ctx, int sprn, int gprn)
540 TCGv t0 = tcg_temp_new();
541 tcg_gen_andi_tl(t0, cpu_gpr[gprn], 0xF);
542 gen_store_spr(SPR_PIR, t0);
543 tcg_temp_free(t0);
545 #endif
547 /* SPE specific registers */
548 static void spr_read_spefscr(DisasContext *ctx, int gprn, int sprn)
550 TCGv_i32 t0 = tcg_temp_new_i32();
551 tcg_gen_ld_i32(t0, cpu_env, offsetof(CPUPPCState, spe_fscr));
552 tcg_gen_extu_i32_tl(cpu_gpr[gprn], t0);
553 tcg_temp_free_i32(t0);
556 static void spr_write_spefscr(DisasContext *ctx, int sprn, int gprn)
558 TCGv_i32 t0 = tcg_temp_new_i32();
559 tcg_gen_trunc_tl_i32(t0, cpu_gpr[gprn]);
560 tcg_gen_st_i32(t0, cpu_env, offsetof(CPUPPCState, spe_fscr));
561 tcg_temp_free_i32(t0);
564 #if !defined(CONFIG_USER_ONLY)
565 /* Callback used to write the exception vector base */
566 static void spr_write_excp_prefix(DisasContext *ctx, int sprn, int gprn)
568 TCGv t0 = tcg_temp_new();
569 tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUPPCState, ivpr_mask));
570 tcg_gen_and_tl(t0, t0, cpu_gpr[gprn]);
571 tcg_gen_st_tl(t0, cpu_env, offsetof(CPUPPCState, excp_prefix));
572 gen_store_spr(sprn, t0);
573 tcg_temp_free(t0);
576 static void spr_write_excp_vector(DisasContext *ctx, int sprn, int gprn)
578 int sprn_offs;
580 if (sprn >= SPR_BOOKE_IVOR0 && sprn <= SPR_BOOKE_IVOR15) {
581 sprn_offs = sprn - SPR_BOOKE_IVOR0;
582 } else if (sprn >= SPR_BOOKE_IVOR32 && sprn <= SPR_BOOKE_IVOR37) {
583 sprn_offs = sprn - SPR_BOOKE_IVOR32 + 32;
584 } else if (sprn >= SPR_BOOKE_IVOR38 && sprn <= SPR_BOOKE_IVOR42) {
585 sprn_offs = sprn - SPR_BOOKE_IVOR38 + 38;
586 } else {
587 printf("Trying to write an unknown exception vector %d %03x\n",
588 sprn, sprn);
589 gen_inval_exception(ctx, POWERPC_EXCP_PRIV_REG);
590 return;
593 TCGv t0 = tcg_temp_new();
594 tcg_gen_ld_tl(t0, cpu_env, offsetof(CPUPPCState, ivor_mask));
595 tcg_gen_and_tl(t0, t0, cpu_gpr[gprn]);
596 tcg_gen_st_tl(t0, cpu_env, offsetof(CPUPPCState, excp_vectors[sprn_offs]));
597 gen_store_spr(sprn, t0);
598 tcg_temp_free(t0);
600 #endif
602 static inline void vscr_init(CPUPPCState *env, uint32_t val)
604 env->vscr = val;
605 /* Altivec always uses round-to-nearest */
606 set_float_rounding_mode(float_round_nearest_even, &env->vec_status);
607 set_flush_to_zero(vscr_nj, &env->vec_status);
610 #ifdef CONFIG_USER_ONLY
611 #define spr_register_kvm(env, num, name, uea_read, uea_write, \
612 oea_read, oea_write, one_reg_id, initial_value) \
613 _spr_register(env, num, name, uea_read, uea_write, initial_value)
614 #define spr_register_kvm_hv(env, num, name, uea_read, uea_write, \
615 oea_read, oea_write, hea_read, hea_write, \
616 one_reg_id, initial_value) \
617 _spr_register(env, num, name, uea_read, uea_write, initial_value)
618 #else
619 #if !defined(CONFIG_KVM)
620 #define spr_register_kvm(env, num, name, uea_read, uea_write, \
621 oea_read, oea_write, one_reg_id, initial_value) \
622 _spr_register(env, num, name, uea_read, uea_write, \
623 oea_read, oea_write, oea_read, oea_write, initial_value)
624 #define spr_register_kvm_hv(env, num, name, uea_read, uea_write, \
625 oea_read, oea_write, hea_read, hea_write, \
626 one_reg_id, initial_value) \
627 _spr_register(env, num, name, uea_read, uea_write, \
628 oea_read, oea_write, hea_read, hea_write, initial_value)
629 #else
630 #define spr_register_kvm(env, num, name, uea_read, uea_write, \
631 oea_read, oea_write, one_reg_id, initial_value) \
632 _spr_register(env, num, name, uea_read, uea_write, \
633 oea_read, oea_write, oea_read, oea_write, \
634 one_reg_id, initial_value)
635 #define spr_register_kvm_hv(env, num, name, uea_read, uea_write, \
636 oea_read, oea_write, hea_read, hea_write, \
637 one_reg_id, initial_value) \
638 _spr_register(env, num, name, uea_read, uea_write, \
639 oea_read, oea_write, hea_read, hea_write, \
640 one_reg_id, initial_value)
641 #endif
642 #endif
644 #define spr_register(env, num, name, uea_read, uea_write, \
645 oea_read, oea_write, initial_value) \
646 spr_register_kvm(env, num, name, uea_read, uea_write, \
647 oea_read, oea_write, 0, initial_value)
649 #define spr_register_hv(env, num, name, uea_read, uea_write, \
650 oea_read, oea_write, hea_read, hea_write, \
651 initial_value) \
652 spr_register_kvm_hv(env, num, name, uea_read, uea_write, \
653 oea_read, oea_write, hea_read, hea_write, \
654 0, initial_value)
656 static inline void _spr_register(CPUPPCState *env, int num,
657 const char *name,
658 void (*uea_read)(DisasContext *ctx, int gprn, int sprn),
659 void (*uea_write)(DisasContext *ctx, int sprn, int gprn),
660 #if !defined(CONFIG_USER_ONLY)
662 void (*oea_read)(DisasContext *ctx, int gprn, int sprn),
663 void (*oea_write)(DisasContext *ctx, int sprn, int gprn),
664 void (*hea_read)(DisasContext *opaque, int gprn, int sprn),
665 void (*hea_write)(DisasContext *opaque, int sprn, int gprn),
666 #endif
667 #if defined(CONFIG_KVM)
668 uint64_t one_reg_id,
669 #endif
670 target_ulong initial_value)
672 ppc_spr_t *spr;
674 spr = &env->spr_cb[num];
675 if (spr->name != NULL ||env-> spr[num] != 0x00000000 ||
676 #if !defined(CONFIG_USER_ONLY)
677 spr->oea_read != NULL || spr->oea_write != NULL ||
678 #endif
679 spr->uea_read != NULL || spr->uea_write != NULL) {
680 printf("Error: Trying to register SPR %d (%03x) twice !\n", num, num);
681 exit(1);
683 #if defined(PPC_DEBUG_SPR)
684 printf("*** register spr %d (%03x) %s val " TARGET_FMT_lx "\n", num, num,
685 name, initial_value);
686 #endif
687 spr->name = name;
688 spr->uea_read = uea_read;
689 spr->uea_write = uea_write;
690 #if !defined(CONFIG_USER_ONLY)
691 spr->oea_read = oea_read;
692 spr->oea_write = oea_write;
693 spr->hea_read = hea_read;
694 spr->hea_write = hea_write;
695 #endif
696 #if defined(CONFIG_KVM)
697 spr->one_reg_id = one_reg_id,
698 #endif
699 env->spr[num] = spr->default_value = initial_value;
702 /* Generic PowerPC SPRs */
703 static void gen_spr_generic(CPUPPCState *env)
705 /* Integer processing */
706 spr_register(env, SPR_XER, "XER",
707 &spr_read_xer, &spr_write_xer,
708 &spr_read_xer, &spr_write_xer,
709 0x00000000);
710 /* Branch contol */
711 spr_register(env, SPR_LR, "LR",
712 &spr_read_lr, &spr_write_lr,
713 &spr_read_lr, &spr_write_lr,
714 0x00000000);
715 spr_register(env, SPR_CTR, "CTR",
716 &spr_read_ctr, &spr_write_ctr,
717 &spr_read_ctr, &spr_write_ctr,
718 0x00000000);
719 /* Interrupt processing */
720 spr_register(env, SPR_SRR0, "SRR0",
721 SPR_NOACCESS, SPR_NOACCESS,
722 &spr_read_generic, &spr_write_generic,
723 0x00000000);
724 spr_register(env, SPR_SRR1, "SRR1",
725 SPR_NOACCESS, SPR_NOACCESS,
726 &spr_read_generic, &spr_write_generic,
727 0x00000000);
728 /* Processor control */
729 spr_register(env, SPR_SPRG0, "SPRG0",
730 SPR_NOACCESS, SPR_NOACCESS,
731 &spr_read_generic, &spr_write_generic,
732 0x00000000);
733 spr_register(env, SPR_SPRG1, "SPRG1",
734 SPR_NOACCESS, SPR_NOACCESS,
735 &spr_read_generic, &spr_write_generic,
736 0x00000000);
737 spr_register(env, SPR_SPRG2, "SPRG2",
738 SPR_NOACCESS, SPR_NOACCESS,
739 &spr_read_generic, &spr_write_generic,
740 0x00000000);
741 spr_register(env, SPR_SPRG3, "SPRG3",
742 SPR_NOACCESS, SPR_NOACCESS,
743 &spr_read_generic, &spr_write_generic,
744 0x00000000);
747 /* SPR common to all non-embedded PowerPC, including 601 */
748 static void gen_spr_ne_601(CPUPPCState *env)
750 /* Exception processing */
751 spr_register_kvm(env, SPR_DSISR, "DSISR",
752 SPR_NOACCESS, SPR_NOACCESS,
753 &spr_read_generic, &spr_write_generic,
754 KVM_REG_PPC_DSISR, 0x00000000);
755 spr_register_kvm(env, SPR_DAR, "DAR",
756 SPR_NOACCESS, SPR_NOACCESS,
757 &spr_read_generic, &spr_write_generic,
758 KVM_REG_PPC_DAR, 0x00000000);
759 /* Timer */
760 spr_register(env, SPR_DECR, "DECR",
761 SPR_NOACCESS, SPR_NOACCESS,
762 &spr_read_decr, &spr_write_decr,
763 0x00000000);
766 /* Storage Description Register 1 */
767 static void gen_spr_sdr1(CPUPPCState *env)
769 #ifndef CONFIG_USER_ONLY
770 if (env->has_hv_mode) {
771 /* SDR1 is a hypervisor resource on CPUs which have a
772 * hypervisor mode */
773 spr_register_hv(env, SPR_SDR1, "SDR1",
774 SPR_NOACCESS, SPR_NOACCESS,
775 SPR_NOACCESS, SPR_NOACCESS,
776 &spr_read_generic, &spr_write_sdr1,
777 0x00000000);
778 } else {
779 spr_register(env, SPR_SDR1, "SDR1",
780 SPR_NOACCESS, SPR_NOACCESS,
781 &spr_read_generic, &spr_write_sdr1,
782 0x00000000);
784 #endif
787 /* BATs 0-3 */
788 static void gen_low_BATs(CPUPPCState *env)
790 #if !defined(CONFIG_USER_ONLY)
791 spr_register(env, SPR_IBAT0U, "IBAT0U",
792 SPR_NOACCESS, SPR_NOACCESS,
793 &spr_read_ibat, &spr_write_ibatu,
794 0x00000000);
795 spr_register(env, SPR_IBAT0L, "IBAT0L",
796 SPR_NOACCESS, SPR_NOACCESS,
797 &spr_read_ibat, &spr_write_ibatl,
798 0x00000000);
799 spr_register(env, SPR_IBAT1U, "IBAT1U",
800 SPR_NOACCESS, SPR_NOACCESS,
801 &spr_read_ibat, &spr_write_ibatu,
802 0x00000000);
803 spr_register(env, SPR_IBAT1L, "IBAT1L",
804 SPR_NOACCESS, SPR_NOACCESS,
805 &spr_read_ibat, &spr_write_ibatl,
806 0x00000000);
807 spr_register(env, SPR_IBAT2U, "IBAT2U",
808 SPR_NOACCESS, SPR_NOACCESS,
809 &spr_read_ibat, &spr_write_ibatu,
810 0x00000000);
811 spr_register(env, SPR_IBAT2L, "IBAT2L",
812 SPR_NOACCESS, SPR_NOACCESS,
813 &spr_read_ibat, &spr_write_ibatl,
814 0x00000000);
815 spr_register(env, SPR_IBAT3U, "IBAT3U",
816 SPR_NOACCESS, SPR_NOACCESS,
817 &spr_read_ibat, &spr_write_ibatu,
818 0x00000000);
819 spr_register(env, SPR_IBAT3L, "IBAT3L",
820 SPR_NOACCESS, SPR_NOACCESS,
821 &spr_read_ibat, &spr_write_ibatl,
822 0x00000000);
823 spr_register(env, SPR_DBAT0U, "DBAT0U",
824 SPR_NOACCESS, SPR_NOACCESS,
825 &spr_read_dbat, &spr_write_dbatu,
826 0x00000000);
827 spr_register(env, SPR_DBAT0L, "DBAT0L",
828 SPR_NOACCESS, SPR_NOACCESS,
829 &spr_read_dbat, &spr_write_dbatl,
830 0x00000000);
831 spr_register(env, SPR_DBAT1U, "DBAT1U",
832 SPR_NOACCESS, SPR_NOACCESS,
833 &spr_read_dbat, &spr_write_dbatu,
834 0x00000000);
835 spr_register(env, SPR_DBAT1L, "DBAT1L",
836 SPR_NOACCESS, SPR_NOACCESS,
837 &spr_read_dbat, &spr_write_dbatl,
838 0x00000000);
839 spr_register(env, SPR_DBAT2U, "DBAT2U",
840 SPR_NOACCESS, SPR_NOACCESS,
841 &spr_read_dbat, &spr_write_dbatu,
842 0x00000000);
843 spr_register(env, SPR_DBAT2L, "DBAT2L",
844 SPR_NOACCESS, SPR_NOACCESS,
845 &spr_read_dbat, &spr_write_dbatl,
846 0x00000000);
847 spr_register(env, SPR_DBAT3U, "DBAT3U",
848 SPR_NOACCESS, SPR_NOACCESS,
849 &spr_read_dbat, &spr_write_dbatu,
850 0x00000000);
851 spr_register(env, SPR_DBAT3L, "DBAT3L",
852 SPR_NOACCESS, SPR_NOACCESS,
853 &spr_read_dbat, &spr_write_dbatl,
854 0x00000000);
855 env->nb_BATs += 4;
856 #endif
859 /* BATs 4-7 */
860 static void gen_high_BATs(CPUPPCState *env)
862 #if !defined(CONFIG_USER_ONLY)
863 spr_register(env, SPR_IBAT4U, "IBAT4U",
864 SPR_NOACCESS, SPR_NOACCESS,
865 &spr_read_ibat_h, &spr_write_ibatu_h,
866 0x00000000);
867 spr_register(env, SPR_IBAT4L, "IBAT4L",
868 SPR_NOACCESS, SPR_NOACCESS,
869 &spr_read_ibat_h, &spr_write_ibatl_h,
870 0x00000000);
871 spr_register(env, SPR_IBAT5U, "IBAT5U",
872 SPR_NOACCESS, SPR_NOACCESS,
873 &spr_read_ibat_h, &spr_write_ibatu_h,
874 0x00000000);
875 spr_register(env, SPR_IBAT5L, "IBAT5L",
876 SPR_NOACCESS, SPR_NOACCESS,
877 &spr_read_ibat_h, &spr_write_ibatl_h,
878 0x00000000);
879 spr_register(env, SPR_IBAT6U, "IBAT6U",
880 SPR_NOACCESS, SPR_NOACCESS,
881 &spr_read_ibat_h, &spr_write_ibatu_h,
882 0x00000000);
883 spr_register(env, SPR_IBAT6L, "IBAT6L",
884 SPR_NOACCESS, SPR_NOACCESS,
885 &spr_read_ibat_h, &spr_write_ibatl_h,
886 0x00000000);
887 spr_register(env, SPR_IBAT7U, "IBAT7U",
888 SPR_NOACCESS, SPR_NOACCESS,
889 &spr_read_ibat_h, &spr_write_ibatu_h,
890 0x00000000);
891 spr_register(env, SPR_IBAT7L, "IBAT7L",
892 SPR_NOACCESS, SPR_NOACCESS,
893 &spr_read_ibat_h, &spr_write_ibatl_h,
894 0x00000000);
895 spr_register(env, SPR_DBAT4U, "DBAT4U",
896 SPR_NOACCESS, SPR_NOACCESS,
897 &spr_read_dbat_h, &spr_write_dbatu_h,
898 0x00000000);
899 spr_register(env, SPR_DBAT4L, "DBAT4L",
900 SPR_NOACCESS, SPR_NOACCESS,
901 &spr_read_dbat_h, &spr_write_dbatl_h,
902 0x00000000);
903 spr_register(env, SPR_DBAT5U, "DBAT5U",
904 SPR_NOACCESS, SPR_NOACCESS,
905 &spr_read_dbat_h, &spr_write_dbatu_h,
906 0x00000000);
907 spr_register(env, SPR_DBAT5L, "DBAT5L",
908 SPR_NOACCESS, SPR_NOACCESS,
909 &spr_read_dbat_h, &spr_write_dbatl_h,
910 0x00000000);
911 spr_register(env, SPR_DBAT6U, "DBAT6U",
912 SPR_NOACCESS, SPR_NOACCESS,
913 &spr_read_dbat_h, &spr_write_dbatu_h,
914 0x00000000);
915 spr_register(env, SPR_DBAT6L, "DBAT6L",
916 SPR_NOACCESS, SPR_NOACCESS,
917 &spr_read_dbat_h, &spr_write_dbatl_h,
918 0x00000000);
919 spr_register(env, SPR_DBAT7U, "DBAT7U",
920 SPR_NOACCESS, SPR_NOACCESS,
921 &spr_read_dbat_h, &spr_write_dbatu_h,
922 0x00000000);
923 spr_register(env, SPR_DBAT7L, "DBAT7L",
924 SPR_NOACCESS, SPR_NOACCESS,
925 &spr_read_dbat_h, &spr_write_dbatl_h,
926 0x00000000);
927 env->nb_BATs += 4;
928 #endif
931 /* Generic PowerPC time base */
932 static void gen_tbl(CPUPPCState *env)
934 spr_register(env, SPR_VTBL, "TBL",
935 &spr_read_tbl, SPR_NOACCESS,
936 &spr_read_tbl, SPR_NOACCESS,
937 0x00000000);
938 spr_register(env, SPR_TBL, "TBL",
939 &spr_read_tbl, SPR_NOACCESS,
940 &spr_read_tbl, &spr_write_tbl,
941 0x00000000);
942 spr_register(env, SPR_VTBU, "TBU",
943 &spr_read_tbu, SPR_NOACCESS,
944 &spr_read_tbu, SPR_NOACCESS,
945 0x00000000);
946 spr_register(env, SPR_TBU, "TBU",
947 &spr_read_tbu, SPR_NOACCESS,
948 &spr_read_tbu, &spr_write_tbu,
949 0x00000000);
952 /* Softare table search registers */
953 static void gen_6xx_7xx_soft_tlb(CPUPPCState *env, int nb_tlbs, int nb_ways)
955 #if !defined(CONFIG_USER_ONLY)
956 env->nb_tlb = nb_tlbs;
957 env->nb_ways = nb_ways;
958 env->id_tlbs = 1;
959 env->tlb_type = TLB_6XX;
960 spr_register(env, SPR_DMISS, "DMISS",
961 SPR_NOACCESS, SPR_NOACCESS,
962 &spr_read_generic, SPR_NOACCESS,
963 0x00000000);
964 spr_register(env, SPR_DCMP, "DCMP",
965 SPR_NOACCESS, SPR_NOACCESS,
966 &spr_read_generic, SPR_NOACCESS,
967 0x00000000);
968 spr_register(env, SPR_HASH1, "HASH1",
969 SPR_NOACCESS, SPR_NOACCESS,
970 &spr_read_generic, SPR_NOACCESS,
971 0x00000000);
972 spr_register(env, SPR_HASH2, "HASH2",
973 SPR_NOACCESS, SPR_NOACCESS,
974 &spr_read_generic, SPR_NOACCESS,
975 0x00000000);
976 spr_register(env, SPR_IMISS, "IMISS",
977 SPR_NOACCESS, SPR_NOACCESS,
978 &spr_read_generic, SPR_NOACCESS,
979 0x00000000);
980 spr_register(env, SPR_ICMP, "ICMP",
981 SPR_NOACCESS, SPR_NOACCESS,
982 &spr_read_generic, SPR_NOACCESS,
983 0x00000000);
984 spr_register(env, SPR_RPA, "RPA",
985 SPR_NOACCESS, SPR_NOACCESS,
986 &spr_read_generic, &spr_write_generic,
987 0x00000000);
988 #endif
991 /* SPR common to MPC755 and G2 */
992 static void gen_spr_G2_755(CPUPPCState *env)
994 /* SGPRs */
995 spr_register(env, SPR_SPRG4, "SPRG4",
996 SPR_NOACCESS, SPR_NOACCESS,
997 &spr_read_generic, &spr_write_generic,
998 0x00000000);
999 spr_register(env, SPR_SPRG5, "SPRG5",
1000 SPR_NOACCESS, SPR_NOACCESS,
1001 &spr_read_generic, &spr_write_generic,
1002 0x00000000);
1003 spr_register(env, SPR_SPRG6, "SPRG6",
1004 SPR_NOACCESS, SPR_NOACCESS,
1005 &spr_read_generic, &spr_write_generic,
1006 0x00000000);
1007 spr_register(env, SPR_SPRG7, "SPRG7",
1008 SPR_NOACCESS, SPR_NOACCESS,
1009 &spr_read_generic, &spr_write_generic,
1010 0x00000000);
1013 /* SPR common to all 7xx PowerPC implementations */
1014 static void gen_spr_7xx(CPUPPCState *env)
1016 /* Breakpoints */
1017 /* XXX : not implemented */
1018 spr_register_kvm(env, SPR_DABR, "DABR",
1019 SPR_NOACCESS, SPR_NOACCESS,
1020 &spr_read_generic, &spr_write_generic,
1021 KVM_REG_PPC_DABR, 0x00000000);
1022 /* XXX : not implemented */
1023 spr_register(env, SPR_IABR, "IABR",
1024 SPR_NOACCESS, SPR_NOACCESS,
1025 &spr_read_generic, &spr_write_generic,
1026 0x00000000);
1027 /* Cache management */
1028 /* XXX : not implemented */
1029 spr_register(env, SPR_ICTC, "ICTC",
1030 SPR_NOACCESS, SPR_NOACCESS,
1031 &spr_read_generic, &spr_write_generic,
1032 0x00000000);
1033 /* Performance monitors */
1034 /* XXX : not implemented */
1035 spr_register(env, SPR_7XX_MMCR0, "MMCR0",
1036 SPR_NOACCESS, SPR_NOACCESS,
1037 &spr_read_generic, &spr_write_generic,
1038 0x00000000);
1039 /* XXX : not implemented */
1040 spr_register(env, SPR_7XX_MMCR1, "MMCR1",
1041 SPR_NOACCESS, SPR_NOACCESS,
1042 &spr_read_generic, &spr_write_generic,
1043 0x00000000);
1044 /* XXX : not implemented */
1045 spr_register(env, SPR_7XX_PMC1, "PMC1",
1046 SPR_NOACCESS, SPR_NOACCESS,
1047 &spr_read_generic, &spr_write_generic,
1048 0x00000000);
1049 /* XXX : not implemented */
1050 spr_register(env, SPR_7XX_PMC2, "PMC2",
1051 SPR_NOACCESS, SPR_NOACCESS,
1052 &spr_read_generic, &spr_write_generic,
1053 0x00000000);
1054 /* XXX : not implemented */
1055 spr_register(env, SPR_7XX_PMC3, "PMC3",
1056 SPR_NOACCESS, SPR_NOACCESS,
1057 &spr_read_generic, &spr_write_generic,
1058 0x00000000);
1059 /* XXX : not implemented */
1060 spr_register(env, SPR_7XX_PMC4, "PMC4",
1061 SPR_NOACCESS, SPR_NOACCESS,
1062 &spr_read_generic, &spr_write_generic,
1063 0x00000000);
1064 /* XXX : not implemented */
1065 spr_register(env, SPR_7XX_SIAR, "SIAR",
1066 SPR_NOACCESS, SPR_NOACCESS,
1067 &spr_read_generic, SPR_NOACCESS,
1068 0x00000000);
1069 /* XXX : not implemented */
1070 spr_register(env, SPR_7XX_UMMCR0, "UMMCR0",
1071 &spr_read_ureg, SPR_NOACCESS,
1072 &spr_read_ureg, SPR_NOACCESS,
1073 0x00000000);
1074 /* XXX : not implemented */
1075 spr_register(env, SPR_7XX_UMMCR1, "UMMCR1",
1076 &spr_read_ureg, SPR_NOACCESS,
1077 &spr_read_ureg, SPR_NOACCESS,
1078 0x00000000);
1079 /* XXX : not implemented */
1080 spr_register(env, SPR_7XX_UPMC1, "UPMC1",
1081 &spr_read_ureg, SPR_NOACCESS,
1082 &spr_read_ureg, SPR_NOACCESS,
1083 0x00000000);
1084 /* XXX : not implemented */
1085 spr_register(env, SPR_7XX_UPMC2, "UPMC2",
1086 &spr_read_ureg, SPR_NOACCESS,
1087 &spr_read_ureg, SPR_NOACCESS,
1088 0x00000000);
1089 /* XXX : not implemented */
1090 spr_register(env, SPR_7XX_UPMC3, "UPMC3",
1091 &spr_read_ureg, SPR_NOACCESS,
1092 &spr_read_ureg, SPR_NOACCESS,
1093 0x00000000);
1094 /* XXX : not implemented */
1095 spr_register(env, SPR_7XX_UPMC4, "UPMC4",
1096 &spr_read_ureg, SPR_NOACCESS,
1097 &spr_read_ureg, SPR_NOACCESS,
1098 0x00000000);
1099 /* XXX : not implemented */
1100 spr_register(env, SPR_7XX_USIAR, "USIAR",
1101 &spr_read_ureg, SPR_NOACCESS,
1102 &spr_read_ureg, SPR_NOACCESS,
1103 0x00000000);
1104 /* External access control */
1105 /* XXX : not implemented */
1106 spr_register(env, SPR_EAR, "EAR",
1107 SPR_NOACCESS, SPR_NOACCESS,
1108 &spr_read_generic, &spr_write_generic,
1109 0x00000000);
1112 #ifdef TARGET_PPC64
1113 #ifndef CONFIG_USER_ONLY
1114 static void spr_write_amr(DisasContext *ctx, int sprn, int gprn)
1116 TCGv t0 = tcg_temp_new();
1117 TCGv t1 = tcg_temp_new();
1118 TCGv t2 = tcg_temp_new();
1120 /* Note, the HV=1 PR=0 case is handled earlier by simply using
1121 * spr_write_generic for HV mode in the SPR table
1124 /* Build insertion mask into t1 based on context */
1125 if (ctx->pr) {
1126 gen_load_spr(t1, SPR_UAMOR);
1127 } else {
1128 gen_load_spr(t1, SPR_AMOR);
1131 /* Mask new bits into t2 */
1132 tcg_gen_and_tl(t2, t1, cpu_gpr[gprn]);
1134 /* Load AMR and clear new bits in t0 */
1135 gen_load_spr(t0, SPR_AMR);
1136 tcg_gen_andc_tl(t0, t0, t1);
1138 /* Or'in new bits and write it out */
1139 tcg_gen_or_tl(t0, t0, t2);
1140 gen_store_spr(SPR_AMR, t0);
1141 spr_store_dump_spr(SPR_AMR);
1143 tcg_temp_free(t0);
1144 tcg_temp_free(t1);
1145 tcg_temp_free(t2);
1148 static void spr_write_uamor(DisasContext *ctx, int sprn, int gprn)
1150 TCGv t0 = tcg_temp_new();
1151 TCGv t1 = tcg_temp_new();
1152 TCGv t2 = tcg_temp_new();
1154 /* Note, the HV=1 case is handled earlier by simply using
1155 * spr_write_generic for HV mode in the SPR table
1158 /* Build insertion mask into t1 based on context */
1159 gen_load_spr(t1, SPR_AMOR);
1161 /* Mask new bits into t2 */
1162 tcg_gen_and_tl(t2, t1, cpu_gpr[gprn]);
1164 /* Load AMR and clear new bits in t0 */
1165 gen_load_spr(t0, SPR_UAMOR);
1166 tcg_gen_andc_tl(t0, t0, t1);
1168 /* Or'in new bits and write it out */
1169 tcg_gen_or_tl(t0, t0, t2);
1170 gen_store_spr(SPR_UAMOR, t0);
1171 spr_store_dump_spr(SPR_UAMOR);
1173 tcg_temp_free(t0);
1174 tcg_temp_free(t1);
1175 tcg_temp_free(t2);
1178 static void spr_write_iamr(DisasContext *ctx, int sprn, int gprn)
1180 TCGv t0 = tcg_temp_new();
1181 TCGv t1 = tcg_temp_new();
1182 TCGv t2 = tcg_temp_new();
1184 /* Note, the HV=1 case is handled earlier by simply using
1185 * spr_write_generic for HV mode in the SPR table
1188 /* Build insertion mask into t1 based on context */
1189 gen_load_spr(t1, SPR_AMOR);
1191 /* Mask new bits into t2 */
1192 tcg_gen_and_tl(t2, t1, cpu_gpr[gprn]);
1194 /* Load AMR and clear new bits in t0 */
1195 gen_load_spr(t0, SPR_IAMR);
1196 tcg_gen_andc_tl(t0, t0, t1);
1198 /* Or'in new bits and write it out */
1199 tcg_gen_or_tl(t0, t0, t2);
1200 gen_store_spr(SPR_IAMR, t0);
1201 spr_store_dump_spr(SPR_IAMR);
1203 tcg_temp_free(t0);
1204 tcg_temp_free(t1);
1205 tcg_temp_free(t2);
1207 #endif /* CONFIG_USER_ONLY */
1209 static void gen_spr_amr(CPUPPCState *env)
1211 #ifndef CONFIG_USER_ONLY
1212 /* Virtual Page Class Key protection */
1213 /* The AMR is accessible either via SPR 13 or SPR 29. 13 is
1214 * userspace accessible, 29 is privileged. So we only need to set
1215 * the kvm ONE_REG id on one of them, we use 29 */
1216 spr_register(env, SPR_UAMR, "UAMR",
1217 &spr_read_generic, &spr_write_amr,
1218 &spr_read_generic, &spr_write_amr,
1220 spr_register_kvm_hv(env, SPR_AMR, "AMR",
1221 SPR_NOACCESS, SPR_NOACCESS,
1222 &spr_read_generic, &spr_write_amr,
1223 &spr_read_generic, &spr_write_generic,
1224 KVM_REG_PPC_AMR, 0);
1225 spr_register_kvm_hv(env, SPR_UAMOR, "UAMOR",
1226 SPR_NOACCESS, SPR_NOACCESS,
1227 &spr_read_generic, &spr_write_uamor,
1228 &spr_read_generic, &spr_write_generic,
1229 KVM_REG_PPC_UAMOR, 0);
1230 spr_register_hv(env, SPR_AMOR, "AMOR",
1231 SPR_NOACCESS, SPR_NOACCESS,
1232 SPR_NOACCESS, SPR_NOACCESS,
1233 &spr_read_generic, &spr_write_generic,
1235 #endif /* !CONFIG_USER_ONLY */
1238 static void gen_spr_iamr(CPUPPCState *env)
1240 #ifndef CONFIG_USER_ONLY
1241 spr_register_kvm_hv(env, SPR_IAMR, "IAMR",
1242 SPR_NOACCESS, SPR_NOACCESS,
1243 &spr_read_generic, &spr_write_iamr,
1244 &spr_read_generic, &spr_write_generic,
1245 KVM_REG_PPC_IAMR, 0);
1246 #endif /* !CONFIG_USER_ONLY */
1248 #endif /* TARGET_PPC64 */
1250 #ifndef CONFIG_USER_ONLY
1251 static void spr_read_thrm(DisasContext *ctx, int gprn, int sprn)
1253 gen_helper_fixup_thrm(cpu_env);
1254 gen_load_spr(cpu_gpr[gprn], sprn);
1255 spr_load_dump_spr(sprn);
1257 #endif /* !CONFIG_USER_ONLY */
1259 static void gen_spr_thrm(CPUPPCState *env)
1261 /* Thermal management */
1262 /* XXX : not implemented */
1263 spr_register(env, SPR_THRM1, "THRM1",
1264 SPR_NOACCESS, SPR_NOACCESS,
1265 &spr_read_thrm, &spr_write_generic,
1266 0x00000000);
1267 /* XXX : not implemented */
1268 spr_register(env, SPR_THRM2, "THRM2",
1269 SPR_NOACCESS, SPR_NOACCESS,
1270 &spr_read_thrm, &spr_write_generic,
1271 0x00000000);
1272 /* XXX : not implemented */
1273 spr_register(env, SPR_THRM3, "THRM3",
1274 SPR_NOACCESS, SPR_NOACCESS,
1275 &spr_read_thrm, &spr_write_generic,
1276 0x00000000);
1279 /* SPR specific to PowerPC 604 implementation */
1280 static void gen_spr_604(CPUPPCState *env)
1282 /* Processor identification */
1283 spr_register(env, SPR_PIR, "PIR",
1284 SPR_NOACCESS, SPR_NOACCESS,
1285 &spr_read_generic, &spr_write_pir,
1286 0x00000000);
1287 /* Breakpoints */
1288 /* XXX : not implemented */
1289 spr_register(env, SPR_IABR, "IABR",
1290 SPR_NOACCESS, SPR_NOACCESS,
1291 &spr_read_generic, &spr_write_generic,
1292 0x00000000);
1293 /* XXX : not implemented */
1294 spr_register_kvm(env, SPR_DABR, "DABR",
1295 SPR_NOACCESS, SPR_NOACCESS,
1296 &spr_read_generic, &spr_write_generic,
1297 KVM_REG_PPC_DABR, 0x00000000);
1298 /* Performance counters */
1299 /* XXX : not implemented */
1300 spr_register(env, SPR_7XX_MMCR0, "MMCR0",
1301 SPR_NOACCESS, SPR_NOACCESS,
1302 &spr_read_generic, &spr_write_generic,
1303 0x00000000);
1304 /* XXX : not implemented */
1305 spr_register(env, SPR_7XX_PMC1, "PMC1",
1306 SPR_NOACCESS, SPR_NOACCESS,
1307 &spr_read_generic, &spr_write_generic,
1308 0x00000000);
1309 /* XXX : not implemented */
1310 spr_register(env, SPR_7XX_PMC2, "PMC2",
1311 SPR_NOACCESS, SPR_NOACCESS,
1312 &spr_read_generic, &spr_write_generic,
1313 0x00000000);
1314 /* XXX : not implemented */
1315 spr_register(env, SPR_7XX_SIAR, "SIAR",
1316 SPR_NOACCESS, SPR_NOACCESS,
1317 &spr_read_generic, SPR_NOACCESS,
1318 0x00000000);
1319 /* XXX : not implemented */
1320 spr_register(env, SPR_SDA, "SDA",
1321 SPR_NOACCESS, SPR_NOACCESS,
1322 &spr_read_generic, SPR_NOACCESS,
1323 0x00000000);
1324 /* External access control */
1325 /* XXX : not implemented */
1326 spr_register(env, SPR_EAR, "EAR",
1327 SPR_NOACCESS, SPR_NOACCESS,
1328 &spr_read_generic, &spr_write_generic,
1329 0x00000000);
1332 /* SPR specific to PowerPC 603 implementation */
1333 static void gen_spr_603(CPUPPCState *env)
1335 /* External access control */
1336 /* XXX : not implemented */
1337 spr_register(env, SPR_EAR, "EAR",
1338 SPR_NOACCESS, SPR_NOACCESS,
1339 &spr_read_generic, &spr_write_generic,
1340 0x00000000);
1341 /* Breakpoints */
1342 /* XXX : not implemented */
1343 spr_register(env, SPR_IABR, "IABR",
1344 SPR_NOACCESS, SPR_NOACCESS,
1345 &spr_read_generic, &spr_write_generic,
1346 0x00000000);
1350 /* SPR specific to PowerPC G2 implementation */
1351 static void gen_spr_G2(CPUPPCState *env)
1353 /* Memory base address */
1354 /* MBAR */
1355 /* XXX : not implemented */
1356 spr_register(env, SPR_MBAR, "MBAR",
1357 SPR_NOACCESS, SPR_NOACCESS,
1358 &spr_read_generic, &spr_write_generic,
1359 0x00000000);
1360 /* Exception processing */
1361 spr_register(env, SPR_BOOKE_CSRR0, "CSRR0",
1362 SPR_NOACCESS, SPR_NOACCESS,
1363 &spr_read_generic, &spr_write_generic,
1364 0x00000000);
1365 spr_register(env, SPR_BOOKE_CSRR1, "CSRR1",
1366 SPR_NOACCESS, SPR_NOACCESS,
1367 &spr_read_generic, &spr_write_generic,
1368 0x00000000);
1369 /* Breakpoints */
1370 /* XXX : not implemented */
1371 spr_register(env, SPR_DABR, "DABR",
1372 SPR_NOACCESS, SPR_NOACCESS,
1373 &spr_read_generic, &spr_write_generic,
1374 0x00000000);
1375 /* XXX : not implemented */
1376 spr_register(env, SPR_DABR2, "DABR2",
1377 SPR_NOACCESS, SPR_NOACCESS,
1378 &spr_read_generic, &spr_write_generic,
1379 0x00000000);
1380 /* XXX : not implemented */
1381 spr_register(env, SPR_IABR, "IABR",
1382 SPR_NOACCESS, SPR_NOACCESS,
1383 &spr_read_generic, &spr_write_generic,
1384 0x00000000);
1385 /* XXX : not implemented */
1386 spr_register(env, SPR_IABR2, "IABR2",
1387 SPR_NOACCESS, SPR_NOACCESS,
1388 &spr_read_generic, &spr_write_generic,
1389 0x00000000);
1390 /* XXX : not implemented */
1391 spr_register(env, SPR_IBCR, "IBCR",
1392 SPR_NOACCESS, SPR_NOACCESS,
1393 &spr_read_generic, &spr_write_generic,
1394 0x00000000);
1395 /* XXX : not implemented */
1396 spr_register(env, SPR_DBCR, "DBCR",
1397 SPR_NOACCESS, SPR_NOACCESS,
1398 &spr_read_generic, &spr_write_generic,
1399 0x00000000);
1402 /* SPR specific to PowerPC 602 implementation */
1403 static void gen_spr_602(CPUPPCState *env)
1405 /* ESA registers */
1406 /* XXX : not implemented */
1407 spr_register(env, SPR_SER, "SER",
1408 SPR_NOACCESS, SPR_NOACCESS,
1409 &spr_read_generic, &spr_write_generic,
1410 0x00000000);
1411 /* XXX : not implemented */
1412 spr_register(env, SPR_SEBR, "SEBR",
1413 SPR_NOACCESS, SPR_NOACCESS,
1414 &spr_read_generic, &spr_write_generic,
1415 0x00000000);
1416 /* XXX : not implemented */
1417 spr_register(env, SPR_ESASRR, "ESASRR",
1418 SPR_NOACCESS, SPR_NOACCESS,
1419 &spr_read_generic, &spr_write_generic,
1420 0x00000000);
1421 /* Floating point status */
1422 /* XXX : not implemented */
1423 spr_register(env, SPR_SP, "SP",
1424 SPR_NOACCESS, SPR_NOACCESS,
1425 &spr_read_generic, &spr_write_generic,
1426 0x00000000);
1427 /* XXX : not implemented */
1428 spr_register(env, SPR_LT, "LT",
1429 SPR_NOACCESS, SPR_NOACCESS,
1430 &spr_read_generic, &spr_write_generic,
1431 0x00000000);
1432 /* Watchdog timer */
1433 /* XXX : not implemented */
1434 spr_register(env, SPR_TCR, "TCR",
1435 SPR_NOACCESS, SPR_NOACCESS,
1436 &spr_read_generic, &spr_write_generic,
1437 0x00000000);
1438 /* Interrupt base */
1439 spr_register(env, SPR_IBR, "IBR",
1440 SPR_NOACCESS, SPR_NOACCESS,
1441 &spr_read_generic, &spr_write_generic,
1442 0x00000000);
1443 /* XXX : not implemented */
1444 spr_register(env, SPR_IABR, "IABR",
1445 SPR_NOACCESS, SPR_NOACCESS,
1446 &spr_read_generic, &spr_write_generic,
1447 0x00000000);
1450 /* SPR specific to PowerPC 601 implementation */
1451 static void gen_spr_601(CPUPPCState *env)
1453 /* Multiplication/division register */
1454 /* MQ */
1455 spr_register(env, SPR_MQ, "MQ",
1456 &spr_read_generic, &spr_write_generic,
1457 &spr_read_generic, &spr_write_generic,
1458 0x00000000);
1459 /* RTC registers */
1460 spr_register(env, SPR_601_RTCU, "RTCU",
1461 SPR_NOACCESS, SPR_NOACCESS,
1462 SPR_NOACCESS, &spr_write_601_rtcu,
1463 0x00000000);
1464 spr_register(env, SPR_601_VRTCU, "RTCU",
1465 &spr_read_601_rtcu, SPR_NOACCESS,
1466 &spr_read_601_rtcu, SPR_NOACCESS,
1467 0x00000000);
1468 spr_register(env, SPR_601_RTCL, "RTCL",
1469 SPR_NOACCESS, SPR_NOACCESS,
1470 SPR_NOACCESS, &spr_write_601_rtcl,
1471 0x00000000);
1472 spr_register(env, SPR_601_VRTCL, "RTCL",
1473 &spr_read_601_rtcl, SPR_NOACCESS,
1474 &spr_read_601_rtcl, SPR_NOACCESS,
1475 0x00000000);
1476 /* Timer */
1477 #if 0 /* ? */
1478 spr_register(env, SPR_601_UDECR, "UDECR",
1479 &spr_read_decr, SPR_NOACCESS,
1480 &spr_read_decr, SPR_NOACCESS,
1481 0x00000000);
1482 #endif
1483 /* External access control */
1484 /* XXX : not implemented */
1485 spr_register(env, SPR_EAR, "EAR",
1486 SPR_NOACCESS, SPR_NOACCESS,
1487 &spr_read_generic, &spr_write_generic,
1488 0x00000000);
1489 /* Memory management */
1490 #if !defined(CONFIG_USER_ONLY)
1491 spr_register(env, SPR_IBAT0U, "IBAT0U",
1492 SPR_NOACCESS, SPR_NOACCESS,
1493 &spr_read_601_ubat, &spr_write_601_ubatu,
1494 0x00000000);
1495 spr_register(env, SPR_IBAT0L, "IBAT0L",
1496 SPR_NOACCESS, SPR_NOACCESS,
1497 &spr_read_601_ubat, &spr_write_601_ubatl,
1498 0x00000000);
1499 spr_register(env, SPR_IBAT1U, "IBAT1U",
1500 SPR_NOACCESS, SPR_NOACCESS,
1501 &spr_read_601_ubat, &spr_write_601_ubatu,
1502 0x00000000);
1503 spr_register(env, SPR_IBAT1L, "IBAT1L",
1504 SPR_NOACCESS, SPR_NOACCESS,
1505 &spr_read_601_ubat, &spr_write_601_ubatl,
1506 0x00000000);
1507 spr_register(env, SPR_IBAT2U, "IBAT2U",
1508 SPR_NOACCESS, SPR_NOACCESS,
1509 &spr_read_601_ubat, &spr_write_601_ubatu,
1510 0x00000000);
1511 spr_register(env, SPR_IBAT2L, "IBAT2L",
1512 SPR_NOACCESS, SPR_NOACCESS,
1513 &spr_read_601_ubat, &spr_write_601_ubatl,
1514 0x00000000);
1515 spr_register(env, SPR_IBAT3U, "IBAT3U",
1516 SPR_NOACCESS, SPR_NOACCESS,
1517 &spr_read_601_ubat, &spr_write_601_ubatu,
1518 0x00000000);
1519 spr_register(env, SPR_IBAT3L, "IBAT3L",
1520 SPR_NOACCESS, SPR_NOACCESS,
1521 &spr_read_601_ubat, &spr_write_601_ubatl,
1522 0x00000000);
1523 env->nb_BATs = 4;
1524 #endif
1527 static void gen_spr_74xx(CPUPPCState *env)
1529 /* Processor identification */
1530 spr_register(env, SPR_PIR, "PIR",
1531 SPR_NOACCESS, SPR_NOACCESS,
1532 &spr_read_generic, &spr_write_pir,
1533 0x00000000);
1534 /* XXX : not implemented */
1535 spr_register(env, SPR_74XX_MMCR2, "MMCR2",
1536 SPR_NOACCESS, SPR_NOACCESS,
1537 &spr_read_generic, &spr_write_generic,
1538 0x00000000);
1539 /* XXX : not implemented */
1540 spr_register(env, SPR_74XX_UMMCR2, "UMMCR2",
1541 &spr_read_ureg, SPR_NOACCESS,
1542 &spr_read_ureg, SPR_NOACCESS,
1543 0x00000000);
1544 /* XXX: not implemented */
1545 spr_register(env, SPR_BAMR, "BAMR",
1546 SPR_NOACCESS, SPR_NOACCESS,
1547 &spr_read_generic, &spr_write_generic,
1548 0x00000000);
1549 /* XXX : not implemented */
1550 spr_register(env, SPR_MSSCR0, "MSSCR0",
1551 SPR_NOACCESS, SPR_NOACCESS,
1552 &spr_read_generic, &spr_write_generic,
1553 0x00000000);
1554 /* Hardware implementation registers */
1555 /* XXX : not implemented */
1556 spr_register(env, SPR_HID0, "HID0",
1557 SPR_NOACCESS, SPR_NOACCESS,
1558 &spr_read_generic, &spr_write_generic,
1559 0x00000000);
1560 /* XXX : not implemented */
1561 spr_register(env, SPR_HID1, "HID1",
1562 SPR_NOACCESS, SPR_NOACCESS,
1563 &spr_read_generic, &spr_write_generic,
1564 0x00000000);
1565 /* Altivec */
1566 spr_register(env, SPR_VRSAVE, "VRSAVE",
1567 &spr_read_generic, &spr_write_generic,
1568 &spr_read_generic, &spr_write_generic,
1569 0x00000000);
1570 /* XXX : not implemented */
1571 spr_register(env, SPR_L2CR, "L2CR",
1572 SPR_NOACCESS, SPR_NOACCESS,
1573 &spr_read_generic, spr_access_nop,
1574 0x00000000);
1575 /* Not strictly an SPR */
1576 vscr_init(env, 0x00010000);
1579 static void gen_l3_ctrl(CPUPPCState *env)
1581 /* L3CR */
1582 /* XXX : not implemented */
1583 spr_register(env, SPR_L3CR, "L3CR",
1584 SPR_NOACCESS, SPR_NOACCESS,
1585 &spr_read_generic, &spr_write_generic,
1586 0x00000000);
1587 /* L3ITCR0 */
1588 /* XXX : not implemented */
1589 spr_register(env, SPR_L3ITCR0, "L3ITCR0",
1590 SPR_NOACCESS, SPR_NOACCESS,
1591 &spr_read_generic, &spr_write_generic,
1592 0x00000000);
1593 /* L3PM */
1594 /* XXX : not implemented */
1595 spr_register(env, SPR_L3PM, "L3PM",
1596 SPR_NOACCESS, SPR_NOACCESS,
1597 &spr_read_generic, &spr_write_generic,
1598 0x00000000);
1601 static void gen_74xx_soft_tlb(CPUPPCState *env, int nb_tlbs, int nb_ways)
1603 #if !defined(CONFIG_USER_ONLY)
1604 env->nb_tlb = nb_tlbs;
1605 env->nb_ways = nb_ways;
1606 env->id_tlbs = 1;
1607 env->tlb_type = TLB_6XX;
1608 /* XXX : not implemented */
1609 spr_register(env, SPR_PTEHI, "PTEHI",
1610 SPR_NOACCESS, SPR_NOACCESS,
1611 &spr_read_generic, &spr_write_generic,
1612 0x00000000);
1613 /* XXX : not implemented */
1614 spr_register(env, SPR_PTELO, "PTELO",
1615 SPR_NOACCESS, SPR_NOACCESS,
1616 &spr_read_generic, &spr_write_generic,
1617 0x00000000);
1618 /* XXX : not implemented */
1619 spr_register(env, SPR_TLBMISS, "TLBMISS",
1620 SPR_NOACCESS, SPR_NOACCESS,
1621 &spr_read_generic, &spr_write_generic,
1622 0x00000000);
1623 #endif
1626 #if !defined(CONFIG_USER_ONLY)
1627 static void spr_write_e500_l1csr0(DisasContext *ctx, int sprn, int gprn)
1629 TCGv t0 = tcg_temp_new();
1631 tcg_gen_andi_tl(t0, cpu_gpr[gprn], L1CSR0_DCE | L1CSR0_CPE);
1632 gen_store_spr(sprn, t0);
1633 tcg_temp_free(t0);
1636 static void spr_write_e500_l1csr1(DisasContext *ctx, int sprn, int gprn)
1638 TCGv t0 = tcg_temp_new();
1640 tcg_gen_andi_tl(t0, cpu_gpr[gprn], L1CSR1_ICE | L1CSR1_CPE);
1641 gen_store_spr(sprn, t0);
1642 tcg_temp_free(t0);
1645 static void spr_write_booke206_mmucsr0(DisasContext *ctx, int sprn, int gprn)
1647 gen_helper_booke206_tlbflush(cpu_env, cpu_gpr[gprn]);
1650 static void spr_write_booke_pid(DisasContext *ctx, int sprn, int gprn)
1652 TCGv_i32 t0 = tcg_const_i32(sprn);
1653 gen_helper_booke_setpid(cpu_env, t0, cpu_gpr[gprn]);
1654 tcg_temp_free_i32(t0);
1656 #endif
1658 static void gen_spr_usprg3(CPUPPCState *env)
1660 spr_register(env, SPR_USPRG3, "USPRG3",
1661 &spr_read_ureg, SPR_NOACCESS,
1662 &spr_read_ureg, SPR_NOACCESS,
1663 0x00000000);
1666 static void gen_spr_usprgh(CPUPPCState *env)
1668 spr_register(env, SPR_USPRG4, "USPRG4",
1669 &spr_read_ureg, SPR_NOACCESS,
1670 &spr_read_ureg, SPR_NOACCESS,
1671 0x00000000);
1672 spr_register(env, SPR_USPRG5, "USPRG5",
1673 &spr_read_ureg, SPR_NOACCESS,
1674 &spr_read_ureg, SPR_NOACCESS,
1675 0x00000000);
1676 spr_register(env, SPR_USPRG6, "USPRG6",
1677 &spr_read_ureg, SPR_NOACCESS,
1678 &spr_read_ureg, SPR_NOACCESS,
1679 0x00000000);
1680 spr_register(env, SPR_USPRG7, "USPRG7",
1681 &spr_read_ureg, SPR_NOACCESS,
1682 &spr_read_ureg, SPR_NOACCESS,
1683 0x00000000);
1686 /* PowerPC BookE SPR */
1687 static void gen_spr_BookE(CPUPPCState *env, uint64_t ivor_mask)
1689 const char *ivor_names[64] = {
1690 "IVOR0", "IVOR1", "IVOR2", "IVOR3",
1691 "IVOR4", "IVOR5", "IVOR6", "IVOR7",
1692 "IVOR8", "IVOR9", "IVOR10", "IVOR11",
1693 "IVOR12", "IVOR13", "IVOR14", "IVOR15",
1694 "IVOR16", "IVOR17", "IVOR18", "IVOR19",
1695 "IVOR20", "IVOR21", "IVOR22", "IVOR23",
1696 "IVOR24", "IVOR25", "IVOR26", "IVOR27",
1697 "IVOR28", "IVOR29", "IVOR30", "IVOR31",
1698 "IVOR32", "IVOR33", "IVOR34", "IVOR35",
1699 "IVOR36", "IVOR37", "IVOR38", "IVOR39",
1700 "IVOR40", "IVOR41", "IVOR42", "IVOR43",
1701 "IVOR44", "IVOR45", "IVOR46", "IVOR47",
1702 "IVOR48", "IVOR49", "IVOR50", "IVOR51",
1703 "IVOR52", "IVOR53", "IVOR54", "IVOR55",
1704 "IVOR56", "IVOR57", "IVOR58", "IVOR59",
1705 "IVOR60", "IVOR61", "IVOR62", "IVOR63",
1707 #define SPR_BOOKE_IVORxx (-1)
1708 int ivor_sprn[64] = {
1709 SPR_BOOKE_IVOR0, SPR_BOOKE_IVOR1, SPR_BOOKE_IVOR2, SPR_BOOKE_IVOR3,
1710 SPR_BOOKE_IVOR4, SPR_BOOKE_IVOR5, SPR_BOOKE_IVOR6, SPR_BOOKE_IVOR7,
1711 SPR_BOOKE_IVOR8, SPR_BOOKE_IVOR9, SPR_BOOKE_IVOR10, SPR_BOOKE_IVOR11,
1712 SPR_BOOKE_IVOR12, SPR_BOOKE_IVOR13, SPR_BOOKE_IVOR14, SPR_BOOKE_IVOR15,
1713 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1714 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1715 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1716 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1717 SPR_BOOKE_IVOR32, SPR_BOOKE_IVOR33, SPR_BOOKE_IVOR34, SPR_BOOKE_IVOR35,
1718 SPR_BOOKE_IVOR36, SPR_BOOKE_IVOR37, SPR_BOOKE_IVOR38, SPR_BOOKE_IVOR39,
1719 SPR_BOOKE_IVOR40, SPR_BOOKE_IVOR41, SPR_BOOKE_IVOR42, SPR_BOOKE_IVORxx,
1720 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1721 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1722 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1723 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1724 SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx, SPR_BOOKE_IVORxx,
1726 int i;
1728 /* Interrupt processing */
1729 spr_register(env, SPR_BOOKE_CSRR0, "CSRR0",
1730 SPR_NOACCESS, SPR_NOACCESS,
1731 &spr_read_generic, &spr_write_generic,
1732 0x00000000);
1733 spr_register(env, SPR_BOOKE_CSRR1, "CSRR1",
1734 SPR_NOACCESS, SPR_NOACCESS,
1735 &spr_read_generic, &spr_write_generic,
1736 0x00000000);
1737 /* Debug */
1738 /* XXX : not implemented */
1739 spr_register(env, SPR_BOOKE_IAC1, "IAC1",
1740 SPR_NOACCESS, SPR_NOACCESS,
1741 &spr_read_generic, &spr_write_generic,
1742 0x00000000);
1743 /* XXX : not implemented */
1744 spr_register(env, SPR_BOOKE_IAC2, "IAC2",
1745 SPR_NOACCESS, SPR_NOACCESS,
1746 &spr_read_generic, &spr_write_generic,
1747 0x00000000);
1748 /* XXX : not implemented */
1749 spr_register(env, SPR_BOOKE_DAC1, "DAC1",
1750 SPR_NOACCESS, SPR_NOACCESS,
1751 &spr_read_generic, &spr_write_generic,
1752 0x00000000);
1753 /* XXX : not implemented */
1754 spr_register(env, SPR_BOOKE_DAC2, "DAC2",
1755 SPR_NOACCESS, SPR_NOACCESS,
1756 &spr_read_generic, &spr_write_generic,
1757 0x00000000);
1758 /* XXX : not implemented */
1759 spr_register(env, SPR_BOOKE_DBCR0, "DBCR0",
1760 SPR_NOACCESS, SPR_NOACCESS,
1761 &spr_read_generic, &spr_write_40x_dbcr0,
1762 0x00000000);
1763 /* XXX : not implemented */
1764 spr_register(env, SPR_BOOKE_DBCR1, "DBCR1",
1765 SPR_NOACCESS, SPR_NOACCESS,
1766 &spr_read_generic, &spr_write_generic,
1767 0x00000000);
1768 /* XXX : not implemented */
1769 spr_register(env, SPR_BOOKE_DBCR2, "DBCR2",
1770 SPR_NOACCESS, SPR_NOACCESS,
1771 &spr_read_generic, &spr_write_generic,
1772 0x00000000);
1773 spr_register(env, SPR_BOOKE_DSRR0, "DSRR0",
1774 SPR_NOACCESS, SPR_NOACCESS,
1775 &spr_read_generic, &spr_write_generic,
1776 0x00000000);
1777 spr_register(env, SPR_BOOKE_DSRR1, "DSRR1",
1778 SPR_NOACCESS, SPR_NOACCESS,
1779 &spr_read_generic, &spr_write_generic,
1780 0x00000000);
1781 /* XXX : not implemented */
1782 spr_register(env, SPR_BOOKE_DBSR, "DBSR",
1783 SPR_NOACCESS, SPR_NOACCESS,
1784 &spr_read_generic, &spr_write_clear,
1785 0x00000000);
1786 spr_register(env, SPR_BOOKE_DEAR, "DEAR",
1787 SPR_NOACCESS, SPR_NOACCESS,
1788 &spr_read_generic, &spr_write_generic,
1789 0x00000000);
1790 spr_register(env, SPR_BOOKE_ESR, "ESR",
1791 SPR_NOACCESS, SPR_NOACCESS,
1792 &spr_read_generic, &spr_write_generic,
1793 0x00000000);
1794 spr_register(env, SPR_BOOKE_IVPR, "IVPR",
1795 SPR_NOACCESS, SPR_NOACCESS,
1796 &spr_read_generic, &spr_write_excp_prefix,
1797 0x00000000);
1798 /* Exception vectors */
1799 for (i = 0; i < 64; i++) {
1800 if (ivor_mask & (1ULL << i)) {
1801 if (ivor_sprn[i] == SPR_BOOKE_IVORxx) {
1802 fprintf(stderr, "ERROR: IVOR %d SPR is not defined\n", i);
1803 exit(1);
1805 spr_register(env, ivor_sprn[i], ivor_names[i],
1806 SPR_NOACCESS, SPR_NOACCESS,
1807 &spr_read_generic, &spr_write_excp_vector,
1808 0x00000000);
1811 spr_register(env, SPR_BOOKE_PID, "PID",
1812 SPR_NOACCESS, SPR_NOACCESS,
1813 &spr_read_generic, &spr_write_booke_pid,
1814 0x00000000);
1815 spr_register(env, SPR_BOOKE_TCR, "TCR",
1816 SPR_NOACCESS, SPR_NOACCESS,
1817 &spr_read_generic, &spr_write_booke_tcr,
1818 0x00000000);
1819 spr_register(env, SPR_BOOKE_TSR, "TSR",
1820 SPR_NOACCESS, SPR_NOACCESS,
1821 &spr_read_generic, &spr_write_booke_tsr,
1822 0x00000000);
1823 /* Timer */
1824 spr_register(env, SPR_DECR, "DECR",
1825 SPR_NOACCESS, SPR_NOACCESS,
1826 &spr_read_decr, &spr_write_decr,
1827 0x00000000);
1828 spr_register(env, SPR_BOOKE_DECAR, "DECAR",
1829 SPR_NOACCESS, SPR_NOACCESS,
1830 SPR_NOACCESS, &spr_write_generic,
1831 0x00000000);
1832 /* SPRGs */
1833 spr_register(env, SPR_USPRG0, "USPRG0",
1834 &spr_read_generic, &spr_write_generic,
1835 &spr_read_generic, &spr_write_generic,
1836 0x00000000);
1837 spr_register(env, SPR_SPRG4, "SPRG4",
1838 SPR_NOACCESS, SPR_NOACCESS,
1839 &spr_read_generic, &spr_write_generic,
1840 0x00000000);
1841 spr_register(env, SPR_SPRG5, "SPRG5",
1842 SPR_NOACCESS, SPR_NOACCESS,
1843 &spr_read_generic, &spr_write_generic,
1844 0x00000000);
1845 spr_register(env, SPR_SPRG6, "SPRG6",
1846 SPR_NOACCESS, SPR_NOACCESS,
1847 &spr_read_generic, &spr_write_generic,
1848 0x00000000);
1849 spr_register(env, SPR_SPRG7, "SPRG7",
1850 SPR_NOACCESS, SPR_NOACCESS,
1851 &spr_read_generic, &spr_write_generic,
1852 0x00000000);
1853 spr_register(env, SPR_BOOKE_SPRG8, "SPRG8",
1854 SPR_NOACCESS, SPR_NOACCESS,
1855 &spr_read_generic, &spr_write_generic,
1856 0x00000000);
1857 spr_register(env, SPR_BOOKE_SPRG9, "SPRG9",
1858 SPR_NOACCESS, SPR_NOACCESS,
1859 &spr_read_generic, &spr_write_generic,
1860 0x00000000);
1863 static inline uint32_t gen_tlbncfg(uint32_t assoc, uint32_t minsize,
1864 uint32_t maxsize, uint32_t flags,
1865 uint32_t nentries)
1867 return (assoc << TLBnCFG_ASSOC_SHIFT) |
1868 (minsize << TLBnCFG_MINSIZE_SHIFT) |
1869 (maxsize << TLBnCFG_MAXSIZE_SHIFT) |
1870 flags | nentries;
1873 /* BookE 2.06 storage control registers */
1874 static void gen_spr_BookE206(CPUPPCState *env, uint32_t mas_mask,
1875 uint32_t *tlbncfg, uint32_t mmucfg)
1877 #if !defined(CONFIG_USER_ONLY)
1878 const char *mas_names[8] = {
1879 "MAS0", "MAS1", "MAS2", "MAS3", "MAS4", "MAS5", "MAS6", "MAS7",
1881 int mas_sprn[8] = {
1882 SPR_BOOKE_MAS0, SPR_BOOKE_MAS1, SPR_BOOKE_MAS2, SPR_BOOKE_MAS3,
1883 SPR_BOOKE_MAS4, SPR_BOOKE_MAS5, SPR_BOOKE_MAS6, SPR_BOOKE_MAS7,
1885 int i;
1887 /* TLB assist registers */
1888 /* XXX : not implemented */
1889 for (i = 0; i < 8; i++) {
1890 void (*uea_write)(DisasContext *ctx, int sprn, int gprn) = &spr_write_generic32;
1891 if (i == 2 && (mas_mask & (1 << i)) && (env->insns_flags & PPC_64B)) {
1892 uea_write = &spr_write_generic;
1894 if (mas_mask & (1 << i)) {
1895 spr_register(env, mas_sprn[i], mas_names[i],
1896 SPR_NOACCESS, SPR_NOACCESS,
1897 &spr_read_generic, uea_write,
1898 0x00000000);
1901 if (env->nb_pids > 1) {
1902 /* XXX : not implemented */
1903 spr_register(env, SPR_BOOKE_PID1, "PID1",
1904 SPR_NOACCESS, SPR_NOACCESS,
1905 &spr_read_generic, &spr_write_booke_pid,
1906 0x00000000);
1908 if (env->nb_pids > 2) {
1909 /* XXX : not implemented */
1910 spr_register(env, SPR_BOOKE_PID2, "PID2",
1911 SPR_NOACCESS, SPR_NOACCESS,
1912 &spr_read_generic, &spr_write_booke_pid,
1913 0x00000000);
1915 /* XXX : not implemented */
1916 spr_register(env, SPR_MMUCFG, "MMUCFG",
1917 SPR_NOACCESS, SPR_NOACCESS,
1918 &spr_read_generic, SPR_NOACCESS,
1919 mmucfg);
1920 switch (env->nb_ways) {
1921 case 4:
1922 spr_register(env, SPR_BOOKE_TLB3CFG, "TLB3CFG",
1923 SPR_NOACCESS, SPR_NOACCESS,
1924 &spr_read_generic, SPR_NOACCESS,
1925 tlbncfg[3]);
1926 /* Fallthru */
1927 case 3:
1928 spr_register(env, SPR_BOOKE_TLB2CFG, "TLB2CFG",
1929 SPR_NOACCESS, SPR_NOACCESS,
1930 &spr_read_generic, SPR_NOACCESS,
1931 tlbncfg[2]);
1932 /* Fallthru */
1933 case 2:
1934 spr_register(env, SPR_BOOKE_TLB1CFG, "TLB1CFG",
1935 SPR_NOACCESS, SPR_NOACCESS,
1936 &spr_read_generic, SPR_NOACCESS,
1937 tlbncfg[1]);
1938 /* Fallthru */
1939 case 1:
1940 spr_register(env, SPR_BOOKE_TLB0CFG, "TLB0CFG",
1941 SPR_NOACCESS, SPR_NOACCESS,
1942 &spr_read_generic, SPR_NOACCESS,
1943 tlbncfg[0]);
1944 /* Fallthru */
1945 case 0:
1946 default:
1947 break;
1949 #endif
1951 gen_spr_usprgh(env);
1954 /* SPR specific to PowerPC 440 implementation */
1955 static void gen_spr_440(CPUPPCState *env)
1957 /* Cache control */
1958 /* XXX : not implemented */
1959 spr_register(env, SPR_440_DNV0, "DNV0",
1960 SPR_NOACCESS, SPR_NOACCESS,
1961 &spr_read_generic, &spr_write_generic,
1962 0x00000000);
1963 /* XXX : not implemented */
1964 spr_register(env, SPR_440_DNV1, "DNV1",
1965 SPR_NOACCESS, SPR_NOACCESS,
1966 &spr_read_generic, &spr_write_generic,
1967 0x00000000);
1968 /* XXX : not implemented */
1969 spr_register(env, SPR_440_DNV2, "DNV2",
1970 SPR_NOACCESS, SPR_NOACCESS,
1971 &spr_read_generic, &spr_write_generic,
1972 0x00000000);
1973 /* XXX : not implemented */
1974 spr_register(env, SPR_440_DNV3, "DNV3",
1975 SPR_NOACCESS, SPR_NOACCESS,
1976 &spr_read_generic, &spr_write_generic,
1977 0x00000000);
1978 /* XXX : not implemented */
1979 spr_register(env, SPR_440_DTV0, "DTV0",
1980 SPR_NOACCESS, SPR_NOACCESS,
1981 &spr_read_generic, &spr_write_generic,
1982 0x00000000);
1983 /* XXX : not implemented */
1984 spr_register(env, SPR_440_DTV1, "DTV1",
1985 SPR_NOACCESS, SPR_NOACCESS,
1986 &spr_read_generic, &spr_write_generic,
1987 0x00000000);
1988 /* XXX : not implemented */
1989 spr_register(env, SPR_440_DTV2, "DTV2",
1990 SPR_NOACCESS, SPR_NOACCESS,
1991 &spr_read_generic, &spr_write_generic,
1992 0x00000000);
1993 /* XXX : not implemented */
1994 spr_register(env, SPR_440_DTV3, "DTV3",
1995 SPR_NOACCESS, SPR_NOACCESS,
1996 &spr_read_generic, &spr_write_generic,
1997 0x00000000);
1998 /* XXX : not implemented */
1999 spr_register(env, SPR_440_DVLIM, "DVLIM",
2000 SPR_NOACCESS, SPR_NOACCESS,
2001 &spr_read_generic, &spr_write_generic,
2002 0x00000000);
2003 /* XXX : not implemented */
2004 spr_register(env, SPR_440_INV0, "INV0",
2005 SPR_NOACCESS, SPR_NOACCESS,
2006 &spr_read_generic, &spr_write_generic,
2007 0x00000000);
2008 /* XXX : not implemented */
2009 spr_register(env, SPR_440_INV1, "INV1",
2010 SPR_NOACCESS, SPR_NOACCESS,
2011 &spr_read_generic, &spr_write_generic,
2012 0x00000000);
2013 /* XXX : not implemented */
2014 spr_register(env, SPR_440_INV2, "INV2",
2015 SPR_NOACCESS, SPR_NOACCESS,
2016 &spr_read_generic, &spr_write_generic,
2017 0x00000000);
2018 /* XXX : not implemented */
2019 spr_register(env, SPR_440_INV3, "INV3",
2020 SPR_NOACCESS, SPR_NOACCESS,
2021 &spr_read_generic, &spr_write_generic,
2022 0x00000000);
2023 /* XXX : not implemented */
2024 spr_register(env, SPR_440_ITV0, "ITV0",
2025 SPR_NOACCESS, SPR_NOACCESS,
2026 &spr_read_generic, &spr_write_generic,
2027 0x00000000);
2028 /* XXX : not implemented */
2029 spr_register(env, SPR_440_ITV1, "ITV1",
2030 SPR_NOACCESS, SPR_NOACCESS,
2031 &spr_read_generic, &spr_write_generic,
2032 0x00000000);
2033 /* XXX : not implemented */
2034 spr_register(env, SPR_440_ITV2, "ITV2",
2035 SPR_NOACCESS, SPR_NOACCESS,
2036 &spr_read_generic, &spr_write_generic,
2037 0x00000000);
2038 /* XXX : not implemented */
2039 spr_register(env, SPR_440_ITV3, "ITV3",
2040 SPR_NOACCESS, SPR_NOACCESS,
2041 &spr_read_generic, &spr_write_generic,
2042 0x00000000);
2043 /* XXX : not implemented */
2044 spr_register(env, SPR_440_IVLIM, "IVLIM",
2045 SPR_NOACCESS, SPR_NOACCESS,
2046 &spr_read_generic, &spr_write_generic,
2047 0x00000000);
2048 /* Cache debug */
2049 /* XXX : not implemented */
2050 spr_register(env, SPR_BOOKE_DCDBTRH, "DCDBTRH",
2051 SPR_NOACCESS, SPR_NOACCESS,
2052 &spr_read_generic, SPR_NOACCESS,
2053 0x00000000);
2054 /* XXX : not implemented */
2055 spr_register(env, SPR_BOOKE_DCDBTRL, "DCDBTRL",
2056 SPR_NOACCESS, SPR_NOACCESS,
2057 &spr_read_generic, SPR_NOACCESS,
2058 0x00000000);
2059 /* XXX : not implemented */
2060 spr_register(env, SPR_BOOKE_ICDBDR, "ICDBDR",
2061 SPR_NOACCESS, SPR_NOACCESS,
2062 &spr_read_generic, SPR_NOACCESS,
2063 0x00000000);
2064 /* XXX : not implemented */
2065 spr_register(env, SPR_BOOKE_ICDBTRH, "ICDBTRH",
2066 SPR_NOACCESS, SPR_NOACCESS,
2067 &spr_read_generic, SPR_NOACCESS,
2068 0x00000000);
2069 /* XXX : not implemented */
2070 spr_register(env, SPR_BOOKE_ICDBTRL, "ICDBTRL",
2071 SPR_NOACCESS, SPR_NOACCESS,
2072 &spr_read_generic, SPR_NOACCESS,
2073 0x00000000);
2074 /* XXX : not implemented */
2075 spr_register(env, SPR_440_DBDR, "DBDR",
2076 SPR_NOACCESS, SPR_NOACCESS,
2077 &spr_read_generic, &spr_write_generic,
2078 0x00000000);
2079 /* Processor control */
2080 spr_register(env, SPR_4xx_CCR0, "CCR0",
2081 SPR_NOACCESS, SPR_NOACCESS,
2082 &spr_read_generic, &spr_write_generic,
2083 0x00000000);
2084 spr_register(env, SPR_440_RSTCFG, "RSTCFG",
2085 SPR_NOACCESS, SPR_NOACCESS,
2086 &spr_read_generic, SPR_NOACCESS,
2087 0x00000000);
2088 /* Storage control */
2089 spr_register(env, SPR_440_MMUCR, "MMUCR",
2090 SPR_NOACCESS, SPR_NOACCESS,
2091 &spr_read_generic, &spr_write_generic,
2092 0x00000000);
2095 /* SPR shared between PowerPC 40x implementations */
2096 static void gen_spr_40x(CPUPPCState *env)
2098 /* Cache */
2099 /* not emulated, as QEMU do not emulate caches */
2100 spr_register(env, SPR_40x_DCCR, "DCCR",
2101 SPR_NOACCESS, SPR_NOACCESS,
2102 &spr_read_generic, &spr_write_generic,
2103 0x00000000);
2104 /* not emulated, as QEMU do not emulate caches */
2105 spr_register(env, SPR_40x_ICCR, "ICCR",
2106 SPR_NOACCESS, SPR_NOACCESS,
2107 &spr_read_generic, &spr_write_generic,
2108 0x00000000);
2109 /* not emulated, as QEMU do not emulate caches */
2110 spr_register(env, SPR_BOOKE_ICDBDR, "ICDBDR",
2111 SPR_NOACCESS, SPR_NOACCESS,
2112 &spr_read_generic, SPR_NOACCESS,
2113 0x00000000);
2114 /* Exception */
2115 spr_register(env, SPR_40x_DEAR, "DEAR",
2116 SPR_NOACCESS, SPR_NOACCESS,
2117 &spr_read_generic, &spr_write_generic,
2118 0x00000000);
2119 spr_register(env, SPR_40x_ESR, "ESR",
2120 SPR_NOACCESS, SPR_NOACCESS,
2121 &spr_read_generic, &spr_write_generic,
2122 0x00000000);
2123 spr_register(env, SPR_40x_EVPR, "EVPR",
2124 SPR_NOACCESS, SPR_NOACCESS,
2125 &spr_read_generic, &spr_write_excp_prefix,
2126 0x00000000);
2127 spr_register(env, SPR_40x_SRR2, "SRR2",
2128 &spr_read_generic, &spr_write_generic,
2129 &spr_read_generic, &spr_write_generic,
2130 0x00000000);
2131 spr_register(env, SPR_40x_SRR3, "SRR3",
2132 &spr_read_generic, &spr_write_generic,
2133 &spr_read_generic, &spr_write_generic,
2134 0x00000000);
2135 /* Timers */
2136 spr_register(env, SPR_40x_PIT, "PIT",
2137 SPR_NOACCESS, SPR_NOACCESS,
2138 &spr_read_40x_pit, &spr_write_40x_pit,
2139 0x00000000);
2140 spr_register(env, SPR_40x_TCR, "TCR",
2141 SPR_NOACCESS, SPR_NOACCESS,
2142 &spr_read_generic, &spr_write_booke_tcr,
2143 0x00000000);
2144 spr_register(env, SPR_40x_TSR, "TSR",
2145 SPR_NOACCESS, SPR_NOACCESS,
2146 &spr_read_generic, &spr_write_booke_tsr,
2147 0x00000000);
2150 /* SPR specific to PowerPC 405 implementation */
2151 static void gen_spr_405(CPUPPCState *env)
2153 /* MMU */
2154 spr_register(env, SPR_40x_PID, "PID",
2155 SPR_NOACCESS, SPR_NOACCESS,
2156 &spr_read_generic, &spr_write_generic,
2157 0x00000000);
2158 spr_register(env, SPR_4xx_CCR0, "CCR0",
2159 SPR_NOACCESS, SPR_NOACCESS,
2160 &spr_read_generic, &spr_write_generic,
2161 0x00700000);
2162 /* Debug interface */
2163 /* XXX : not implemented */
2164 spr_register(env, SPR_40x_DBCR0, "DBCR0",
2165 SPR_NOACCESS, SPR_NOACCESS,
2166 &spr_read_generic, &spr_write_40x_dbcr0,
2167 0x00000000);
2168 /* XXX : not implemented */
2169 spr_register(env, SPR_405_DBCR1, "DBCR1",
2170 SPR_NOACCESS, SPR_NOACCESS,
2171 &spr_read_generic, &spr_write_generic,
2172 0x00000000);
2173 /* XXX : not implemented */
2174 spr_register(env, SPR_40x_DBSR, "DBSR",
2175 SPR_NOACCESS, SPR_NOACCESS,
2176 &spr_read_generic, &spr_write_clear,
2177 /* Last reset was system reset */
2178 0x00000300);
2179 /* XXX : not implemented */
2180 spr_register(env, SPR_40x_DAC1, "DAC1",
2181 SPR_NOACCESS, SPR_NOACCESS,
2182 &spr_read_generic, &spr_write_generic,
2183 0x00000000);
2184 spr_register(env, SPR_40x_DAC2, "DAC2",
2185 SPR_NOACCESS, SPR_NOACCESS,
2186 &spr_read_generic, &spr_write_generic,
2187 0x00000000);
2188 /* XXX : not implemented */
2189 spr_register(env, SPR_405_DVC1, "DVC1",
2190 SPR_NOACCESS, SPR_NOACCESS,
2191 &spr_read_generic, &spr_write_generic,
2192 0x00000000);
2193 /* XXX : not implemented */
2194 spr_register(env, SPR_405_DVC2, "DVC2",
2195 SPR_NOACCESS, SPR_NOACCESS,
2196 &spr_read_generic, &spr_write_generic,
2197 0x00000000);
2198 /* XXX : not implemented */
2199 spr_register(env, SPR_40x_IAC1, "IAC1",
2200 SPR_NOACCESS, SPR_NOACCESS,
2201 &spr_read_generic, &spr_write_generic,
2202 0x00000000);
2203 spr_register(env, SPR_40x_IAC2, "IAC2",
2204 SPR_NOACCESS, SPR_NOACCESS,
2205 &spr_read_generic, &spr_write_generic,
2206 0x00000000);
2207 /* XXX : not implemented */
2208 spr_register(env, SPR_405_IAC3, "IAC3",
2209 SPR_NOACCESS, SPR_NOACCESS,
2210 &spr_read_generic, &spr_write_generic,
2211 0x00000000);
2212 /* XXX : not implemented */
2213 spr_register(env, SPR_405_IAC4, "IAC4",
2214 SPR_NOACCESS, SPR_NOACCESS,
2215 &spr_read_generic, &spr_write_generic,
2216 0x00000000);
2217 /* Storage control */
2218 /* XXX: TODO: not implemented */
2219 spr_register(env, SPR_405_SLER, "SLER",
2220 SPR_NOACCESS, SPR_NOACCESS,
2221 &spr_read_generic, &spr_write_40x_sler,
2222 0x00000000);
2223 spr_register(env, SPR_40x_ZPR, "ZPR",
2224 SPR_NOACCESS, SPR_NOACCESS,
2225 &spr_read_generic, &spr_write_generic,
2226 0x00000000);
2227 /* XXX : not implemented */
2228 spr_register(env, SPR_405_SU0R, "SU0R",
2229 SPR_NOACCESS, SPR_NOACCESS,
2230 &spr_read_generic, &spr_write_generic,
2231 0x00000000);
2232 /* SPRG */
2233 spr_register(env, SPR_USPRG0, "USPRG0",
2234 &spr_read_ureg, SPR_NOACCESS,
2235 &spr_read_ureg, SPR_NOACCESS,
2236 0x00000000);
2237 spr_register(env, SPR_SPRG4, "SPRG4",
2238 SPR_NOACCESS, SPR_NOACCESS,
2239 &spr_read_generic, &spr_write_generic,
2240 0x00000000);
2241 spr_register(env, SPR_SPRG5, "SPRG5",
2242 SPR_NOACCESS, SPR_NOACCESS,
2243 spr_read_generic, &spr_write_generic,
2244 0x00000000);
2245 spr_register(env, SPR_SPRG6, "SPRG6",
2246 SPR_NOACCESS, SPR_NOACCESS,
2247 spr_read_generic, &spr_write_generic,
2248 0x00000000);
2249 spr_register(env, SPR_SPRG7, "SPRG7",
2250 SPR_NOACCESS, SPR_NOACCESS,
2251 spr_read_generic, &spr_write_generic,
2252 0x00000000);
2253 gen_spr_usprgh(env);
2256 /* SPR shared between PowerPC 401 & 403 implementations */
2257 static void gen_spr_401_403(CPUPPCState *env)
2259 /* Time base */
2260 spr_register(env, SPR_403_VTBL, "TBL",
2261 &spr_read_tbl, SPR_NOACCESS,
2262 &spr_read_tbl, SPR_NOACCESS,
2263 0x00000000);
2264 spr_register(env, SPR_403_TBL, "TBL",
2265 SPR_NOACCESS, SPR_NOACCESS,
2266 SPR_NOACCESS, &spr_write_tbl,
2267 0x00000000);
2268 spr_register(env, SPR_403_VTBU, "TBU",
2269 &spr_read_tbu, SPR_NOACCESS,
2270 &spr_read_tbu, SPR_NOACCESS,
2271 0x00000000);
2272 spr_register(env, SPR_403_TBU, "TBU",
2273 SPR_NOACCESS, SPR_NOACCESS,
2274 SPR_NOACCESS, &spr_write_tbu,
2275 0x00000000);
2276 /* Debug */
2277 /* not emulated, as QEMU do not emulate caches */
2278 spr_register(env, SPR_403_CDBCR, "CDBCR",
2279 SPR_NOACCESS, SPR_NOACCESS,
2280 &spr_read_generic, &spr_write_generic,
2281 0x00000000);
2284 /* SPR specific to PowerPC 401 implementation */
2285 static void gen_spr_401(CPUPPCState *env)
2287 /* Debug interface */
2288 /* XXX : not implemented */
2289 spr_register(env, SPR_40x_DBCR0, "DBCR",
2290 SPR_NOACCESS, SPR_NOACCESS,
2291 &spr_read_generic, &spr_write_40x_dbcr0,
2292 0x00000000);
2293 /* XXX : not implemented */
2294 spr_register(env, SPR_40x_DBSR, "DBSR",
2295 SPR_NOACCESS, SPR_NOACCESS,
2296 &spr_read_generic, &spr_write_clear,
2297 /* Last reset was system reset */
2298 0x00000300);
2299 /* XXX : not implemented */
2300 spr_register(env, SPR_40x_DAC1, "DAC",
2301 SPR_NOACCESS, SPR_NOACCESS,
2302 &spr_read_generic, &spr_write_generic,
2303 0x00000000);
2304 /* XXX : not implemented */
2305 spr_register(env, SPR_40x_IAC1, "IAC",
2306 SPR_NOACCESS, SPR_NOACCESS,
2307 &spr_read_generic, &spr_write_generic,
2308 0x00000000);
2309 /* Storage control */
2310 /* XXX: TODO: not implemented */
2311 spr_register(env, SPR_405_SLER, "SLER",
2312 SPR_NOACCESS, SPR_NOACCESS,
2313 &spr_read_generic, &spr_write_40x_sler,
2314 0x00000000);
2315 /* not emulated, as QEMU never does speculative access */
2316 spr_register(env, SPR_40x_SGR, "SGR",
2317 SPR_NOACCESS, SPR_NOACCESS,
2318 &spr_read_generic, &spr_write_generic,
2319 0xFFFFFFFF);
2320 /* not emulated, as QEMU do not emulate caches */
2321 spr_register(env, SPR_40x_DCWR, "DCWR",
2322 SPR_NOACCESS, SPR_NOACCESS,
2323 &spr_read_generic, &spr_write_generic,
2324 0x00000000);
2327 static void gen_spr_401x2(CPUPPCState *env)
2329 gen_spr_401(env);
2330 spr_register(env, SPR_40x_PID, "PID",
2331 SPR_NOACCESS, SPR_NOACCESS,
2332 &spr_read_generic, &spr_write_generic,
2333 0x00000000);
2334 spr_register(env, SPR_40x_ZPR, "ZPR",
2335 SPR_NOACCESS, SPR_NOACCESS,
2336 &spr_read_generic, &spr_write_generic,
2337 0x00000000);
2340 /* SPR specific to PowerPC 403 implementation */
2341 static void gen_spr_403(CPUPPCState *env)
2343 /* Debug interface */
2344 /* XXX : not implemented */
2345 spr_register(env, SPR_40x_DBCR0, "DBCR0",
2346 SPR_NOACCESS, SPR_NOACCESS,
2347 &spr_read_generic, &spr_write_40x_dbcr0,
2348 0x00000000);
2349 /* XXX : not implemented */
2350 spr_register(env, SPR_40x_DBSR, "DBSR",
2351 SPR_NOACCESS, SPR_NOACCESS,
2352 &spr_read_generic, &spr_write_clear,
2353 /* Last reset was system reset */
2354 0x00000300);
2355 /* XXX : not implemented */
2356 spr_register(env, SPR_40x_DAC1, "DAC1",
2357 SPR_NOACCESS, SPR_NOACCESS,
2358 &spr_read_generic, &spr_write_generic,
2359 0x00000000);
2360 /* XXX : not implemented */
2361 spr_register(env, SPR_40x_DAC2, "DAC2",
2362 SPR_NOACCESS, SPR_NOACCESS,
2363 &spr_read_generic, &spr_write_generic,
2364 0x00000000);
2365 /* XXX : not implemented */
2366 spr_register(env, SPR_40x_IAC1, "IAC1",
2367 SPR_NOACCESS, SPR_NOACCESS,
2368 &spr_read_generic, &spr_write_generic,
2369 0x00000000);
2370 /* XXX : not implemented */
2371 spr_register(env, SPR_40x_IAC2, "IAC2",
2372 SPR_NOACCESS, SPR_NOACCESS,
2373 &spr_read_generic, &spr_write_generic,
2374 0x00000000);
2377 static void gen_spr_403_real(CPUPPCState *env)
2379 spr_register(env, SPR_403_PBL1, "PBL1",
2380 SPR_NOACCESS, SPR_NOACCESS,
2381 &spr_read_403_pbr, &spr_write_403_pbr,
2382 0x00000000);
2383 spr_register(env, SPR_403_PBU1, "PBU1",
2384 SPR_NOACCESS, SPR_NOACCESS,
2385 &spr_read_403_pbr, &spr_write_403_pbr,
2386 0x00000000);
2387 spr_register(env, SPR_403_PBL2, "PBL2",
2388 SPR_NOACCESS, SPR_NOACCESS,
2389 &spr_read_403_pbr, &spr_write_403_pbr,
2390 0x00000000);
2391 spr_register(env, SPR_403_PBU2, "PBU2",
2392 SPR_NOACCESS, SPR_NOACCESS,
2393 &spr_read_403_pbr, &spr_write_403_pbr,
2394 0x00000000);
2397 static void gen_spr_403_mmu(CPUPPCState *env)
2399 /* MMU */
2400 spr_register(env, SPR_40x_PID, "PID",
2401 SPR_NOACCESS, SPR_NOACCESS,
2402 &spr_read_generic, &spr_write_generic,
2403 0x00000000);
2404 spr_register(env, SPR_40x_ZPR, "ZPR",
2405 SPR_NOACCESS, SPR_NOACCESS,
2406 &spr_read_generic, &spr_write_generic,
2407 0x00000000);
2410 /* SPR specific to PowerPC compression coprocessor extension */
2411 static void gen_spr_compress(CPUPPCState *env)
2413 /* XXX : not implemented */
2414 spr_register(env, SPR_401_SKR, "SKR",
2415 SPR_NOACCESS, SPR_NOACCESS,
2416 &spr_read_generic, &spr_write_generic,
2417 0x00000000);
2420 static void gen_spr_5xx_8xx(CPUPPCState *env)
2422 /* Exception processing */
2423 spr_register_kvm(env, SPR_DSISR, "DSISR",
2424 SPR_NOACCESS, SPR_NOACCESS,
2425 &spr_read_generic, &spr_write_generic,
2426 KVM_REG_PPC_DSISR, 0x00000000);
2427 spr_register_kvm(env, SPR_DAR, "DAR",
2428 SPR_NOACCESS, SPR_NOACCESS,
2429 &spr_read_generic, &spr_write_generic,
2430 KVM_REG_PPC_DAR, 0x00000000);
2431 /* Timer */
2432 spr_register(env, SPR_DECR, "DECR",
2433 SPR_NOACCESS, SPR_NOACCESS,
2434 &spr_read_decr, &spr_write_decr,
2435 0x00000000);
2436 /* XXX : not implemented */
2437 spr_register(env, SPR_MPC_EIE, "EIE",
2438 SPR_NOACCESS, SPR_NOACCESS,
2439 &spr_read_generic, &spr_write_generic,
2440 0x00000000);
2441 /* XXX : not implemented */
2442 spr_register(env, SPR_MPC_EID, "EID",
2443 SPR_NOACCESS, SPR_NOACCESS,
2444 &spr_read_generic, &spr_write_generic,
2445 0x00000000);
2446 /* XXX : not implemented */
2447 spr_register(env, SPR_MPC_NRI, "NRI",
2448 SPR_NOACCESS, SPR_NOACCESS,
2449 &spr_read_generic, &spr_write_generic,
2450 0x00000000);
2451 /* XXX : not implemented */
2452 spr_register(env, SPR_MPC_CMPA, "CMPA",
2453 SPR_NOACCESS, SPR_NOACCESS,
2454 &spr_read_generic, &spr_write_generic,
2455 0x00000000);
2456 /* XXX : not implemented */
2457 spr_register(env, SPR_MPC_CMPB, "CMPB",
2458 SPR_NOACCESS, SPR_NOACCESS,
2459 &spr_read_generic, &spr_write_generic,
2460 0x00000000);
2461 /* XXX : not implemented */
2462 spr_register(env, SPR_MPC_CMPC, "CMPC",
2463 SPR_NOACCESS, SPR_NOACCESS,
2464 &spr_read_generic, &spr_write_generic,
2465 0x00000000);
2466 /* XXX : not implemented */
2467 spr_register(env, SPR_MPC_CMPD, "CMPD",
2468 SPR_NOACCESS, SPR_NOACCESS,
2469 &spr_read_generic, &spr_write_generic,
2470 0x00000000);
2471 /* XXX : not implemented */
2472 spr_register(env, SPR_MPC_ECR, "ECR",
2473 SPR_NOACCESS, SPR_NOACCESS,
2474 &spr_read_generic, &spr_write_generic,
2475 0x00000000);
2476 /* XXX : not implemented */
2477 spr_register(env, SPR_MPC_DER, "DER",
2478 SPR_NOACCESS, SPR_NOACCESS,
2479 &spr_read_generic, &spr_write_generic,
2480 0x00000000);
2481 /* XXX : not implemented */
2482 spr_register(env, SPR_MPC_COUNTA, "COUNTA",
2483 SPR_NOACCESS, SPR_NOACCESS,
2484 &spr_read_generic, &spr_write_generic,
2485 0x00000000);
2486 /* XXX : not implemented */
2487 spr_register(env, SPR_MPC_COUNTB, "COUNTB",
2488 SPR_NOACCESS, SPR_NOACCESS,
2489 &spr_read_generic, &spr_write_generic,
2490 0x00000000);
2491 /* XXX : not implemented */
2492 spr_register(env, SPR_MPC_CMPE, "CMPE",
2493 SPR_NOACCESS, SPR_NOACCESS,
2494 &spr_read_generic, &spr_write_generic,
2495 0x00000000);
2496 /* XXX : not implemented */
2497 spr_register(env, SPR_MPC_CMPF, "CMPF",
2498 SPR_NOACCESS, SPR_NOACCESS,
2499 &spr_read_generic, &spr_write_generic,
2500 0x00000000);
2501 /* XXX : not implemented */
2502 spr_register(env, SPR_MPC_CMPG, "CMPG",
2503 SPR_NOACCESS, SPR_NOACCESS,
2504 &spr_read_generic, &spr_write_generic,
2505 0x00000000);
2506 /* XXX : not implemented */
2507 spr_register(env, SPR_MPC_CMPH, "CMPH",
2508 SPR_NOACCESS, SPR_NOACCESS,
2509 &spr_read_generic, &spr_write_generic,
2510 0x00000000);
2511 /* XXX : not implemented */
2512 spr_register(env, SPR_MPC_LCTRL1, "LCTRL1",
2513 SPR_NOACCESS, SPR_NOACCESS,
2514 &spr_read_generic, &spr_write_generic,
2515 0x00000000);
2516 /* XXX : not implemented */
2517 spr_register(env, SPR_MPC_LCTRL2, "LCTRL2",
2518 SPR_NOACCESS, SPR_NOACCESS,
2519 &spr_read_generic, &spr_write_generic,
2520 0x00000000);
2521 /* XXX : not implemented */
2522 spr_register(env, SPR_MPC_BAR, "BAR",
2523 SPR_NOACCESS, SPR_NOACCESS,
2524 &spr_read_generic, &spr_write_generic,
2525 0x00000000);
2526 /* XXX : not implemented */
2527 spr_register(env, SPR_MPC_DPDR, "DPDR",
2528 SPR_NOACCESS, SPR_NOACCESS,
2529 &spr_read_generic, &spr_write_generic,
2530 0x00000000);
2531 /* XXX : not implemented */
2532 spr_register(env, SPR_MPC_IMMR, "IMMR",
2533 SPR_NOACCESS, SPR_NOACCESS,
2534 &spr_read_generic, &spr_write_generic,
2535 0x00000000);
2538 static void gen_spr_5xx(CPUPPCState *env)
2540 /* XXX : not implemented */
2541 spr_register(env, SPR_RCPU_MI_GRA, "MI_GRA",
2542 SPR_NOACCESS, SPR_NOACCESS,
2543 &spr_read_generic, &spr_write_generic,
2544 0x00000000);
2545 /* XXX : not implemented */
2546 spr_register(env, SPR_RCPU_L2U_GRA, "L2U_GRA",
2547 SPR_NOACCESS, SPR_NOACCESS,
2548 &spr_read_generic, &spr_write_generic,
2549 0x00000000);
2550 /* XXX : not implemented */
2551 spr_register(env, SPR_RPCU_BBCMCR, "L2U_BBCMCR",
2552 SPR_NOACCESS, SPR_NOACCESS,
2553 &spr_read_generic, &spr_write_generic,
2554 0x00000000);
2555 /* XXX : not implemented */
2556 spr_register(env, SPR_RCPU_L2U_MCR, "L2U_MCR",
2557 SPR_NOACCESS, SPR_NOACCESS,
2558 &spr_read_generic, &spr_write_generic,
2559 0x00000000);
2560 /* XXX : not implemented */
2561 spr_register(env, SPR_RCPU_MI_RBA0, "MI_RBA0",
2562 SPR_NOACCESS, SPR_NOACCESS,
2563 &spr_read_generic, &spr_write_generic,
2564 0x00000000);
2565 /* XXX : not implemented */
2566 spr_register(env, SPR_RCPU_MI_RBA1, "MI_RBA1",
2567 SPR_NOACCESS, SPR_NOACCESS,
2568 &spr_read_generic, &spr_write_generic,
2569 0x00000000);
2570 /* XXX : not implemented */
2571 spr_register(env, SPR_RCPU_MI_RBA2, "MI_RBA2",
2572 SPR_NOACCESS, SPR_NOACCESS,
2573 &spr_read_generic, &spr_write_generic,
2574 0x00000000);
2575 /* XXX : not implemented */
2576 spr_register(env, SPR_RCPU_MI_RBA3, "MI_RBA3",
2577 SPR_NOACCESS, SPR_NOACCESS,
2578 &spr_read_generic, &spr_write_generic,
2579 0x00000000);
2580 /* XXX : not implemented */
2581 spr_register(env, SPR_RCPU_L2U_RBA0, "L2U_RBA0",
2582 SPR_NOACCESS, SPR_NOACCESS,
2583 &spr_read_generic, &spr_write_generic,
2584 0x00000000);
2585 /* XXX : not implemented */
2586 spr_register(env, SPR_RCPU_L2U_RBA1, "L2U_RBA1",
2587 SPR_NOACCESS, SPR_NOACCESS,
2588 &spr_read_generic, &spr_write_generic,
2589 0x00000000);
2590 /* XXX : not implemented */
2591 spr_register(env, SPR_RCPU_L2U_RBA2, "L2U_RBA2",
2592 SPR_NOACCESS, SPR_NOACCESS,
2593 &spr_read_generic, &spr_write_generic,
2594 0x00000000);
2595 /* XXX : not implemented */
2596 spr_register(env, SPR_RCPU_L2U_RBA3, "L2U_RBA3",
2597 SPR_NOACCESS, SPR_NOACCESS,
2598 &spr_read_generic, &spr_write_generic,
2599 0x00000000);
2600 /* XXX : not implemented */
2601 spr_register(env, SPR_RCPU_MI_RA0, "MI_RA0",
2602 SPR_NOACCESS, SPR_NOACCESS,
2603 &spr_read_generic, &spr_write_generic,
2604 0x00000000);
2605 /* XXX : not implemented */
2606 spr_register(env, SPR_RCPU_MI_RA1, "MI_RA1",
2607 SPR_NOACCESS, SPR_NOACCESS,
2608 &spr_read_generic, &spr_write_generic,
2609 0x00000000);
2610 /* XXX : not implemented */
2611 spr_register(env, SPR_RCPU_MI_RA2, "MI_RA2",
2612 SPR_NOACCESS, SPR_NOACCESS,
2613 &spr_read_generic, &spr_write_generic,
2614 0x00000000);
2615 /* XXX : not implemented */
2616 spr_register(env, SPR_RCPU_MI_RA3, "MI_RA3",
2617 SPR_NOACCESS, SPR_NOACCESS,
2618 &spr_read_generic, &spr_write_generic,
2619 0x00000000);
2620 /* XXX : not implemented */
2621 spr_register(env, SPR_RCPU_L2U_RA0, "L2U_RA0",
2622 SPR_NOACCESS, SPR_NOACCESS,
2623 &spr_read_generic, &spr_write_generic,
2624 0x00000000);
2625 /* XXX : not implemented */
2626 spr_register(env, SPR_RCPU_L2U_RA1, "L2U_RA1",
2627 SPR_NOACCESS, SPR_NOACCESS,
2628 &spr_read_generic, &spr_write_generic,
2629 0x00000000);
2630 /* XXX : not implemented */
2631 spr_register(env, SPR_RCPU_L2U_RA2, "L2U_RA2",
2632 SPR_NOACCESS, SPR_NOACCESS,
2633 &spr_read_generic, &spr_write_generic,
2634 0x00000000);
2635 /* XXX : not implemented */
2636 spr_register(env, SPR_RCPU_L2U_RA3, "L2U_RA3",
2637 SPR_NOACCESS, SPR_NOACCESS,
2638 &spr_read_generic, &spr_write_generic,
2639 0x00000000);
2640 /* XXX : not implemented */
2641 spr_register(env, SPR_RCPU_FPECR, "FPECR",
2642 SPR_NOACCESS, SPR_NOACCESS,
2643 &spr_read_generic, &spr_write_generic,
2644 0x00000000);
2647 static void gen_spr_8xx(CPUPPCState *env)
2649 /* XXX : not implemented */
2650 spr_register(env, SPR_MPC_IC_CST, "IC_CST",
2651 SPR_NOACCESS, SPR_NOACCESS,
2652 &spr_read_generic, &spr_write_generic,
2653 0x00000000);
2654 /* XXX : not implemented */
2655 spr_register(env, SPR_MPC_IC_ADR, "IC_ADR",
2656 SPR_NOACCESS, SPR_NOACCESS,
2657 &spr_read_generic, &spr_write_generic,
2658 0x00000000);
2659 /* XXX : not implemented */
2660 spr_register(env, SPR_MPC_IC_DAT, "IC_DAT",
2661 SPR_NOACCESS, SPR_NOACCESS,
2662 &spr_read_generic, &spr_write_generic,
2663 0x00000000);
2664 /* XXX : not implemented */
2665 spr_register(env, SPR_MPC_DC_CST, "DC_CST",
2666 SPR_NOACCESS, SPR_NOACCESS,
2667 &spr_read_generic, &spr_write_generic,
2668 0x00000000);
2669 /* XXX : not implemented */
2670 spr_register(env, SPR_MPC_DC_ADR, "DC_ADR",
2671 SPR_NOACCESS, SPR_NOACCESS,
2672 &spr_read_generic, &spr_write_generic,
2673 0x00000000);
2674 /* XXX : not implemented */
2675 spr_register(env, SPR_MPC_DC_DAT, "DC_DAT",
2676 SPR_NOACCESS, SPR_NOACCESS,
2677 &spr_read_generic, &spr_write_generic,
2678 0x00000000);
2679 /* XXX : not implemented */
2680 spr_register(env, SPR_MPC_MI_CTR, "MI_CTR",
2681 SPR_NOACCESS, SPR_NOACCESS,
2682 &spr_read_generic, &spr_write_generic,
2683 0x00000000);
2684 /* XXX : not implemented */
2685 spr_register(env, SPR_MPC_MI_AP, "MI_AP",
2686 SPR_NOACCESS, SPR_NOACCESS,
2687 &spr_read_generic, &spr_write_generic,
2688 0x00000000);
2689 /* XXX : not implemented */
2690 spr_register(env, SPR_MPC_MI_EPN, "MI_EPN",
2691 SPR_NOACCESS, SPR_NOACCESS,
2692 &spr_read_generic, &spr_write_generic,
2693 0x00000000);
2694 /* XXX : not implemented */
2695 spr_register(env, SPR_MPC_MI_TWC, "MI_TWC",
2696 SPR_NOACCESS, SPR_NOACCESS,
2697 &spr_read_generic, &spr_write_generic,
2698 0x00000000);
2699 /* XXX : not implemented */
2700 spr_register(env, SPR_MPC_MI_RPN, "MI_RPN",
2701 SPR_NOACCESS, SPR_NOACCESS,
2702 &spr_read_generic, &spr_write_generic,
2703 0x00000000);
2704 /* XXX : not implemented */
2705 spr_register(env, SPR_MPC_MI_DBCAM, "MI_DBCAM",
2706 SPR_NOACCESS, SPR_NOACCESS,
2707 &spr_read_generic, &spr_write_generic,
2708 0x00000000);
2709 /* XXX : not implemented */
2710 spr_register(env, SPR_MPC_MI_DBRAM0, "MI_DBRAM0",
2711 SPR_NOACCESS, SPR_NOACCESS,
2712 &spr_read_generic, &spr_write_generic,
2713 0x00000000);
2714 /* XXX : not implemented */
2715 spr_register(env, SPR_MPC_MI_DBRAM1, "MI_DBRAM1",
2716 SPR_NOACCESS, SPR_NOACCESS,
2717 &spr_read_generic, &spr_write_generic,
2718 0x00000000);
2719 /* XXX : not implemented */
2720 spr_register(env, SPR_MPC_MD_CTR, "MD_CTR",
2721 SPR_NOACCESS, SPR_NOACCESS,
2722 &spr_read_generic, &spr_write_generic,
2723 0x00000000);
2724 /* XXX : not implemented */
2725 spr_register(env, SPR_MPC_MD_CASID, "MD_CASID",
2726 SPR_NOACCESS, SPR_NOACCESS,
2727 &spr_read_generic, &spr_write_generic,
2728 0x00000000);
2729 /* XXX : not implemented */
2730 spr_register(env, SPR_MPC_MD_AP, "MD_AP",
2731 SPR_NOACCESS, SPR_NOACCESS,
2732 &spr_read_generic, &spr_write_generic,
2733 0x00000000);
2734 /* XXX : not implemented */
2735 spr_register(env, SPR_MPC_MD_EPN, "MD_EPN",
2736 SPR_NOACCESS, SPR_NOACCESS,
2737 &spr_read_generic, &spr_write_generic,
2738 0x00000000);
2739 /* XXX : not implemented */
2740 spr_register(env, SPR_MPC_MD_TWB, "MD_TWB",
2741 SPR_NOACCESS, SPR_NOACCESS,
2742 &spr_read_generic, &spr_write_generic,
2743 0x00000000);
2744 /* XXX : not implemented */
2745 spr_register(env, SPR_MPC_MD_TWC, "MD_TWC",
2746 SPR_NOACCESS, SPR_NOACCESS,
2747 &spr_read_generic, &spr_write_generic,
2748 0x00000000);
2749 /* XXX : not implemented */
2750 spr_register(env, SPR_MPC_MD_RPN, "MD_RPN",
2751 SPR_NOACCESS, SPR_NOACCESS,
2752 &spr_read_generic, &spr_write_generic,
2753 0x00000000);
2754 /* XXX : not implemented */
2755 spr_register(env, SPR_MPC_MD_TW, "MD_TW",
2756 SPR_NOACCESS, SPR_NOACCESS,
2757 &spr_read_generic, &spr_write_generic,
2758 0x00000000);
2759 /* XXX : not implemented */
2760 spr_register(env, SPR_MPC_MD_DBCAM, "MD_DBCAM",
2761 SPR_NOACCESS, SPR_NOACCESS,
2762 &spr_read_generic, &spr_write_generic,
2763 0x00000000);
2764 /* XXX : not implemented */
2765 spr_register(env, SPR_MPC_MD_DBRAM0, "MD_DBRAM0",
2766 SPR_NOACCESS, SPR_NOACCESS,
2767 &spr_read_generic, &spr_write_generic,
2768 0x00000000);
2769 /* XXX : not implemented */
2770 spr_register(env, SPR_MPC_MD_DBRAM1, "MD_DBRAM1",
2771 SPR_NOACCESS, SPR_NOACCESS,
2772 &spr_read_generic, &spr_write_generic,
2773 0x00000000);
2776 // XXX: TODO
2778 * AMR => SPR 29 (Power 2.04)
2779 * CTRL => SPR 136 (Power 2.04)
2780 * CTRL => SPR 152 (Power 2.04)
2781 * SCOMC => SPR 276 (64 bits ?)
2782 * SCOMD => SPR 277 (64 bits ?)
2783 * TBU40 => SPR 286 (Power 2.04 hypv)
2784 * HSPRG0 => SPR 304 (Power 2.04 hypv)
2785 * HSPRG1 => SPR 305 (Power 2.04 hypv)
2786 * HDSISR => SPR 306 (Power 2.04 hypv)
2787 * HDAR => SPR 307 (Power 2.04 hypv)
2788 * PURR => SPR 309 (Power 2.04 hypv)
2789 * HDEC => SPR 310 (Power 2.04 hypv)
2790 * HIOR => SPR 311 (hypv)
2791 * RMOR => SPR 312 (970)
2792 * HRMOR => SPR 313 (Power 2.04 hypv)
2793 * HSRR0 => SPR 314 (Power 2.04 hypv)
2794 * HSRR1 => SPR 315 (Power 2.04 hypv)
2795 * LPIDR => SPR 317 (970)
2796 * EPR => SPR 702 (Power 2.04 emb)
2797 * perf => 768-783 (Power 2.04)
2798 * perf => 784-799 (Power 2.04)
2799 * PPR => SPR 896 (Power 2.04)
2800 * EPLC => SPR 947 (Power 2.04 emb)
2801 * EPSC => SPR 948 (Power 2.04 emb)
2802 * DABRX => 1015 (Power 2.04 hypv)
2803 * FPECR => SPR 1022 (?)
2804 * ... and more (thermal management, performance counters, ...)
2807 /*****************************************************************************/
2808 /* Exception vectors models */
2809 static void init_excp_4xx_real(CPUPPCState *env)
2811 #if !defined(CONFIG_USER_ONLY)
2812 env->excp_vectors[POWERPC_EXCP_CRITICAL] = 0x00000100;
2813 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2814 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2815 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2816 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2817 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2818 env->excp_vectors[POWERPC_EXCP_PIT] = 0x00001000;
2819 env->excp_vectors[POWERPC_EXCP_FIT] = 0x00001010;
2820 env->excp_vectors[POWERPC_EXCP_WDT] = 0x00001020;
2821 env->excp_vectors[POWERPC_EXCP_DEBUG] = 0x00002000;
2822 env->ivor_mask = 0x0000FFF0UL;
2823 env->ivpr_mask = 0xFFFF0000UL;
2824 /* Hardware reset vector */
2825 env->hreset_vector = 0xFFFFFFFCUL;
2826 #endif
2829 static void init_excp_4xx_softmmu(CPUPPCState *env)
2831 #if !defined(CONFIG_USER_ONLY)
2832 env->excp_vectors[POWERPC_EXCP_CRITICAL] = 0x00000100;
2833 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2834 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2835 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2836 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2837 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2838 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2839 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2840 env->excp_vectors[POWERPC_EXCP_PIT] = 0x00001000;
2841 env->excp_vectors[POWERPC_EXCP_FIT] = 0x00001010;
2842 env->excp_vectors[POWERPC_EXCP_WDT] = 0x00001020;
2843 env->excp_vectors[POWERPC_EXCP_DTLB] = 0x00001100;
2844 env->excp_vectors[POWERPC_EXCP_ITLB] = 0x00001200;
2845 env->excp_vectors[POWERPC_EXCP_DEBUG] = 0x00002000;
2846 env->ivor_mask = 0x0000FFF0UL;
2847 env->ivpr_mask = 0xFFFF0000UL;
2848 /* Hardware reset vector */
2849 env->hreset_vector = 0xFFFFFFFCUL;
2850 #endif
2853 static void init_excp_MPC5xx(CPUPPCState *env)
2855 #if !defined(CONFIG_USER_ONLY)
2856 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2857 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2858 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2859 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2860 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2861 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000900;
2862 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2863 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2864 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2865 env->excp_vectors[POWERPC_EXCP_FPA] = 0x00000E00;
2866 env->excp_vectors[POWERPC_EXCP_EMUL] = 0x00001000;
2867 env->excp_vectors[POWERPC_EXCP_DABR] = 0x00001C00;
2868 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001C00;
2869 env->excp_vectors[POWERPC_EXCP_MEXTBR] = 0x00001E00;
2870 env->excp_vectors[POWERPC_EXCP_NMEXTBR] = 0x00001F00;
2871 env->ivor_mask = 0x0000FFF0UL;
2872 env->ivpr_mask = 0xFFFF0000UL;
2873 /* Hardware reset vector */
2874 env->hreset_vector = 0x00000100UL;
2875 #endif
2878 static void init_excp_MPC8xx(CPUPPCState *env)
2880 #if !defined(CONFIG_USER_ONLY)
2881 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2882 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2883 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2884 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2885 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2886 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2887 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2888 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000900;
2889 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2890 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2891 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2892 env->excp_vectors[POWERPC_EXCP_FPA] = 0x00000E00;
2893 env->excp_vectors[POWERPC_EXCP_EMUL] = 0x00001000;
2894 env->excp_vectors[POWERPC_EXCP_ITLB] = 0x00001100;
2895 env->excp_vectors[POWERPC_EXCP_DTLB] = 0x00001200;
2896 env->excp_vectors[POWERPC_EXCP_ITLBE] = 0x00001300;
2897 env->excp_vectors[POWERPC_EXCP_DTLBE] = 0x00001400;
2898 env->excp_vectors[POWERPC_EXCP_DABR] = 0x00001C00;
2899 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001C00;
2900 env->excp_vectors[POWERPC_EXCP_MEXTBR] = 0x00001E00;
2901 env->excp_vectors[POWERPC_EXCP_NMEXTBR] = 0x00001F00;
2902 env->ivor_mask = 0x0000FFF0UL;
2903 env->ivpr_mask = 0xFFFF0000UL;
2904 /* Hardware reset vector */
2905 env->hreset_vector = 0x00000100UL;
2906 #endif
2909 static void init_excp_G2(CPUPPCState *env)
2911 #if !defined(CONFIG_USER_ONLY)
2912 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2913 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2914 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2915 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2916 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2917 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2918 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
2919 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
2920 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
2921 env->excp_vectors[POWERPC_EXCP_CRITICAL] = 0x00000A00;
2922 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
2923 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
2924 env->excp_vectors[POWERPC_EXCP_IFTLB] = 0x00001000;
2925 env->excp_vectors[POWERPC_EXCP_DLTLB] = 0x00001100;
2926 env->excp_vectors[POWERPC_EXCP_DSTLB] = 0x00001200;
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;
2931 #endif
2934 static void init_excp_e200(CPUPPCState *env, target_ulong ivpr_mask)
2936 #if !defined(CONFIG_USER_ONLY)
2937 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000FFC;
2938 env->excp_vectors[POWERPC_EXCP_CRITICAL] = 0x00000000;
2939 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000000;
2940 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000000;
2941 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000000;
2942 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000000;
2943 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000000;
2944 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000000;
2945 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000000;
2946 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000000;
2947 env->excp_vectors[POWERPC_EXCP_APU] = 0x00000000;
2948 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000000;
2949 env->excp_vectors[POWERPC_EXCP_FIT] = 0x00000000;
2950 env->excp_vectors[POWERPC_EXCP_WDT] = 0x00000000;
2951 env->excp_vectors[POWERPC_EXCP_DTLB] = 0x00000000;
2952 env->excp_vectors[POWERPC_EXCP_ITLB] = 0x00000000;
2953 env->excp_vectors[POWERPC_EXCP_DEBUG] = 0x00000000;
2954 env->excp_vectors[POWERPC_EXCP_SPEU] = 0x00000000;
2955 env->excp_vectors[POWERPC_EXCP_EFPDI] = 0x00000000;
2956 env->excp_vectors[POWERPC_EXCP_EFPRI] = 0x00000000;
2957 env->ivor_mask = 0x0000FFF7UL;
2958 env->ivpr_mask = ivpr_mask;
2959 /* Hardware reset vector */
2960 env->hreset_vector = 0xFFFFFFFCUL;
2961 #endif
2964 static void init_excp_BookE(CPUPPCState *env)
2966 #if !defined(CONFIG_USER_ONLY)
2967 env->excp_vectors[POWERPC_EXCP_CRITICAL] = 0x00000000;
2968 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000000;
2969 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000000;
2970 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000000;
2971 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000000;
2972 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000000;
2973 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000000;
2974 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000000;
2975 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000000;
2976 env->excp_vectors[POWERPC_EXCP_APU] = 0x00000000;
2977 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000000;
2978 env->excp_vectors[POWERPC_EXCP_FIT] = 0x00000000;
2979 env->excp_vectors[POWERPC_EXCP_WDT] = 0x00000000;
2980 env->excp_vectors[POWERPC_EXCP_DTLB] = 0x00000000;
2981 env->excp_vectors[POWERPC_EXCP_ITLB] = 0x00000000;
2982 env->excp_vectors[POWERPC_EXCP_DEBUG] = 0x00000000;
2983 env->ivor_mask = 0x0000FFF0UL;
2984 env->ivpr_mask = 0xFFFF0000UL;
2985 /* Hardware reset vector */
2986 env->hreset_vector = 0xFFFFFFFCUL;
2987 #endif
2990 static void init_excp_601(CPUPPCState *env)
2992 #if !defined(CONFIG_USER_ONLY)
2993 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
2994 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
2995 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
2996 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
2997 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
2998 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
2999 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3000 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3001 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3002 env->excp_vectors[POWERPC_EXCP_IO] = 0x00000A00;
3003 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3004 env->excp_vectors[POWERPC_EXCP_RUNM] = 0x00002000;
3005 /* Hardware reset vector */
3006 env->hreset_vector = 0x00000100UL;
3007 #endif
3010 static void init_excp_602(CPUPPCState *env)
3012 #if !defined(CONFIG_USER_ONLY)
3013 /* XXX: exception prefix has a special behavior on 602 */
3014 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3015 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3016 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3017 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3018 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3019 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3020 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3021 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3022 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3023 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3024 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3025 env->excp_vectors[POWERPC_EXCP_IFTLB] = 0x00001000;
3026 env->excp_vectors[POWERPC_EXCP_DLTLB] = 0x00001100;
3027 env->excp_vectors[POWERPC_EXCP_DSTLB] = 0x00001200;
3028 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3029 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
3030 env->excp_vectors[POWERPC_EXCP_WDT] = 0x00001500;
3031 env->excp_vectors[POWERPC_EXCP_EMUL] = 0x00001600;
3032 /* Hardware reset vector */
3033 env->hreset_vector = 0x00000100UL;
3034 #endif
3037 static void init_excp_603(CPUPPCState *env)
3039 #if !defined(CONFIG_USER_ONLY)
3040 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3041 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3042 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3043 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3044 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3045 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3046 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3047 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3048 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3049 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3050 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3051 env->excp_vectors[POWERPC_EXCP_IFTLB] = 0x00001000;
3052 env->excp_vectors[POWERPC_EXCP_DLTLB] = 0x00001100;
3053 env->excp_vectors[POWERPC_EXCP_DSTLB] = 0x00001200;
3054 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3055 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
3056 /* Hardware reset vector */
3057 env->hreset_vector = 0x00000100UL;
3058 #endif
3061 static void init_excp_604(CPUPPCState *env)
3063 #if !defined(CONFIG_USER_ONLY)
3064 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3065 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3066 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3067 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3068 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3069 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3070 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3071 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3072 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3073 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3074 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3075 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3076 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3077 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
3078 /* Hardware reset vector */
3079 env->hreset_vector = 0x00000100UL;
3080 #endif
3083 static void init_excp_7x0(CPUPPCState *env)
3085 #if !defined(CONFIG_USER_ONLY)
3086 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3087 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3088 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3089 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3090 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3091 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3092 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3093 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3094 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3095 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3096 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3097 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3098 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3099 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
3100 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001700;
3101 /* Hardware reset vector */
3102 env->hreset_vector = 0x00000100UL;
3103 #endif
3106 static void init_excp_750cl(CPUPPCState *env)
3108 #if !defined(CONFIG_USER_ONLY)
3109 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3110 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3111 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3112 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3113 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3114 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3115 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3116 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3117 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3118 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3119 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3120 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3121 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3122 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
3123 /* Hardware reset vector */
3124 env->hreset_vector = 0x00000100UL;
3125 #endif
3128 static void init_excp_750cx(CPUPPCState *env)
3130 #if !defined(CONFIG_USER_ONLY)
3131 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3132 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3133 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3134 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3135 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3136 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3137 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3138 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3139 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3140 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3141 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3142 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3143 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3144 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001700;
3145 /* Hardware reset vector */
3146 env->hreset_vector = 0x00000100UL;
3147 #endif
3150 /* XXX: Check if this is correct */
3151 static void init_excp_7x5(CPUPPCState *env)
3153 #if !defined(CONFIG_USER_ONLY)
3154 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3155 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3156 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3157 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3158 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3159 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3160 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3161 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3162 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3163 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3164 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3165 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3166 env->excp_vectors[POWERPC_EXCP_IFTLB] = 0x00001000;
3167 env->excp_vectors[POWERPC_EXCP_DLTLB] = 0x00001100;
3168 env->excp_vectors[POWERPC_EXCP_DSTLB] = 0x00001200;
3169 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3170 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
3171 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001700;
3172 /* Hardware reset vector */
3173 env->hreset_vector = 0x00000100UL;
3174 #endif
3177 static void init_excp_7400(CPUPPCState *env)
3179 #if !defined(CONFIG_USER_ONLY)
3180 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3181 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3182 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3183 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3184 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3185 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3186 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3187 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3188 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3189 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3190 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3191 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3192 env->excp_vectors[POWERPC_EXCP_VPU] = 0x00000F20;
3193 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3194 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
3195 env->excp_vectors[POWERPC_EXCP_VPUA] = 0x00001600;
3196 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001700;
3197 /* Hardware reset vector */
3198 env->hreset_vector = 0x00000100UL;
3199 #endif
3202 static void init_excp_7450(CPUPPCState *env)
3204 #if !defined(CONFIG_USER_ONLY)
3205 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3206 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3207 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3208 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3209 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3210 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3211 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3212 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3213 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3214 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3215 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3216 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3217 env->excp_vectors[POWERPC_EXCP_VPU] = 0x00000F20;
3218 env->excp_vectors[POWERPC_EXCP_IFTLB] = 0x00001000;
3219 env->excp_vectors[POWERPC_EXCP_DLTLB] = 0x00001100;
3220 env->excp_vectors[POWERPC_EXCP_DSTLB] = 0x00001200;
3221 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3222 env->excp_vectors[POWERPC_EXCP_SMI] = 0x00001400;
3223 env->excp_vectors[POWERPC_EXCP_VPUA] = 0x00001600;
3224 /* Hardware reset vector */
3225 env->hreset_vector = 0x00000100UL;
3226 #endif
3229 #if defined(TARGET_PPC64)
3230 static void init_excp_970(CPUPPCState *env)
3232 #if !defined(CONFIG_USER_ONLY)
3233 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3234 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3235 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3236 env->excp_vectors[POWERPC_EXCP_DSEG] = 0x00000380;
3237 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3238 env->excp_vectors[POWERPC_EXCP_ISEG] = 0x00000480;
3239 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3240 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3241 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3242 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3243 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3244 env->excp_vectors[POWERPC_EXCP_HDECR] = 0x00000980;
3245 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3246 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3247 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3248 env->excp_vectors[POWERPC_EXCP_VPU] = 0x00000F20;
3249 env->excp_vectors[POWERPC_EXCP_IABR] = 0x00001300;
3250 env->excp_vectors[POWERPC_EXCP_MAINT] = 0x00001600;
3251 env->excp_vectors[POWERPC_EXCP_VPUA] = 0x00001700;
3252 env->excp_vectors[POWERPC_EXCP_THERM] = 0x00001800;
3253 /* Hardware reset vector */
3254 env->hreset_vector = 0x0000000000000100ULL;
3255 #endif
3258 static void init_excp_POWER7(CPUPPCState *env)
3260 #if !defined(CONFIG_USER_ONLY)
3261 env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000100;
3262 env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000200;
3263 env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000300;
3264 env->excp_vectors[POWERPC_EXCP_DSEG] = 0x00000380;
3265 env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000400;
3266 env->excp_vectors[POWERPC_EXCP_ISEG] = 0x00000480;
3267 env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x00000500;
3268 env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x00000600;
3269 env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x00000700;
3270 env->excp_vectors[POWERPC_EXCP_FPU] = 0x00000800;
3271 env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000900;
3272 env->excp_vectors[POWERPC_EXCP_HDECR] = 0x00000980;
3273 env->excp_vectors[POWERPC_EXCP_SYSCALL] = 0x00000C00;
3274 env->excp_vectors[POWERPC_EXCP_TRACE] = 0x00000D00;
3275 env->excp_vectors[POWERPC_EXCP_HDSI] = 0x00000E00;
3276 env->excp_vectors[POWERPC_EXCP_HISI] = 0x00000E20;
3277 env->excp_vectors[POWERPC_EXCP_HV_EMU] = 0x00000E40;
3278 env->excp_vectors[POWERPC_EXCP_HV_MAINT] = 0x00000E60;
3279 env->excp_vectors[POWERPC_EXCP_PERFM] = 0x00000F00;
3280 env->excp_vectors[POWERPC_EXCP_VPU] = 0x00000F20;
3281 env->excp_vectors[POWERPC_EXCP_VSXU] = 0x00000F40;
3282 /* Hardware reset vector */
3283 env->hreset_vector = 0x0000000000000100ULL;
3284 #endif
3287 static void init_excp_POWER8(CPUPPCState *env)
3289 init_excp_POWER7(env);
3291 #if !defined(CONFIG_USER_ONLY)
3292 env->excp_vectors[POWERPC_EXCP_SDOOR] = 0x00000A00;
3293 env->excp_vectors[POWERPC_EXCP_FU] = 0x00000F60;
3294 env->excp_vectors[POWERPC_EXCP_HV_FU] = 0x00000F80;
3295 env->excp_vectors[POWERPC_EXCP_SDOOR_HV] = 0x00000E80;
3296 #endif
3299 #endif
3301 /*****************************************************************************/
3302 /* Power management enable checks */
3303 static int check_pow_none(CPUPPCState *env)
3305 return 0;
3308 static int check_pow_nocheck(CPUPPCState *env)
3310 return 1;
3313 static int check_pow_hid0(CPUPPCState *env)
3315 if (env->spr[SPR_HID0] & 0x00E00000)
3316 return 1;
3318 return 0;
3321 static int check_pow_hid0_74xx(CPUPPCState *env)
3323 if (env->spr[SPR_HID0] & 0x00600000)
3324 return 1;
3326 return 0;
3329 static bool ppc_cpu_interrupts_big_endian_always(PowerPCCPU *cpu)
3331 return true;
3334 #ifdef TARGET_PPC64
3335 static bool ppc_cpu_interrupts_big_endian_lpcr(PowerPCCPU *cpu)
3337 return !(cpu->env.spr[SPR_LPCR] & LPCR_ILE);
3339 #endif
3341 /*****************************************************************************/
3342 /* PowerPC implementations definitions */
3344 #define POWERPC_FAMILY(_name) \
3345 static void \
3346 glue(glue(ppc_, _name), _cpu_family_class_init)(ObjectClass *, void *); \
3348 static const TypeInfo \
3349 glue(glue(ppc_, _name), _cpu_family_type_info) = { \
3350 .name = stringify(_name) "-family-" TYPE_POWERPC_CPU, \
3351 .parent = TYPE_POWERPC_CPU, \
3352 .abstract = true, \
3353 .class_init = glue(glue(ppc_, _name), _cpu_family_class_init), \
3354 }; \
3356 static void glue(glue(ppc_, _name), _cpu_family_register_types)(void) \
3358 type_register_static( \
3359 &glue(glue(ppc_, _name), _cpu_family_type_info)); \
3362 type_init(glue(glue(ppc_, _name), _cpu_family_register_types)) \
3364 static void glue(glue(ppc_, _name), _cpu_family_class_init)
3366 static void init_proc_401(CPUPPCState *env)
3368 gen_spr_40x(env);
3369 gen_spr_401_403(env);
3370 gen_spr_401(env);
3371 init_excp_4xx_real(env);
3372 env->dcache_line_size = 32;
3373 env->icache_line_size = 32;
3374 /* Allocate hardware IRQ controller */
3375 ppc40x_irq_init(ppc_env_get_cpu(env));
3377 SET_FIT_PERIOD(12, 16, 20, 24);
3378 SET_WDT_PERIOD(16, 20, 24, 28);
3381 POWERPC_FAMILY(401)(ObjectClass *oc, void *data)
3383 DeviceClass *dc = DEVICE_CLASS(oc);
3384 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3386 dc->desc = "PowerPC 401";
3387 pcc->init_proc = init_proc_401;
3388 pcc->check_pow = check_pow_nocheck;
3389 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3390 PPC_WRTEE | PPC_DCR |
3391 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3392 PPC_CACHE_DCBZ |
3393 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3394 PPC_4xx_COMMON | PPC_40x_EXCP;
3395 pcc->msr_mask = (1ull << MSR_KEY) |
3396 (1ull << MSR_POW) |
3397 (1ull << MSR_CE) |
3398 (1ull << MSR_ILE) |
3399 (1ull << MSR_EE) |
3400 (1ull << MSR_PR) |
3401 (1ull << MSR_ME) |
3402 (1ull << MSR_DE) |
3403 (1ull << MSR_LE);
3404 pcc->mmu_model = POWERPC_MMU_REAL;
3405 pcc->excp_model = POWERPC_EXCP_40x;
3406 pcc->bus_model = PPC_FLAGS_INPUT_401;
3407 pcc->bfd_mach = bfd_mach_ppc_403;
3408 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
3409 POWERPC_FLAG_BUS_CLK;
3412 static void init_proc_401x2(CPUPPCState *env)
3414 gen_spr_40x(env);
3415 gen_spr_401_403(env);
3416 gen_spr_401x2(env);
3417 gen_spr_compress(env);
3418 /* Memory management */
3419 #if !defined(CONFIG_USER_ONLY)
3420 env->nb_tlb = 64;
3421 env->nb_ways = 1;
3422 env->id_tlbs = 0;
3423 env->tlb_type = TLB_EMB;
3424 #endif
3425 init_excp_4xx_softmmu(env);
3426 env->dcache_line_size = 32;
3427 env->icache_line_size = 32;
3428 /* Allocate hardware IRQ controller */
3429 ppc40x_irq_init(ppc_env_get_cpu(env));
3431 SET_FIT_PERIOD(12, 16, 20, 24);
3432 SET_WDT_PERIOD(16, 20, 24, 28);
3435 POWERPC_FAMILY(401x2)(ObjectClass *oc, void *data)
3437 DeviceClass *dc = DEVICE_CLASS(oc);
3438 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3440 dc->desc = "PowerPC 401x2";
3441 pcc->init_proc = init_proc_401x2;
3442 pcc->check_pow = check_pow_nocheck;
3443 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
3444 PPC_DCR | PPC_WRTEE |
3445 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3446 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3447 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3448 PPC_40x_TLB | PPC_MEM_TLBIA | PPC_MEM_TLBSYNC |
3449 PPC_4xx_COMMON | PPC_40x_EXCP;
3450 pcc->msr_mask = (1ull << 20) |
3451 (1ull << MSR_KEY) |
3452 (1ull << MSR_POW) |
3453 (1ull << MSR_CE) |
3454 (1ull << MSR_ILE) |
3455 (1ull << MSR_EE) |
3456 (1ull << MSR_PR) |
3457 (1ull << MSR_ME) |
3458 (1ull << MSR_DE) |
3459 (1ull << MSR_IR) |
3460 (1ull << MSR_DR) |
3461 (1ull << MSR_LE);
3462 pcc->mmu_model = POWERPC_MMU_SOFT_4xx_Z;
3463 pcc->excp_model = POWERPC_EXCP_40x;
3464 pcc->bus_model = PPC_FLAGS_INPUT_401;
3465 pcc->bfd_mach = bfd_mach_ppc_403;
3466 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
3467 POWERPC_FLAG_BUS_CLK;
3470 static void init_proc_401x3(CPUPPCState *env)
3472 gen_spr_40x(env);
3473 gen_spr_401_403(env);
3474 gen_spr_401(env);
3475 gen_spr_401x2(env);
3476 gen_spr_compress(env);
3477 init_excp_4xx_softmmu(env);
3478 env->dcache_line_size = 32;
3479 env->icache_line_size = 32;
3480 /* Allocate hardware IRQ controller */
3481 ppc40x_irq_init(ppc_env_get_cpu(env));
3483 SET_FIT_PERIOD(12, 16, 20, 24);
3484 SET_WDT_PERIOD(16, 20, 24, 28);
3487 POWERPC_FAMILY(401x3)(ObjectClass *oc, void *data)
3489 DeviceClass *dc = DEVICE_CLASS(oc);
3490 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3492 dc->desc = "PowerPC 401x3";
3493 pcc->init_proc = init_proc_401x3;
3494 pcc->check_pow = check_pow_nocheck;
3495 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
3496 PPC_DCR | PPC_WRTEE |
3497 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3498 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3499 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3500 PPC_40x_TLB | PPC_MEM_TLBIA | PPC_MEM_TLBSYNC |
3501 PPC_4xx_COMMON | PPC_40x_EXCP;
3502 pcc->msr_mask = (1ull << 20) |
3503 (1ull << MSR_KEY) |
3504 (1ull << MSR_POW) |
3505 (1ull << MSR_CE) |
3506 (1ull << MSR_ILE) |
3507 (1ull << MSR_EE) |
3508 (1ull << MSR_PR) |
3509 (1ull << MSR_ME) |
3510 (1ull << MSR_DWE) |
3511 (1ull << MSR_DE) |
3512 (1ull << MSR_IR) |
3513 (1ull << MSR_DR) |
3514 (1ull << MSR_LE);
3515 pcc->mmu_model = POWERPC_MMU_SOFT_4xx_Z;
3516 pcc->excp_model = POWERPC_EXCP_40x;
3517 pcc->bus_model = PPC_FLAGS_INPUT_401;
3518 pcc->bfd_mach = bfd_mach_ppc_403;
3519 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
3520 POWERPC_FLAG_BUS_CLK;
3523 static void init_proc_IOP480(CPUPPCState *env)
3525 gen_spr_40x(env);
3526 gen_spr_401_403(env);
3527 gen_spr_401x2(env);
3528 gen_spr_compress(env);
3529 /* Memory management */
3530 #if !defined(CONFIG_USER_ONLY)
3531 env->nb_tlb = 64;
3532 env->nb_ways = 1;
3533 env->id_tlbs = 0;
3534 env->tlb_type = TLB_EMB;
3535 #endif
3536 init_excp_4xx_softmmu(env);
3537 env->dcache_line_size = 32;
3538 env->icache_line_size = 32;
3539 /* Allocate hardware IRQ controller */
3540 ppc40x_irq_init(ppc_env_get_cpu(env));
3542 SET_FIT_PERIOD(8, 12, 16, 20);
3543 SET_WDT_PERIOD(16, 20, 24, 28);
3546 POWERPC_FAMILY(IOP480)(ObjectClass *oc, void *data)
3548 DeviceClass *dc = DEVICE_CLASS(oc);
3549 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3551 dc->desc = "IOP480";
3552 pcc->init_proc = init_proc_IOP480;
3553 pcc->check_pow = check_pow_nocheck;
3554 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3555 PPC_DCR | PPC_WRTEE |
3556 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3557 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3558 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3559 PPC_40x_TLB | PPC_MEM_TLBIA | PPC_MEM_TLBSYNC |
3560 PPC_4xx_COMMON | PPC_40x_EXCP;
3561 pcc->msr_mask = (1ull << 20) |
3562 (1ull << MSR_KEY) |
3563 (1ull << MSR_POW) |
3564 (1ull << MSR_CE) |
3565 (1ull << MSR_ILE) |
3566 (1ull << MSR_EE) |
3567 (1ull << MSR_PR) |
3568 (1ull << MSR_ME) |
3569 (1ull << MSR_DE) |
3570 (1ull << MSR_IR) |
3571 (1ull << MSR_DR) |
3572 (1ull << MSR_LE);
3573 pcc->mmu_model = POWERPC_MMU_SOFT_4xx_Z;
3574 pcc->excp_model = POWERPC_EXCP_40x;
3575 pcc->bus_model = PPC_FLAGS_INPUT_401;
3576 pcc->bfd_mach = bfd_mach_ppc_403;
3577 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
3578 POWERPC_FLAG_BUS_CLK;
3581 static void init_proc_403(CPUPPCState *env)
3583 gen_spr_40x(env);
3584 gen_spr_401_403(env);
3585 gen_spr_403(env);
3586 gen_spr_403_real(env);
3587 init_excp_4xx_real(env);
3588 env->dcache_line_size = 32;
3589 env->icache_line_size = 32;
3590 /* Allocate hardware IRQ controller */
3591 ppc40x_irq_init(ppc_env_get_cpu(env));
3593 SET_FIT_PERIOD(8, 12, 16, 20);
3594 SET_WDT_PERIOD(16, 20, 24, 28);
3597 POWERPC_FAMILY(403)(ObjectClass *oc, void *data)
3599 DeviceClass *dc = DEVICE_CLASS(oc);
3600 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3602 dc->desc = "PowerPC 403";
3603 pcc->init_proc = init_proc_403;
3604 pcc->check_pow = check_pow_nocheck;
3605 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3606 PPC_DCR | PPC_WRTEE |
3607 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3608 PPC_CACHE_DCBZ |
3609 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3610 PPC_4xx_COMMON | PPC_40x_EXCP;
3611 pcc->msr_mask = (1ull << MSR_POW) |
3612 (1ull << MSR_CE) |
3613 (1ull << MSR_ILE) |
3614 (1ull << MSR_EE) |
3615 (1ull << MSR_PR) |
3616 (1ull << MSR_ME) |
3617 (1ull << MSR_PE) |
3618 (1ull << MSR_PX) |
3619 (1ull << MSR_LE);
3620 pcc->mmu_model = POWERPC_MMU_REAL;
3621 pcc->excp_model = POWERPC_EXCP_40x;
3622 pcc->bus_model = PPC_FLAGS_INPUT_401;
3623 pcc->bfd_mach = bfd_mach_ppc_403;
3624 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_PX |
3625 POWERPC_FLAG_BUS_CLK;
3628 static void init_proc_403GCX(CPUPPCState *env)
3630 gen_spr_40x(env);
3631 gen_spr_401_403(env);
3632 gen_spr_403(env);
3633 gen_spr_403_real(env);
3634 gen_spr_403_mmu(env);
3635 /* Bus access control */
3636 /* not emulated, as QEMU never does speculative access */
3637 spr_register(env, SPR_40x_SGR, "SGR",
3638 SPR_NOACCESS, SPR_NOACCESS,
3639 &spr_read_generic, &spr_write_generic,
3640 0xFFFFFFFF);
3641 /* not emulated, as QEMU do not emulate caches */
3642 spr_register(env, SPR_40x_DCWR, "DCWR",
3643 SPR_NOACCESS, SPR_NOACCESS,
3644 &spr_read_generic, &spr_write_generic,
3645 0x00000000);
3646 /* Memory management */
3647 #if !defined(CONFIG_USER_ONLY)
3648 env->nb_tlb = 64;
3649 env->nb_ways = 1;
3650 env->id_tlbs = 0;
3651 env->tlb_type = TLB_EMB;
3652 #endif
3653 init_excp_4xx_softmmu(env);
3654 env->dcache_line_size = 32;
3655 env->icache_line_size = 32;
3656 /* Allocate hardware IRQ controller */
3657 ppc40x_irq_init(ppc_env_get_cpu(env));
3659 SET_FIT_PERIOD(8, 12, 16, 20);
3660 SET_WDT_PERIOD(16, 20, 24, 28);
3663 POWERPC_FAMILY(403GCX)(ObjectClass *oc, void *data)
3665 DeviceClass *dc = DEVICE_CLASS(oc);
3666 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3668 dc->desc = "PowerPC 403 GCX";
3669 pcc->init_proc = init_proc_403GCX;
3670 pcc->check_pow = check_pow_nocheck;
3671 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3672 PPC_DCR | PPC_WRTEE |
3673 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3674 PPC_CACHE_DCBZ |
3675 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3676 PPC_40x_TLB | PPC_MEM_TLBIA | PPC_MEM_TLBSYNC |
3677 PPC_4xx_COMMON | PPC_40x_EXCP;
3678 pcc->msr_mask = (1ull << MSR_POW) |
3679 (1ull << MSR_CE) |
3680 (1ull << MSR_ILE) |
3681 (1ull << MSR_EE) |
3682 (1ull << MSR_PR) |
3683 (1ull << MSR_ME) |
3684 (1ull << MSR_PE) |
3685 (1ull << MSR_PX) |
3686 (1ull << MSR_LE);
3687 pcc->mmu_model = POWERPC_MMU_SOFT_4xx_Z;
3688 pcc->excp_model = POWERPC_EXCP_40x;
3689 pcc->bus_model = PPC_FLAGS_INPUT_401;
3690 pcc->bfd_mach = bfd_mach_ppc_403;
3691 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_PX |
3692 POWERPC_FLAG_BUS_CLK;
3695 static void init_proc_405(CPUPPCState *env)
3697 /* Time base */
3698 gen_tbl(env);
3699 gen_spr_40x(env);
3700 gen_spr_405(env);
3701 /* Bus access control */
3702 /* not emulated, as QEMU never does speculative access */
3703 spr_register(env, SPR_40x_SGR, "SGR",
3704 SPR_NOACCESS, SPR_NOACCESS,
3705 &spr_read_generic, &spr_write_generic,
3706 0xFFFFFFFF);
3707 /* not emulated, as QEMU do not emulate caches */
3708 spr_register(env, SPR_40x_DCWR, "DCWR",
3709 SPR_NOACCESS, SPR_NOACCESS,
3710 &spr_read_generic, &spr_write_generic,
3711 0x00000000);
3712 /* Memory management */
3713 #if !defined(CONFIG_USER_ONLY)
3714 env->nb_tlb = 64;
3715 env->nb_ways = 1;
3716 env->id_tlbs = 0;
3717 env->tlb_type = TLB_EMB;
3718 #endif
3719 init_excp_4xx_softmmu(env);
3720 env->dcache_line_size = 32;
3721 env->icache_line_size = 32;
3722 /* Allocate hardware IRQ controller */
3723 ppc40x_irq_init(ppc_env_get_cpu(env));
3725 SET_FIT_PERIOD(8, 12, 16, 20);
3726 SET_WDT_PERIOD(16, 20, 24, 28);
3729 POWERPC_FAMILY(405)(ObjectClass *oc, void *data)
3731 DeviceClass *dc = DEVICE_CLASS(oc);
3732 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3734 dc->desc = "PowerPC 405";
3735 pcc->init_proc = init_proc_405;
3736 pcc->check_pow = check_pow_nocheck;
3737 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
3738 PPC_DCR | PPC_WRTEE |
3739 PPC_CACHE | PPC_CACHE_ICBI | PPC_40x_ICBT |
3740 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3741 PPC_MEM_SYNC | PPC_MEM_EIEIO |
3742 PPC_40x_TLB | PPC_MEM_TLBIA | PPC_MEM_TLBSYNC |
3743 PPC_4xx_COMMON | PPC_405_MAC | PPC_40x_EXCP;
3744 pcc->msr_mask = (1ull << MSR_POW) |
3745 (1ull << MSR_CE) |
3746 (1ull << MSR_EE) |
3747 (1ull << MSR_PR) |
3748 (1ull << MSR_FP) |
3749 (1ull << MSR_DWE) |
3750 (1ull << MSR_DE) |
3751 (1ull << MSR_IR) |
3752 (1ull << MSR_DR);
3753 pcc->mmu_model = POWERPC_MMU_SOFT_4xx;
3754 pcc->excp_model = POWERPC_EXCP_40x;
3755 pcc->bus_model = PPC_FLAGS_INPUT_405;
3756 pcc->bfd_mach = bfd_mach_ppc_403;
3757 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
3758 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
3761 static void init_proc_440EP(CPUPPCState *env)
3763 /* Time base */
3764 gen_tbl(env);
3765 gen_spr_BookE(env, 0x000000000000FFFFULL);
3766 gen_spr_440(env);
3767 gen_spr_usprgh(env);
3768 /* Processor identification */
3769 spr_register(env, SPR_BOOKE_PIR, "PIR",
3770 SPR_NOACCESS, SPR_NOACCESS,
3771 &spr_read_generic, &spr_write_pir,
3772 0x00000000);
3773 /* XXX : not implemented */
3774 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
3775 SPR_NOACCESS, SPR_NOACCESS,
3776 &spr_read_generic, &spr_write_generic,
3777 0x00000000);
3778 /* XXX : not implemented */
3779 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
3780 SPR_NOACCESS, SPR_NOACCESS,
3781 &spr_read_generic, &spr_write_generic,
3782 0x00000000);
3783 /* XXX : not implemented */
3784 spr_register(env, SPR_BOOKE_DVC1, "DVC1",
3785 SPR_NOACCESS, SPR_NOACCESS,
3786 &spr_read_generic, &spr_write_generic,
3787 0x00000000);
3788 /* XXX : not implemented */
3789 spr_register(env, SPR_BOOKE_DVC2, "DVC2",
3790 SPR_NOACCESS, SPR_NOACCESS,
3791 &spr_read_generic, &spr_write_generic,
3792 0x00000000);
3793 /* XXX : not implemented */
3794 spr_register(env, SPR_BOOKE_MCSR, "MCSR",
3795 SPR_NOACCESS, SPR_NOACCESS,
3796 &spr_read_generic, &spr_write_generic,
3797 0x00000000);
3798 spr_register(env, SPR_BOOKE_MCSRR0, "MCSRR0",
3799 SPR_NOACCESS, SPR_NOACCESS,
3800 &spr_read_generic, &spr_write_generic,
3801 0x00000000);
3802 spr_register(env, SPR_BOOKE_MCSRR1, "MCSRR1",
3803 SPR_NOACCESS, SPR_NOACCESS,
3804 &spr_read_generic, &spr_write_generic,
3805 0x00000000);
3806 /* XXX : not implemented */
3807 spr_register(env, SPR_440_CCR1, "CCR1",
3808 SPR_NOACCESS, SPR_NOACCESS,
3809 &spr_read_generic, &spr_write_generic,
3810 0x00000000);
3811 /* Memory management */
3812 #if !defined(CONFIG_USER_ONLY)
3813 env->nb_tlb = 64;
3814 env->nb_ways = 1;
3815 env->id_tlbs = 0;
3816 env->tlb_type = TLB_EMB;
3817 #endif
3818 init_excp_BookE(env);
3819 env->dcache_line_size = 32;
3820 env->icache_line_size = 32;
3821 ppc40x_irq_init(ppc_env_get_cpu(env));
3823 SET_FIT_PERIOD(12, 16, 20, 24);
3824 SET_WDT_PERIOD(20, 24, 28, 32);
3827 POWERPC_FAMILY(440EP)(ObjectClass *oc, void *data)
3829 DeviceClass *dc = DEVICE_CLASS(oc);
3830 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3832 dc->desc = "PowerPC 440 EP";
3833 pcc->init_proc = init_proc_440EP;
3834 pcc->check_pow = check_pow_nocheck;
3835 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3836 PPC_FLOAT | PPC_FLOAT_FRES | PPC_FLOAT_FSEL |
3837 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
3838 PPC_FLOAT_STFIWX |
3839 PPC_DCR | PPC_WRTEE | PPC_RFMCI |
3840 PPC_CACHE | PPC_CACHE_ICBI |
3841 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3842 PPC_MEM_TLBSYNC | PPC_MFTB |
3843 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
3844 PPC_440_SPEC;
3845 pcc->msr_mask = (1ull << MSR_POW) |
3846 (1ull << MSR_CE) |
3847 (1ull << MSR_EE) |
3848 (1ull << MSR_PR) |
3849 (1ull << MSR_FP) |
3850 (1ull << MSR_ME) |
3851 (1ull << MSR_FE0) |
3852 (1ull << MSR_DWE) |
3853 (1ull << MSR_DE) |
3854 (1ull << MSR_FE1) |
3855 (1ull << MSR_IR) |
3856 (1ull << MSR_DR);
3857 pcc->mmu_model = POWERPC_MMU_BOOKE;
3858 pcc->excp_model = POWERPC_EXCP_BOOKE;
3859 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
3860 pcc->bfd_mach = bfd_mach_ppc_403;
3861 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
3862 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
3865 POWERPC_FAMILY(460EX)(ObjectClass *oc, void *data)
3867 DeviceClass *dc = DEVICE_CLASS(oc);
3868 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3870 dc->desc = "PowerPC 460 EX";
3871 pcc->init_proc = init_proc_440EP;
3872 pcc->check_pow = check_pow_nocheck;
3873 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3874 PPC_FLOAT | PPC_FLOAT_FRES | PPC_FLOAT_FSEL |
3875 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
3876 PPC_FLOAT_STFIWX |
3877 PPC_DCR | PPC_DCRX | PPC_WRTEE | PPC_RFMCI |
3878 PPC_CACHE | PPC_CACHE_ICBI |
3879 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3880 PPC_MEM_TLBSYNC | PPC_MFTB |
3881 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
3882 PPC_440_SPEC;
3883 pcc->msr_mask = (1ull << MSR_POW) |
3884 (1ull << MSR_CE) |
3885 (1ull << MSR_EE) |
3886 (1ull << MSR_PR) |
3887 (1ull << MSR_FP) |
3888 (1ull << MSR_ME) |
3889 (1ull << MSR_FE0) |
3890 (1ull << MSR_DWE) |
3891 (1ull << MSR_DE) |
3892 (1ull << MSR_FE1) |
3893 (1ull << MSR_IR) |
3894 (1ull << MSR_DR);
3895 pcc->mmu_model = POWERPC_MMU_BOOKE;
3896 pcc->excp_model = POWERPC_EXCP_BOOKE;
3897 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
3898 pcc->bfd_mach = bfd_mach_ppc_403;
3899 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
3900 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
3903 static void init_proc_440GP(CPUPPCState *env)
3905 /* Time base */
3906 gen_tbl(env);
3907 gen_spr_BookE(env, 0x000000000000FFFFULL);
3908 gen_spr_440(env);
3909 gen_spr_usprgh(env);
3910 /* Processor identification */
3911 spr_register(env, SPR_BOOKE_PIR, "PIR",
3912 SPR_NOACCESS, SPR_NOACCESS,
3913 &spr_read_generic, &spr_write_pir,
3914 0x00000000);
3915 /* XXX : not implemented */
3916 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
3917 SPR_NOACCESS, SPR_NOACCESS,
3918 &spr_read_generic, &spr_write_generic,
3919 0x00000000);
3920 /* XXX : not implemented */
3921 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
3922 SPR_NOACCESS, SPR_NOACCESS,
3923 &spr_read_generic, &spr_write_generic,
3924 0x00000000);
3925 /* XXX : not implemented */
3926 spr_register(env, SPR_BOOKE_DVC1, "DVC1",
3927 SPR_NOACCESS, SPR_NOACCESS,
3928 &spr_read_generic, &spr_write_generic,
3929 0x00000000);
3930 /* XXX : not implemented */
3931 spr_register(env, SPR_BOOKE_DVC2, "DVC2",
3932 SPR_NOACCESS, SPR_NOACCESS,
3933 &spr_read_generic, &spr_write_generic,
3934 0x00000000);
3935 /* Memory management */
3936 #if !defined(CONFIG_USER_ONLY)
3937 env->nb_tlb = 64;
3938 env->nb_ways = 1;
3939 env->id_tlbs = 0;
3940 env->tlb_type = TLB_EMB;
3941 #endif
3942 init_excp_BookE(env);
3943 env->dcache_line_size = 32;
3944 env->icache_line_size = 32;
3945 /* XXX: TODO: allocate internal IRQ controller */
3947 SET_FIT_PERIOD(12, 16, 20, 24);
3948 SET_WDT_PERIOD(20, 24, 28, 32);
3951 POWERPC_FAMILY(440GP)(ObjectClass *oc, void *data)
3953 DeviceClass *dc = DEVICE_CLASS(oc);
3954 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
3956 dc->desc = "PowerPC 440 GP";
3957 pcc->init_proc = init_proc_440GP;
3958 pcc->check_pow = check_pow_nocheck;
3959 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
3960 PPC_DCR | PPC_DCRX | PPC_WRTEE | PPC_MFAPIDI |
3961 PPC_CACHE | PPC_CACHE_ICBI |
3962 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
3963 PPC_MEM_TLBSYNC | PPC_TLBIVA | PPC_MFTB |
3964 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
3965 PPC_440_SPEC;
3966 pcc->msr_mask = (1ull << MSR_POW) |
3967 (1ull << MSR_CE) |
3968 (1ull << MSR_EE) |
3969 (1ull << MSR_PR) |
3970 (1ull << MSR_FP) |
3971 (1ull << MSR_ME) |
3972 (1ull << MSR_FE0) |
3973 (1ull << MSR_DWE) |
3974 (1ull << MSR_DE) |
3975 (1ull << MSR_FE1) |
3976 (1ull << MSR_IR) |
3977 (1ull << MSR_DR);
3978 pcc->mmu_model = POWERPC_MMU_BOOKE;
3979 pcc->excp_model = POWERPC_EXCP_BOOKE;
3980 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
3981 pcc->bfd_mach = bfd_mach_ppc_403;
3982 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
3983 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
3986 static void init_proc_440x4(CPUPPCState *env)
3988 /* Time base */
3989 gen_tbl(env);
3990 gen_spr_BookE(env, 0x000000000000FFFFULL);
3991 gen_spr_440(env);
3992 gen_spr_usprgh(env);
3993 /* Processor identification */
3994 spr_register(env, SPR_BOOKE_PIR, "PIR",
3995 SPR_NOACCESS, SPR_NOACCESS,
3996 &spr_read_generic, &spr_write_pir,
3997 0x00000000);
3998 /* XXX : not implemented */
3999 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
4000 SPR_NOACCESS, SPR_NOACCESS,
4001 &spr_read_generic, &spr_write_generic,
4002 0x00000000);
4003 /* XXX : not implemented */
4004 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
4005 SPR_NOACCESS, SPR_NOACCESS,
4006 &spr_read_generic, &spr_write_generic,
4007 0x00000000);
4008 /* XXX : not implemented */
4009 spr_register(env, SPR_BOOKE_DVC1, "DVC1",
4010 SPR_NOACCESS, SPR_NOACCESS,
4011 &spr_read_generic, &spr_write_generic,
4012 0x00000000);
4013 /* XXX : not implemented */
4014 spr_register(env, SPR_BOOKE_DVC2, "DVC2",
4015 SPR_NOACCESS, SPR_NOACCESS,
4016 &spr_read_generic, &spr_write_generic,
4017 0x00000000);
4018 /* Memory management */
4019 #if !defined(CONFIG_USER_ONLY)
4020 env->nb_tlb = 64;
4021 env->nb_ways = 1;
4022 env->id_tlbs = 0;
4023 env->tlb_type = TLB_EMB;
4024 #endif
4025 init_excp_BookE(env);
4026 env->dcache_line_size = 32;
4027 env->icache_line_size = 32;
4028 /* XXX: TODO: allocate internal IRQ controller */
4030 SET_FIT_PERIOD(12, 16, 20, 24);
4031 SET_WDT_PERIOD(20, 24, 28, 32);
4034 POWERPC_FAMILY(440x4)(ObjectClass *oc, void *data)
4036 DeviceClass *dc = DEVICE_CLASS(oc);
4037 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4039 dc->desc = "PowerPC 440x4";
4040 pcc->init_proc = init_proc_440x4;
4041 pcc->check_pow = check_pow_nocheck;
4042 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
4043 PPC_DCR | PPC_WRTEE |
4044 PPC_CACHE | PPC_CACHE_ICBI |
4045 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
4046 PPC_MEM_TLBSYNC | PPC_MFTB |
4047 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
4048 PPC_440_SPEC;
4049 pcc->msr_mask = (1ull << MSR_POW) |
4050 (1ull << MSR_CE) |
4051 (1ull << MSR_EE) |
4052 (1ull << MSR_PR) |
4053 (1ull << MSR_FP) |
4054 (1ull << MSR_ME) |
4055 (1ull << MSR_FE0) |
4056 (1ull << MSR_DWE) |
4057 (1ull << MSR_DE) |
4058 (1ull << MSR_FE1) |
4059 (1ull << MSR_IR) |
4060 (1ull << MSR_DR);
4061 pcc->mmu_model = POWERPC_MMU_BOOKE;
4062 pcc->excp_model = POWERPC_EXCP_BOOKE;
4063 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
4064 pcc->bfd_mach = bfd_mach_ppc_403;
4065 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
4066 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
4069 static void init_proc_440x5(CPUPPCState *env)
4071 /* Time base */
4072 gen_tbl(env);
4073 gen_spr_BookE(env, 0x000000000000FFFFULL);
4074 gen_spr_440(env);
4075 gen_spr_usprgh(env);
4076 /* Processor identification */
4077 spr_register(env, SPR_BOOKE_PIR, "PIR",
4078 SPR_NOACCESS, SPR_NOACCESS,
4079 &spr_read_generic, &spr_write_pir,
4080 0x00000000);
4081 /* XXX : not implemented */
4082 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
4083 SPR_NOACCESS, SPR_NOACCESS,
4084 &spr_read_generic, &spr_write_generic,
4085 0x00000000);
4086 /* XXX : not implemented */
4087 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
4088 SPR_NOACCESS, SPR_NOACCESS,
4089 &spr_read_generic, &spr_write_generic,
4090 0x00000000);
4091 /* XXX : not implemented */
4092 spr_register(env, SPR_BOOKE_DVC1, "DVC1",
4093 SPR_NOACCESS, SPR_NOACCESS,
4094 &spr_read_generic, &spr_write_generic,
4095 0x00000000);
4096 /* XXX : not implemented */
4097 spr_register(env, SPR_BOOKE_DVC2, "DVC2",
4098 SPR_NOACCESS, SPR_NOACCESS,
4099 &spr_read_generic, &spr_write_generic,
4100 0x00000000);
4101 /* XXX : not implemented */
4102 spr_register(env, SPR_BOOKE_MCSR, "MCSR",
4103 SPR_NOACCESS, SPR_NOACCESS,
4104 &spr_read_generic, &spr_write_generic,
4105 0x00000000);
4106 spr_register(env, SPR_BOOKE_MCSRR0, "MCSRR0",
4107 SPR_NOACCESS, SPR_NOACCESS,
4108 &spr_read_generic, &spr_write_generic,
4109 0x00000000);
4110 spr_register(env, SPR_BOOKE_MCSRR1, "MCSRR1",
4111 SPR_NOACCESS, SPR_NOACCESS,
4112 &spr_read_generic, &spr_write_generic,
4113 0x00000000);
4114 /* XXX : not implemented */
4115 spr_register(env, SPR_440_CCR1, "CCR1",
4116 SPR_NOACCESS, SPR_NOACCESS,
4117 &spr_read_generic, &spr_write_generic,
4118 0x00000000);
4119 /* Memory management */
4120 #if !defined(CONFIG_USER_ONLY)
4121 env->nb_tlb = 64;
4122 env->nb_ways = 1;
4123 env->id_tlbs = 0;
4124 env->tlb_type = TLB_EMB;
4125 #endif
4126 init_excp_BookE(env);
4127 env->dcache_line_size = 32;
4128 env->icache_line_size = 32;
4129 ppc40x_irq_init(ppc_env_get_cpu(env));
4131 SET_FIT_PERIOD(12, 16, 20, 24);
4132 SET_WDT_PERIOD(20, 24, 28, 32);
4135 POWERPC_FAMILY(440x5)(ObjectClass *oc, void *data)
4137 DeviceClass *dc = DEVICE_CLASS(oc);
4138 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4140 dc->desc = "PowerPC 440x5";
4141 pcc->init_proc = init_proc_440x5;
4142 pcc->check_pow = check_pow_nocheck;
4143 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
4144 PPC_DCR | PPC_WRTEE | PPC_RFMCI |
4145 PPC_CACHE | PPC_CACHE_ICBI |
4146 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
4147 PPC_MEM_TLBSYNC | PPC_MFTB |
4148 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
4149 PPC_440_SPEC;
4150 pcc->msr_mask = (1ull << MSR_POW) |
4151 (1ull << MSR_CE) |
4152 (1ull << MSR_EE) |
4153 (1ull << MSR_PR) |
4154 (1ull << MSR_FP) |
4155 (1ull << MSR_ME) |
4156 (1ull << MSR_FE0) |
4157 (1ull << MSR_DWE) |
4158 (1ull << MSR_DE) |
4159 (1ull << MSR_FE1) |
4160 (1ull << MSR_IR) |
4161 (1ull << MSR_DR);
4162 pcc->mmu_model = POWERPC_MMU_BOOKE;
4163 pcc->excp_model = POWERPC_EXCP_BOOKE;
4164 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
4165 pcc->bfd_mach = bfd_mach_ppc_403;
4166 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
4167 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
4170 POWERPC_FAMILY(440x5wDFPU)(ObjectClass *oc, void *data)
4172 DeviceClass *dc = DEVICE_CLASS(oc);
4173 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4175 dc->desc = "PowerPC 440x5 with double precision FPU";
4176 pcc->init_proc = init_proc_440x5;
4177 pcc->check_pow = check_pow_nocheck;
4178 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
4179 PPC_FLOAT | PPC_FLOAT_FSQRT |
4180 PPC_FLOAT_STFIWX |
4181 PPC_DCR | PPC_WRTEE | PPC_RFMCI |
4182 PPC_CACHE | PPC_CACHE_ICBI |
4183 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
4184 PPC_MEM_TLBSYNC | PPC_MFTB |
4185 PPC_BOOKE | PPC_4xx_COMMON | PPC_405_MAC |
4186 PPC_440_SPEC;
4187 pcc->insns_flags2 = PPC2_FP_CVT_S64;
4188 pcc->msr_mask = (1ull << MSR_POW) |
4189 (1ull << MSR_CE) |
4190 (1ull << MSR_EE) |
4191 (1ull << MSR_PR) |
4192 (1ull << MSR_FP) |
4193 (1ull << MSR_ME) |
4194 (1ull << MSR_FE0) |
4195 (1ull << MSR_DWE) |
4196 (1ull << MSR_DE) |
4197 (1ull << MSR_FE1) |
4198 (1ull << MSR_IR) |
4199 (1ull << MSR_DR);
4200 pcc->mmu_model = POWERPC_MMU_BOOKE;
4201 pcc->excp_model = POWERPC_EXCP_BOOKE;
4202 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
4203 pcc->bfd_mach = bfd_mach_ppc_403;
4204 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DWE |
4205 POWERPC_FLAG_DE | POWERPC_FLAG_BUS_CLK;
4208 static void init_proc_MPC5xx(CPUPPCState *env)
4210 /* Time base */
4211 gen_tbl(env);
4212 gen_spr_5xx_8xx(env);
4213 gen_spr_5xx(env);
4214 init_excp_MPC5xx(env);
4215 env->dcache_line_size = 32;
4216 env->icache_line_size = 32;
4217 /* XXX: TODO: allocate internal IRQ controller */
4220 POWERPC_FAMILY(MPC5xx)(ObjectClass *oc, void *data)
4222 DeviceClass *dc = DEVICE_CLASS(oc);
4223 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4225 dc->desc = "Freescale 5xx cores (aka RCPU)";
4226 pcc->init_proc = init_proc_MPC5xx;
4227 pcc->check_pow = check_pow_none;
4228 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
4229 PPC_MEM_EIEIO | PPC_MEM_SYNC |
4230 PPC_CACHE_ICBI | PPC_FLOAT | PPC_FLOAT_STFIWX |
4231 PPC_MFTB;
4232 pcc->msr_mask = (1ull << MSR_ILE) |
4233 (1ull << MSR_EE) |
4234 (1ull << MSR_PR) |
4235 (1ull << MSR_FP) |
4236 (1ull << MSR_ME) |
4237 (1ull << MSR_FE0) |
4238 (1ull << MSR_SE) |
4239 (1ull << MSR_DE) |
4240 (1ull << MSR_FE1) |
4241 (1ull << MSR_EP) |
4242 (1ull << MSR_RI) |
4243 (1ull << MSR_LE);
4244 pcc->mmu_model = POWERPC_MMU_REAL;
4245 pcc->excp_model = POWERPC_EXCP_603;
4246 pcc->bus_model = PPC_FLAGS_INPUT_RCPU;
4247 pcc->bfd_mach = bfd_mach_ppc_505;
4248 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
4249 POWERPC_FLAG_BUS_CLK;
4252 static void init_proc_MPC8xx(CPUPPCState *env)
4254 /* Time base */
4255 gen_tbl(env);
4256 gen_spr_5xx_8xx(env);
4257 gen_spr_8xx(env);
4258 init_excp_MPC8xx(env);
4259 env->dcache_line_size = 32;
4260 env->icache_line_size = 32;
4261 /* XXX: TODO: allocate internal IRQ controller */
4264 POWERPC_FAMILY(MPC8xx)(ObjectClass *oc, void *data)
4266 DeviceClass *dc = DEVICE_CLASS(oc);
4267 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4269 dc->desc = "Freescale 8xx cores (aka PowerQUICC)";
4270 pcc->init_proc = init_proc_MPC8xx;
4271 pcc->check_pow = check_pow_none;
4272 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING |
4273 PPC_MEM_EIEIO | PPC_MEM_SYNC |
4274 PPC_CACHE_ICBI | PPC_MFTB;
4275 pcc->msr_mask = (1ull << MSR_ILE) |
4276 (1ull << MSR_EE) |
4277 (1ull << MSR_PR) |
4278 (1ull << MSR_FP) |
4279 (1ull << MSR_ME) |
4280 (1ull << MSR_SE) |
4281 (1ull << MSR_DE) |
4282 (1ull << MSR_EP) |
4283 (1ull << MSR_IR) |
4284 (1ull << MSR_DR) |
4285 (1ull << MSR_RI) |
4286 (1ull << MSR_LE);
4287 pcc->mmu_model = POWERPC_MMU_MPC8xx;
4288 pcc->excp_model = POWERPC_EXCP_603;
4289 pcc->bus_model = PPC_FLAGS_INPUT_RCPU;
4290 pcc->bfd_mach = bfd_mach_ppc_860;
4291 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
4292 POWERPC_FLAG_BUS_CLK;
4295 /* Freescale 82xx cores (aka PowerQUICC-II) */
4297 static void init_proc_G2(CPUPPCState *env)
4299 gen_spr_ne_601(env);
4300 gen_spr_sdr1(env);
4301 gen_spr_G2_755(env);
4302 gen_spr_G2(env);
4303 /* Time base */
4304 gen_tbl(env);
4305 /* External access control */
4306 /* XXX : not implemented */
4307 spr_register(env, SPR_EAR, "EAR",
4308 SPR_NOACCESS, SPR_NOACCESS,
4309 &spr_read_generic, &spr_write_generic,
4310 0x00000000);
4311 /* Hardware implementation register */
4312 /* XXX : not implemented */
4313 spr_register(env, SPR_HID0, "HID0",
4314 SPR_NOACCESS, SPR_NOACCESS,
4315 &spr_read_generic, &spr_write_generic,
4316 0x00000000);
4317 /* XXX : not implemented */
4318 spr_register(env, SPR_HID1, "HID1",
4319 SPR_NOACCESS, SPR_NOACCESS,
4320 &spr_read_generic, &spr_write_generic,
4321 0x00000000);
4322 /* XXX : not implemented */
4323 spr_register(env, SPR_HID2, "HID2",
4324 SPR_NOACCESS, SPR_NOACCESS,
4325 &spr_read_generic, &spr_write_generic,
4326 0x00000000);
4327 /* Memory management */
4328 gen_low_BATs(env);
4329 gen_high_BATs(env);
4330 gen_6xx_7xx_soft_tlb(env, 64, 2);
4331 init_excp_G2(env);
4332 env->dcache_line_size = 32;
4333 env->icache_line_size = 32;
4334 /* Allocate hardware IRQ controller */
4335 ppc6xx_irq_init(ppc_env_get_cpu(env));
4338 POWERPC_FAMILY(G2)(ObjectClass *oc, void *data)
4340 DeviceClass *dc = DEVICE_CLASS(oc);
4341 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4343 dc->desc = "PowerPC G2";
4344 pcc->init_proc = init_proc_G2;
4345 pcc->check_pow = check_pow_hid0;
4346 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
4347 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
4348 PPC_FLOAT_STFIWX |
4349 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
4350 PPC_MEM_SYNC | PPC_MEM_EIEIO |
4351 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
4352 PPC_SEGMENT | PPC_EXTERN;
4353 pcc->msr_mask = (1ull << MSR_POW) |
4354 (1ull << MSR_TGPR) |
4355 (1ull << MSR_EE) |
4356 (1ull << MSR_PR) |
4357 (1ull << MSR_FP) |
4358 (1ull << MSR_ME) |
4359 (1ull << MSR_FE0) |
4360 (1ull << MSR_SE) |
4361 (1ull << MSR_DE) |
4362 (1ull << MSR_FE1) |
4363 (1ull << MSR_AL) |
4364 (1ull << MSR_EP) |
4365 (1ull << MSR_IR) |
4366 (1ull << MSR_DR) |
4367 (1ull << MSR_RI);
4368 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
4369 pcc->excp_model = POWERPC_EXCP_G2;
4370 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
4371 pcc->bfd_mach = bfd_mach_ppc_ec603e;
4372 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
4373 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
4376 static void init_proc_G2LE(CPUPPCState *env)
4378 gen_spr_ne_601(env);
4379 gen_spr_sdr1(env);
4380 gen_spr_G2_755(env);
4381 gen_spr_G2(env);
4382 /* Time base */
4383 gen_tbl(env);
4384 /* External access control */
4385 /* XXX : not implemented */
4386 spr_register(env, SPR_EAR, "EAR",
4387 SPR_NOACCESS, SPR_NOACCESS,
4388 &spr_read_generic, &spr_write_generic,
4389 0x00000000);
4390 /* Hardware implementation register */
4391 /* XXX : not implemented */
4392 spr_register(env, SPR_HID0, "HID0",
4393 SPR_NOACCESS, SPR_NOACCESS,
4394 &spr_read_generic, &spr_write_generic,
4395 0x00000000);
4396 /* XXX : not implemented */
4397 spr_register(env, SPR_HID1, "HID1",
4398 SPR_NOACCESS, SPR_NOACCESS,
4399 &spr_read_generic, &spr_write_generic,
4400 0x00000000);
4401 /* XXX : not implemented */
4402 spr_register(env, SPR_HID2, "HID2",
4403 SPR_NOACCESS, SPR_NOACCESS,
4404 &spr_read_generic, &spr_write_generic,
4405 0x00000000);
4407 /* Memory management */
4408 gen_low_BATs(env);
4409 gen_high_BATs(env);
4410 gen_6xx_7xx_soft_tlb(env, 64, 2);
4411 init_excp_G2(env);
4412 env->dcache_line_size = 32;
4413 env->icache_line_size = 32;
4414 /* Allocate hardware IRQ controller */
4415 ppc6xx_irq_init(ppc_env_get_cpu(env));
4418 POWERPC_FAMILY(G2LE)(ObjectClass *oc, void *data)
4420 DeviceClass *dc = DEVICE_CLASS(oc);
4421 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4423 dc->desc = "PowerPC G2LE";
4424 pcc->init_proc = init_proc_G2LE;
4425 pcc->check_pow = check_pow_hid0;
4426 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
4427 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
4428 PPC_FLOAT_STFIWX |
4429 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
4430 PPC_MEM_SYNC | PPC_MEM_EIEIO |
4431 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
4432 PPC_SEGMENT | PPC_EXTERN;
4433 pcc->msr_mask = (1ull << MSR_POW) |
4434 (1ull << MSR_TGPR) |
4435 (1ull << MSR_ILE) |
4436 (1ull << MSR_EE) |
4437 (1ull << MSR_PR) |
4438 (1ull << MSR_FP) |
4439 (1ull << MSR_ME) |
4440 (1ull << MSR_FE0) |
4441 (1ull << MSR_SE) |
4442 (1ull << MSR_DE) |
4443 (1ull << MSR_FE1) |
4444 (1ull << MSR_AL) |
4445 (1ull << MSR_EP) |
4446 (1ull << MSR_IR) |
4447 (1ull << MSR_DR) |
4448 (1ull << MSR_RI) |
4449 (1ull << MSR_LE);
4450 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
4451 pcc->excp_model = POWERPC_EXCP_G2;
4452 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
4453 pcc->bfd_mach = bfd_mach_ppc_ec603e;
4454 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
4455 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
4458 static void init_proc_e200(CPUPPCState *env)
4460 /* Time base */
4461 gen_tbl(env);
4462 gen_spr_BookE(env, 0x000000070000FFFFULL);
4463 /* XXX : not implemented */
4464 spr_register(env, SPR_BOOKE_SPEFSCR, "SPEFSCR",
4465 &spr_read_spefscr, &spr_write_spefscr,
4466 &spr_read_spefscr, &spr_write_spefscr,
4467 0x00000000);
4468 /* Memory management */
4469 gen_spr_BookE206(env, 0x0000005D, NULL, 0);
4470 /* XXX : not implemented */
4471 spr_register(env, SPR_HID0, "HID0",
4472 SPR_NOACCESS, SPR_NOACCESS,
4473 &spr_read_generic, &spr_write_generic,
4474 0x00000000);
4475 /* XXX : not implemented */
4476 spr_register(env, SPR_HID1, "HID1",
4477 SPR_NOACCESS, SPR_NOACCESS,
4478 &spr_read_generic, &spr_write_generic,
4479 0x00000000);
4480 /* XXX : not implemented */
4481 spr_register(env, SPR_Exxx_ALTCTXCR, "ALTCTXCR",
4482 SPR_NOACCESS, SPR_NOACCESS,
4483 &spr_read_generic, &spr_write_generic,
4484 0x00000000);
4485 /* XXX : not implemented */
4486 spr_register(env, SPR_Exxx_BUCSR, "BUCSR",
4487 SPR_NOACCESS, SPR_NOACCESS,
4488 &spr_read_generic, &spr_write_generic,
4489 0x00000000);
4490 /* XXX : not implemented */
4491 spr_register(env, SPR_Exxx_CTXCR, "CTXCR",
4492 SPR_NOACCESS, SPR_NOACCESS,
4493 &spr_read_generic, &spr_write_generic,
4494 0x00000000);
4495 /* XXX : not implemented */
4496 spr_register(env, SPR_Exxx_DBCNT, "DBCNT",
4497 SPR_NOACCESS, SPR_NOACCESS,
4498 &spr_read_generic, &spr_write_generic,
4499 0x00000000);
4500 /* XXX : not implemented */
4501 spr_register(env, SPR_Exxx_DBCR3, "DBCR3",
4502 SPR_NOACCESS, SPR_NOACCESS,
4503 &spr_read_generic, &spr_write_generic,
4504 0x00000000);
4505 /* XXX : not implemented */
4506 spr_register(env, SPR_Exxx_L1CFG0, "L1CFG0",
4507 &spr_read_generic, SPR_NOACCESS,
4508 &spr_read_generic, SPR_NOACCESS,
4509 0x00000000);
4510 /* XXX : not implemented */
4511 spr_register(env, SPR_Exxx_L1CSR0, "L1CSR0",
4512 SPR_NOACCESS, SPR_NOACCESS,
4513 &spr_read_generic, &spr_write_generic,
4514 0x00000000);
4515 /* XXX : not implemented */
4516 spr_register(env, SPR_Exxx_L1FINV0, "L1FINV0",
4517 SPR_NOACCESS, SPR_NOACCESS,
4518 &spr_read_generic, &spr_write_generic,
4519 0x00000000);
4520 /* XXX : not implemented */
4521 spr_register(env, SPR_BOOKE_TLB0CFG, "TLB0CFG",
4522 SPR_NOACCESS, SPR_NOACCESS,
4523 &spr_read_generic, &spr_write_generic,
4524 0x00000000);
4525 /* XXX : not implemented */
4526 spr_register(env, SPR_BOOKE_TLB1CFG, "TLB1CFG",
4527 SPR_NOACCESS, SPR_NOACCESS,
4528 &spr_read_generic, &spr_write_generic,
4529 0x00000000);
4530 /* XXX : not implemented */
4531 spr_register(env, SPR_BOOKE_IAC3, "IAC3",
4532 SPR_NOACCESS, SPR_NOACCESS,
4533 &spr_read_generic, &spr_write_generic,
4534 0x00000000);
4535 /* XXX : not implemented */
4536 spr_register(env, SPR_BOOKE_IAC4, "IAC4",
4537 SPR_NOACCESS, SPR_NOACCESS,
4538 &spr_read_generic, &spr_write_generic,
4539 0x00000000);
4540 /* XXX : not implemented */
4541 spr_register(env, SPR_MMUCSR0, "MMUCSR0",
4542 SPR_NOACCESS, SPR_NOACCESS,
4543 &spr_read_generic, &spr_write_generic,
4544 0x00000000); /* TOFIX */
4545 spr_register(env, SPR_BOOKE_DSRR0, "DSRR0",
4546 SPR_NOACCESS, SPR_NOACCESS,
4547 &spr_read_generic, &spr_write_generic,
4548 0x00000000);
4549 spr_register(env, SPR_BOOKE_DSRR1, "DSRR1",
4550 SPR_NOACCESS, SPR_NOACCESS,
4551 &spr_read_generic, &spr_write_generic,
4552 0x00000000);
4553 #if !defined(CONFIG_USER_ONLY)
4554 env->nb_tlb = 64;
4555 env->nb_ways = 1;
4556 env->id_tlbs = 0;
4557 env->tlb_type = TLB_EMB;
4558 #endif
4559 init_excp_e200(env, 0xFFFF0000UL);
4560 env->dcache_line_size = 32;
4561 env->icache_line_size = 32;
4562 /* XXX: TODO: allocate internal IRQ controller */
4565 POWERPC_FAMILY(e200)(ObjectClass *oc, void *data)
4567 DeviceClass *dc = DEVICE_CLASS(oc);
4568 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4570 dc->desc = "e200 core";
4571 pcc->init_proc = init_proc_e200;
4572 pcc->check_pow = check_pow_hid0;
4573 /* XXX: unimplemented instructions:
4574 * dcblc
4575 * dcbtlst
4576 * dcbtstls
4577 * icblc
4578 * icbtls
4579 * tlbivax
4580 * all SPE multiply-accumulate instructions
4582 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL |
4583 PPC_SPE | PPC_SPE_SINGLE |
4584 PPC_WRTEE | PPC_RFDI |
4585 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
4586 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
4587 PPC_MEM_TLBSYNC | PPC_TLBIVAX |
4588 PPC_BOOKE;
4589 pcc->msr_mask = (1ull << MSR_UCLE) |
4590 (1ull << MSR_SPE) |
4591 (1ull << MSR_POW) |
4592 (1ull << MSR_CE) |
4593 (1ull << MSR_EE) |
4594 (1ull << MSR_PR) |
4595 (1ull << MSR_FP) |
4596 (1ull << MSR_ME) |
4597 (1ull << MSR_FE0) |
4598 (1ull << MSR_DWE) |
4599 (1ull << MSR_DE) |
4600 (1ull << MSR_FE1) |
4601 (1ull << MSR_IR) |
4602 (1ull << MSR_DR);
4603 pcc->mmu_model = POWERPC_MMU_BOOKE206;
4604 pcc->excp_model = POWERPC_EXCP_BOOKE;
4605 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
4606 pcc->bfd_mach = bfd_mach_ppc_860;
4607 pcc->flags = POWERPC_FLAG_SPE | POWERPC_FLAG_CE |
4608 POWERPC_FLAG_UBLE | POWERPC_FLAG_DE |
4609 POWERPC_FLAG_BUS_CLK;
4612 static void init_proc_e300(CPUPPCState *env)
4614 gen_spr_ne_601(env);
4615 gen_spr_sdr1(env);
4616 gen_spr_603(env);
4617 /* Time base */
4618 gen_tbl(env);
4619 /* hardware implementation registers */
4620 /* XXX : not implemented */
4621 spr_register(env, SPR_HID0, "HID0",
4622 SPR_NOACCESS, SPR_NOACCESS,
4623 &spr_read_generic, &spr_write_generic,
4624 0x00000000);
4625 /* XXX : not implemented */
4626 spr_register(env, SPR_HID1, "HID1",
4627 SPR_NOACCESS, SPR_NOACCESS,
4628 &spr_read_generic, &spr_write_generic,
4629 0x00000000);
4630 /* XXX : not implemented */
4631 spr_register(env, SPR_HID2, "HID2",
4632 SPR_NOACCESS, SPR_NOACCESS,
4633 &spr_read_generic, &spr_write_generic,
4634 0x00000000);
4635 /* Breakpoints */
4636 /* XXX : not implemented */
4637 spr_register(env, SPR_DABR, "DABR",
4638 SPR_NOACCESS, SPR_NOACCESS,
4639 &spr_read_generic, &spr_write_generic,
4640 0x00000000);
4641 /* XXX : not implemented */
4642 spr_register(env, SPR_DABR2, "DABR2",
4643 SPR_NOACCESS, SPR_NOACCESS,
4644 &spr_read_generic, &spr_write_generic,
4645 0x00000000);
4646 /* XXX : not implemented */
4647 spr_register(env, SPR_IABR2, "IABR2",
4648 SPR_NOACCESS, SPR_NOACCESS,
4649 &spr_read_generic, &spr_write_generic,
4650 0x00000000);
4651 /* XXX : not implemented */
4652 spr_register(env, SPR_IBCR, "IBCR",
4653 SPR_NOACCESS, SPR_NOACCESS,
4654 &spr_read_generic, &spr_write_generic,
4655 0x00000000);
4656 /* XXX : not implemented */
4657 spr_register(env, SPR_DBCR, "DBCR",
4658 SPR_NOACCESS, SPR_NOACCESS,
4659 &spr_read_generic, &spr_write_generic,
4660 0x00000000);
4661 /* Memory management */
4662 gen_low_BATs(env);
4663 gen_high_BATs(env);
4664 gen_6xx_7xx_soft_tlb(env, 64, 2);
4665 init_excp_603(env);
4666 env->dcache_line_size = 32;
4667 env->icache_line_size = 32;
4668 /* Allocate hardware IRQ controller */
4669 ppc6xx_irq_init(ppc_env_get_cpu(env));
4672 POWERPC_FAMILY(e300)(ObjectClass *oc, void *data)
4674 DeviceClass *dc = DEVICE_CLASS(oc);
4675 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4677 dc->desc = "e300 core";
4678 pcc->init_proc = init_proc_e300;
4679 pcc->check_pow = check_pow_hid0;
4680 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
4681 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
4682 PPC_FLOAT_STFIWX |
4683 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
4684 PPC_MEM_SYNC | PPC_MEM_EIEIO |
4685 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
4686 PPC_SEGMENT | PPC_EXTERN;
4687 pcc->msr_mask = (1ull << MSR_POW) |
4688 (1ull << MSR_TGPR) |
4689 (1ull << MSR_ILE) |
4690 (1ull << MSR_EE) |
4691 (1ull << MSR_PR) |
4692 (1ull << MSR_FP) |
4693 (1ull << MSR_ME) |
4694 (1ull << MSR_FE0) |
4695 (1ull << MSR_SE) |
4696 (1ull << MSR_DE) |
4697 (1ull << MSR_FE1) |
4698 (1ull << MSR_AL) |
4699 (1ull << MSR_EP) |
4700 (1ull << MSR_IR) |
4701 (1ull << MSR_DR) |
4702 (1ull << MSR_RI) |
4703 (1ull << MSR_LE);
4704 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
4705 pcc->excp_model = POWERPC_EXCP_603;
4706 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
4707 pcc->bfd_mach = bfd_mach_ppc_603;
4708 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
4709 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
4712 #if !defined(CONFIG_USER_ONLY)
4713 static void spr_write_mas73(DisasContext *ctx, int sprn, int gprn)
4715 TCGv val = tcg_temp_new();
4716 tcg_gen_ext32u_tl(val, cpu_gpr[gprn]);
4717 gen_store_spr(SPR_BOOKE_MAS3, val);
4718 tcg_gen_shri_tl(val, cpu_gpr[gprn], 32);
4719 gen_store_spr(SPR_BOOKE_MAS7, val);
4720 tcg_temp_free(val);
4723 static void spr_read_mas73(DisasContext *ctx, int gprn, int sprn)
4725 TCGv mas7 = tcg_temp_new();
4726 TCGv mas3 = tcg_temp_new();
4727 gen_load_spr(mas7, SPR_BOOKE_MAS7);
4728 tcg_gen_shli_tl(mas7, mas7, 32);
4729 gen_load_spr(mas3, SPR_BOOKE_MAS3);
4730 tcg_gen_or_tl(cpu_gpr[gprn], mas3, mas7);
4731 tcg_temp_free(mas3);
4732 tcg_temp_free(mas7);
4735 #endif
4737 enum fsl_e500_version {
4738 fsl_e500v1,
4739 fsl_e500v2,
4740 fsl_e500mc,
4741 fsl_e5500,
4742 fsl_e6500,
4745 static void init_proc_e500(CPUPPCState *env, int version)
4747 PowerPCCPU *cpu = ppc_env_get_cpu(env);
4748 uint32_t tlbncfg[2];
4749 uint64_t ivor_mask;
4750 uint64_t ivpr_mask = 0xFFFF0000ULL;
4751 uint32_t l1cfg0 = 0x3800 /* 8 ways */
4752 | 0x0020; /* 32 kb */
4753 uint32_t l1cfg1 = 0x3800 /* 8 ways */
4754 | 0x0020; /* 32 kb */
4755 uint32_t mmucfg = 0;
4756 #if !defined(CONFIG_USER_ONLY)
4757 int i;
4758 #endif
4760 /* Time base */
4761 gen_tbl(env);
4763 * XXX The e500 doesn't implement IVOR7 and IVOR9, but doesn't
4764 * complain when accessing them.
4765 * gen_spr_BookE(env, 0x0000000F0000FD7FULL);
4767 switch (version) {
4768 case fsl_e500v1:
4769 case fsl_e500v2:
4770 default:
4771 ivor_mask = 0x0000000F0000FFFFULL;
4772 break;
4773 case fsl_e500mc:
4774 case fsl_e5500:
4775 ivor_mask = 0x000003FE0000FFFFULL;
4776 break;
4777 case fsl_e6500:
4778 ivor_mask = 0x000003FF0000FFFFULL;
4779 break;
4781 gen_spr_BookE(env, ivor_mask);
4782 gen_spr_usprg3(env);
4783 /* Processor identification */
4784 spr_register(env, SPR_BOOKE_PIR, "PIR",
4785 SPR_NOACCESS, SPR_NOACCESS,
4786 &spr_read_generic, &spr_write_pir,
4787 0x00000000);
4788 /* XXX : not implemented */
4789 spr_register(env, SPR_BOOKE_SPEFSCR, "SPEFSCR",
4790 &spr_read_spefscr, &spr_write_spefscr,
4791 &spr_read_spefscr, &spr_write_spefscr,
4792 0x00000000);
4793 #if !defined(CONFIG_USER_ONLY)
4794 /* Memory management */
4795 env->nb_pids = 3;
4796 env->nb_ways = 2;
4797 env->id_tlbs = 0;
4798 switch (version) {
4799 case fsl_e500v1:
4800 tlbncfg[0] = gen_tlbncfg(2, 1, 1, 0, 256);
4801 tlbncfg[1] = gen_tlbncfg(16, 1, 9, TLBnCFG_AVAIL | TLBnCFG_IPROT, 16);
4802 break;
4803 case fsl_e500v2:
4804 tlbncfg[0] = gen_tlbncfg(4, 1, 1, 0, 512);
4805 tlbncfg[1] = gen_tlbncfg(16, 1, 12, TLBnCFG_AVAIL | TLBnCFG_IPROT, 16);
4806 break;
4807 case fsl_e500mc:
4808 case fsl_e5500:
4809 tlbncfg[0] = gen_tlbncfg(4, 1, 1, 0, 512);
4810 tlbncfg[1] = gen_tlbncfg(64, 1, 12, TLBnCFG_AVAIL | TLBnCFG_IPROT, 64);
4811 break;
4812 case fsl_e6500:
4813 mmucfg = 0x6510B45;
4814 env->nb_pids = 1;
4815 tlbncfg[0] = 0x08052400;
4816 tlbncfg[1] = 0x40028040;
4817 break;
4818 default:
4819 cpu_abort(CPU(cpu), "Unknown CPU: " TARGET_FMT_lx "\n", env->spr[SPR_PVR]);
4821 #endif
4822 /* Cache sizes */
4823 switch (version) {
4824 case fsl_e500v1:
4825 case fsl_e500v2:
4826 env->dcache_line_size = 32;
4827 env->icache_line_size = 32;
4828 break;
4829 case fsl_e500mc:
4830 case fsl_e5500:
4831 env->dcache_line_size = 64;
4832 env->icache_line_size = 64;
4833 l1cfg0 |= 0x1000000; /* 64 byte cache block size */
4834 l1cfg1 |= 0x1000000; /* 64 byte cache block size */
4835 break;
4836 case fsl_e6500:
4837 env->dcache_line_size = 32;
4838 env->icache_line_size = 32;
4839 l1cfg0 |= 0x0F83820;
4840 l1cfg1 |= 0x0B83820;
4841 break;
4842 default:
4843 cpu_abort(CPU(cpu), "Unknown CPU: " TARGET_FMT_lx "\n", env->spr[SPR_PVR]);
4845 gen_spr_BookE206(env, 0x000000DF, tlbncfg, mmucfg);
4846 /* XXX : not implemented */
4847 spr_register(env, SPR_HID0, "HID0",
4848 SPR_NOACCESS, SPR_NOACCESS,
4849 &spr_read_generic, &spr_write_generic,
4850 0x00000000);
4851 /* XXX : not implemented */
4852 spr_register(env, SPR_HID1, "HID1",
4853 SPR_NOACCESS, SPR_NOACCESS,
4854 &spr_read_generic, &spr_write_generic,
4855 0x00000000);
4856 /* XXX : not implemented */
4857 spr_register(env, SPR_Exxx_BBEAR, "BBEAR",
4858 SPR_NOACCESS, SPR_NOACCESS,
4859 &spr_read_generic, &spr_write_generic,
4860 0x00000000);
4861 /* XXX : not implemented */
4862 spr_register(env, SPR_Exxx_BBTAR, "BBTAR",
4863 SPR_NOACCESS, SPR_NOACCESS,
4864 &spr_read_generic, &spr_write_generic,
4865 0x00000000);
4866 /* XXX : not implemented */
4867 spr_register(env, SPR_Exxx_MCAR, "MCAR",
4868 SPR_NOACCESS, SPR_NOACCESS,
4869 &spr_read_generic, &spr_write_generic,
4870 0x00000000);
4871 /* XXX : not implemented */
4872 spr_register(env, SPR_BOOKE_MCSR, "MCSR",
4873 SPR_NOACCESS, SPR_NOACCESS,
4874 &spr_read_generic, &spr_write_generic,
4875 0x00000000);
4876 /* XXX : not implemented */
4877 spr_register(env, SPR_Exxx_NPIDR, "NPIDR",
4878 SPR_NOACCESS, SPR_NOACCESS,
4879 &spr_read_generic, &spr_write_generic,
4880 0x00000000);
4881 /* XXX : not implemented */
4882 spr_register(env, SPR_Exxx_BUCSR, "BUCSR",
4883 SPR_NOACCESS, SPR_NOACCESS,
4884 &spr_read_generic, &spr_write_generic,
4885 0x00000000);
4886 /* XXX : not implemented */
4887 spr_register(env, SPR_Exxx_L1CFG0, "L1CFG0",
4888 &spr_read_generic, SPR_NOACCESS,
4889 &spr_read_generic, SPR_NOACCESS,
4890 l1cfg0);
4891 spr_register(env, SPR_Exxx_L1CFG1, "L1CFG1",
4892 &spr_read_generic, SPR_NOACCESS,
4893 &spr_read_generic, SPR_NOACCESS,
4894 l1cfg1);
4895 spr_register(env, SPR_Exxx_L1CSR0, "L1CSR0",
4896 SPR_NOACCESS, SPR_NOACCESS,
4897 &spr_read_generic, &spr_write_e500_l1csr0,
4898 0x00000000);
4899 spr_register(env, SPR_Exxx_L1CSR1, "L1CSR1",
4900 SPR_NOACCESS, SPR_NOACCESS,
4901 &spr_read_generic, &spr_write_e500_l1csr1,
4902 0x00000000);
4903 spr_register(env, SPR_BOOKE_MCSRR0, "MCSRR0",
4904 SPR_NOACCESS, SPR_NOACCESS,
4905 &spr_read_generic, &spr_write_generic,
4906 0x00000000);
4907 spr_register(env, SPR_BOOKE_MCSRR1, "MCSRR1",
4908 SPR_NOACCESS, SPR_NOACCESS,
4909 &spr_read_generic, &spr_write_generic,
4910 0x00000000);
4911 spr_register(env, SPR_MMUCSR0, "MMUCSR0",
4912 SPR_NOACCESS, SPR_NOACCESS,
4913 &spr_read_generic, &spr_write_booke206_mmucsr0,
4914 0x00000000);
4915 spr_register(env, SPR_BOOKE_EPR, "EPR",
4916 SPR_NOACCESS, SPR_NOACCESS,
4917 &spr_read_generic, SPR_NOACCESS,
4918 0x00000000);
4919 /* XXX better abstract into Emb.xxx features */
4920 if ((version == fsl_e5500) || (version == fsl_e6500)) {
4921 spr_register(env, SPR_BOOKE_EPCR, "EPCR",
4922 SPR_NOACCESS, SPR_NOACCESS,
4923 &spr_read_generic, &spr_write_generic,
4924 0x00000000);
4925 spr_register(env, SPR_BOOKE_MAS7_MAS3, "MAS7_MAS3",
4926 SPR_NOACCESS, SPR_NOACCESS,
4927 &spr_read_mas73, &spr_write_mas73,
4928 0x00000000);
4929 ivpr_mask = (target_ulong)~0xFFFFULL;
4932 if (version == fsl_e6500) {
4933 spr_register(env, SPR_BOOKE_SPRG8, "SPRG8",
4934 SPR_NOACCESS, SPR_NOACCESS,
4935 &spr_read_generic, &spr_write_generic,
4936 0x00000000);
4937 spr_register(env, SPR_BOOKE_SPRG9, "SPRG9",
4938 SPR_NOACCESS, SPR_NOACCESS,
4939 &spr_read_generic, &spr_write_generic,
4940 0x00000000);
4941 /* Thread identification */
4942 spr_register(env, SPR_TIR, "TIR",
4943 SPR_NOACCESS, SPR_NOACCESS,
4944 &spr_read_generic, SPR_NOACCESS,
4945 0x00000000);
4946 spr_register(env, SPR_BOOKE_TLB0PS, "TLB0PS",
4947 SPR_NOACCESS, SPR_NOACCESS,
4948 &spr_read_generic, SPR_NOACCESS,
4949 0x00000004);
4950 spr_register(env, SPR_BOOKE_TLB1PS, "TLB1PS",
4951 SPR_NOACCESS, SPR_NOACCESS,
4952 &spr_read_generic, SPR_NOACCESS,
4953 0x7FFFFFFC);
4956 #if !defined(CONFIG_USER_ONLY)
4957 env->nb_tlb = 0;
4958 env->tlb_type = TLB_MAS;
4959 for (i = 0; i < BOOKE206_MAX_TLBN; i++) {
4960 env->nb_tlb += booke206_tlb_size(env, i);
4962 #endif
4964 init_excp_e200(env, ivpr_mask);
4965 /* Allocate hardware IRQ controller */
4966 ppce500_irq_init(ppc_env_get_cpu(env));
4969 static void init_proc_e500v1(CPUPPCState *env)
4971 init_proc_e500(env, fsl_e500v1);
4974 POWERPC_FAMILY(e500v1)(ObjectClass *oc, void *data)
4976 DeviceClass *dc = DEVICE_CLASS(oc);
4977 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
4979 dc->desc = "e500v1 core";
4980 pcc->init_proc = init_proc_e500v1;
4981 pcc->check_pow = check_pow_hid0;
4982 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL |
4983 PPC_SPE | PPC_SPE_SINGLE |
4984 PPC_WRTEE | PPC_RFDI |
4985 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
4986 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
4987 PPC_MEM_TLBSYNC | PPC_TLBIVAX | PPC_MEM_SYNC;
4988 pcc->insns_flags2 = PPC2_BOOKE206;
4989 pcc->msr_mask = (1ull << MSR_UCLE) |
4990 (1ull << MSR_SPE) |
4991 (1ull << MSR_POW) |
4992 (1ull << MSR_CE) |
4993 (1ull << MSR_EE) |
4994 (1ull << MSR_PR) |
4995 (1ull << MSR_FP) |
4996 (1ull << MSR_ME) |
4997 (1ull << MSR_FE0) |
4998 (1ull << MSR_DWE) |
4999 (1ull << MSR_DE) |
5000 (1ull << MSR_FE1) |
5001 (1ull << MSR_IR) |
5002 (1ull << MSR_DR);
5003 pcc->mmu_model = POWERPC_MMU_BOOKE206;
5004 pcc->excp_model = POWERPC_EXCP_BOOKE;
5005 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
5006 pcc->bfd_mach = bfd_mach_ppc_860;
5007 pcc->flags = POWERPC_FLAG_SPE | POWERPC_FLAG_CE |
5008 POWERPC_FLAG_UBLE | POWERPC_FLAG_DE |
5009 POWERPC_FLAG_BUS_CLK;
5012 static void init_proc_e500v2(CPUPPCState *env)
5014 init_proc_e500(env, fsl_e500v2);
5017 POWERPC_FAMILY(e500v2)(ObjectClass *oc, void *data)
5019 DeviceClass *dc = DEVICE_CLASS(oc);
5020 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5022 dc->desc = "e500v2 core";
5023 pcc->init_proc = init_proc_e500v2;
5024 pcc->check_pow = check_pow_hid0;
5025 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL |
5026 PPC_SPE | PPC_SPE_SINGLE | PPC_SPE_DOUBLE |
5027 PPC_WRTEE | PPC_RFDI |
5028 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
5029 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
5030 PPC_MEM_TLBSYNC | PPC_TLBIVAX | PPC_MEM_SYNC;
5031 pcc->insns_flags2 = PPC2_BOOKE206;
5032 pcc->msr_mask = (1ull << MSR_UCLE) |
5033 (1ull << MSR_SPE) |
5034 (1ull << MSR_POW) |
5035 (1ull << MSR_CE) |
5036 (1ull << MSR_EE) |
5037 (1ull << MSR_PR) |
5038 (1ull << MSR_FP) |
5039 (1ull << MSR_ME) |
5040 (1ull << MSR_FE0) |
5041 (1ull << MSR_DWE) |
5042 (1ull << MSR_DE) |
5043 (1ull << MSR_FE1) |
5044 (1ull << MSR_IR) |
5045 (1ull << MSR_DR);
5046 pcc->mmu_model = POWERPC_MMU_BOOKE206;
5047 pcc->excp_model = POWERPC_EXCP_BOOKE;
5048 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
5049 pcc->bfd_mach = bfd_mach_ppc_860;
5050 pcc->flags = POWERPC_FLAG_SPE | POWERPC_FLAG_CE |
5051 POWERPC_FLAG_UBLE | POWERPC_FLAG_DE |
5052 POWERPC_FLAG_BUS_CLK;
5055 static void init_proc_e500mc(CPUPPCState *env)
5057 init_proc_e500(env, fsl_e500mc);
5060 POWERPC_FAMILY(e500mc)(ObjectClass *oc, void *data)
5062 DeviceClass *dc = DEVICE_CLASS(oc);
5063 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5065 dc->desc = "e500mc core";
5066 pcc->init_proc = init_proc_e500mc;
5067 pcc->check_pow = check_pow_none;
5068 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_MFTB |
5069 PPC_WRTEE | PPC_RFDI | PPC_RFMCI |
5070 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
5071 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
5072 PPC_FLOAT | PPC_FLOAT_FRES |
5073 PPC_FLOAT_FRSQRTE | PPC_FLOAT_FSEL |
5074 PPC_FLOAT_STFIWX | PPC_WAIT |
5075 PPC_MEM_TLBSYNC | PPC_TLBIVAX | PPC_MEM_SYNC;
5076 pcc->insns_flags2 = PPC2_BOOKE206 | PPC2_PRCNTL;
5077 pcc->msr_mask = (1ull << MSR_GS) |
5078 (1ull << MSR_UCLE) |
5079 (1ull << MSR_CE) |
5080 (1ull << MSR_EE) |
5081 (1ull << MSR_PR) |
5082 (1ull << MSR_FP) |
5083 (1ull << MSR_ME) |
5084 (1ull << MSR_FE0) |
5085 (1ull << MSR_DE) |
5086 (1ull << MSR_FE1) |
5087 (1ull << MSR_IR) |
5088 (1ull << MSR_DR) |
5089 (1ull << MSR_PX) |
5090 (1ull << MSR_RI);
5091 pcc->mmu_model = POWERPC_MMU_BOOKE206;
5092 pcc->excp_model = POWERPC_EXCP_BOOKE;
5093 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
5094 /* FIXME: figure out the correct flag for e500mc */
5095 pcc->bfd_mach = bfd_mach_ppc_e500;
5096 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
5097 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5100 #ifdef TARGET_PPC64
5101 static void init_proc_e5500(CPUPPCState *env)
5103 init_proc_e500(env, fsl_e5500);
5106 POWERPC_FAMILY(e5500)(ObjectClass *oc, void *data)
5108 DeviceClass *dc = DEVICE_CLASS(oc);
5109 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5111 dc->desc = "e5500 core";
5112 pcc->init_proc = init_proc_e5500;
5113 pcc->check_pow = check_pow_none;
5114 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_MFTB |
5115 PPC_WRTEE | PPC_RFDI | PPC_RFMCI |
5116 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
5117 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
5118 PPC_FLOAT | PPC_FLOAT_FRES |
5119 PPC_FLOAT_FRSQRTE | PPC_FLOAT_FSEL |
5120 PPC_FLOAT_STFIWX | PPC_WAIT |
5121 PPC_MEM_TLBSYNC | PPC_TLBIVAX | PPC_MEM_SYNC |
5122 PPC_64B | PPC_POPCNTB | PPC_POPCNTWD;
5123 pcc->insns_flags2 = PPC2_BOOKE206 | PPC2_PRCNTL | PPC2_PERM_ISA206 | \
5124 PPC2_FP_CVT_S64;
5125 pcc->msr_mask = (1ull << MSR_CM) |
5126 (1ull << MSR_GS) |
5127 (1ull << MSR_UCLE) |
5128 (1ull << MSR_CE) |
5129 (1ull << MSR_EE) |
5130 (1ull << MSR_PR) |
5131 (1ull << MSR_FP) |
5132 (1ull << MSR_ME) |
5133 (1ull << MSR_FE0) |
5134 (1ull << MSR_DE) |
5135 (1ull << MSR_FE1) |
5136 (1ull << MSR_IR) |
5137 (1ull << MSR_DR) |
5138 (1ull << MSR_PX) |
5139 (1ull << MSR_RI);
5140 pcc->mmu_model = POWERPC_MMU_BOOKE206;
5141 pcc->excp_model = POWERPC_EXCP_BOOKE;
5142 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
5143 /* FIXME: figure out the correct flag for e5500 */
5144 pcc->bfd_mach = bfd_mach_ppc_e500;
5145 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
5146 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5149 static void init_proc_e6500(CPUPPCState *env)
5151 init_proc_e500(env, fsl_e6500);
5154 POWERPC_FAMILY(e6500)(ObjectClass *oc, void *data)
5156 DeviceClass *dc = DEVICE_CLASS(oc);
5157 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5159 dc->desc = "e6500 core";
5160 pcc->init_proc = init_proc_e6500;
5161 pcc->check_pow = check_pow_none;
5162 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_MFTB |
5163 PPC_WRTEE | PPC_RFDI | PPC_RFMCI |
5164 PPC_CACHE | PPC_CACHE_LOCK | PPC_CACHE_ICBI |
5165 PPC_CACHE_DCBZ | PPC_CACHE_DCBA |
5166 PPC_FLOAT | PPC_FLOAT_FRES |
5167 PPC_FLOAT_FRSQRTE | PPC_FLOAT_FSEL |
5168 PPC_FLOAT_STFIWX | PPC_WAIT |
5169 PPC_MEM_TLBSYNC | PPC_TLBIVAX | PPC_MEM_SYNC |
5170 PPC_64B | PPC_POPCNTB | PPC_POPCNTWD | PPC_ALTIVEC;
5171 pcc->insns_flags2 = PPC2_BOOKE206 | PPC2_PRCNTL | PPC2_PERM_ISA206 | \
5172 PPC2_FP_CVT_S64 | PPC2_ATOMIC_ISA206;
5173 pcc->msr_mask = (1ull << MSR_CM) |
5174 (1ull << MSR_GS) |
5175 (1ull << MSR_UCLE) |
5176 (1ull << MSR_CE) |
5177 (1ull << MSR_EE) |
5178 (1ull << MSR_PR) |
5179 (1ull << MSR_FP) |
5180 (1ull << MSR_ME) |
5181 (1ull << MSR_FE0) |
5182 (1ull << MSR_DE) |
5183 (1ull << MSR_FE1) |
5184 (1ull << MSR_IS) |
5185 (1ull << MSR_DS) |
5186 (1ull << MSR_PX) |
5187 (1ull << MSR_RI) |
5188 (1ull << MSR_VR);
5189 pcc->mmu_model = POWERPC_MMU_BOOKE206;
5190 pcc->excp_model = POWERPC_EXCP_BOOKE;
5191 pcc->bus_model = PPC_FLAGS_INPUT_BookE;
5192 pcc->bfd_mach = bfd_mach_ppc_e500;
5193 pcc->flags = POWERPC_FLAG_CE | POWERPC_FLAG_DE |
5194 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK | POWERPC_FLAG_VRE;
5197 #endif
5199 /* Non-embedded PowerPC */
5201 #define POWERPC_MSRR_601 (0x0000000000001040ULL)
5203 static void init_proc_601(CPUPPCState *env)
5205 gen_spr_ne_601(env);
5206 gen_spr_sdr1(env);
5207 gen_spr_601(env);
5208 /* Hardware implementation registers */
5209 /* XXX : not implemented */
5210 spr_register(env, SPR_HID0, "HID0",
5211 SPR_NOACCESS, SPR_NOACCESS,
5212 &spr_read_generic, &spr_write_hid0_601,
5213 0x80010080);
5214 /* XXX : not implemented */
5215 spr_register(env, SPR_HID1, "HID1",
5216 SPR_NOACCESS, SPR_NOACCESS,
5217 &spr_read_generic, &spr_write_generic,
5218 0x00000000);
5219 /* XXX : not implemented */
5220 spr_register(env, SPR_601_HID2, "HID2",
5221 SPR_NOACCESS, SPR_NOACCESS,
5222 &spr_read_generic, &spr_write_generic,
5223 0x00000000);
5224 /* XXX : not implemented */
5225 spr_register(env, SPR_601_HID5, "HID5",
5226 SPR_NOACCESS, SPR_NOACCESS,
5227 &spr_read_generic, &spr_write_generic,
5228 0x00000000);
5229 /* Memory management */
5230 init_excp_601(env);
5231 /* XXX: beware that dcache line size is 64
5232 * but dcbz uses 32 bytes "sectors"
5233 * XXX: this breaks clcs instruction !
5235 env->dcache_line_size = 32;
5236 env->icache_line_size = 64;
5237 /* Allocate hardware IRQ controller */
5238 ppc6xx_irq_init(ppc_env_get_cpu(env));
5241 POWERPC_FAMILY(601)(ObjectClass *oc, void *data)
5243 DeviceClass *dc = DEVICE_CLASS(oc);
5244 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5246 dc->desc = "PowerPC 601";
5247 pcc->init_proc = init_proc_601;
5248 pcc->check_pow = check_pow_none;
5249 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_POWER_BR |
5250 PPC_FLOAT |
5251 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5252 PPC_MEM_SYNC | PPC_MEM_EIEIO | PPC_MEM_TLBIE |
5253 PPC_SEGMENT | PPC_EXTERN;
5254 pcc->msr_mask = (1ull << MSR_EE) |
5255 (1ull << MSR_PR) |
5256 (1ull << MSR_FP) |
5257 (1ull << MSR_ME) |
5258 (1ull << MSR_FE0) |
5259 (1ull << MSR_SE) |
5260 (1ull << MSR_FE1) |
5261 (1ull << MSR_EP) |
5262 (1ull << MSR_IR) |
5263 (1ull << MSR_DR);
5264 pcc->mmu_model = POWERPC_MMU_601;
5265 #if defined(CONFIG_SOFTMMU)
5266 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5267 #endif
5268 pcc->excp_model = POWERPC_EXCP_601;
5269 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5270 pcc->bfd_mach = bfd_mach_ppc_601;
5271 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_RTC_CLK;
5274 #define POWERPC_MSRR_601v (0x0000000000001040ULL)
5276 static void init_proc_601v(CPUPPCState *env)
5278 init_proc_601(env);
5279 /* XXX : not implemented */
5280 spr_register(env, SPR_601_HID15, "HID15",
5281 SPR_NOACCESS, SPR_NOACCESS,
5282 &spr_read_generic, &spr_write_generic,
5283 0x00000000);
5286 POWERPC_FAMILY(601v)(ObjectClass *oc, void *data)
5288 DeviceClass *dc = DEVICE_CLASS(oc);
5289 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5291 dc->desc = "PowerPC 601v";
5292 pcc->init_proc = init_proc_601v;
5293 pcc->check_pow = check_pow_none;
5294 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_POWER_BR |
5295 PPC_FLOAT |
5296 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5297 PPC_MEM_SYNC | PPC_MEM_EIEIO | PPC_MEM_TLBIE |
5298 PPC_SEGMENT | PPC_EXTERN;
5299 pcc->msr_mask = (1ull << MSR_EE) |
5300 (1ull << MSR_PR) |
5301 (1ull << MSR_FP) |
5302 (1ull << MSR_ME) |
5303 (1ull << MSR_FE0) |
5304 (1ull << MSR_SE) |
5305 (1ull << MSR_FE1) |
5306 (1ull << MSR_EP) |
5307 (1ull << MSR_IR) |
5308 (1ull << MSR_DR);
5309 pcc->mmu_model = POWERPC_MMU_601;
5310 #if defined(CONFIG_SOFTMMU)
5311 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5312 #endif
5313 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5314 pcc->bfd_mach = bfd_mach_ppc_601;
5315 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_RTC_CLK;
5318 static void init_proc_602(CPUPPCState *env)
5320 gen_spr_ne_601(env);
5321 gen_spr_sdr1(env);
5322 gen_spr_602(env);
5323 /* Time base */
5324 gen_tbl(env);
5325 /* hardware implementation registers */
5326 /* XXX : not implemented */
5327 spr_register(env, SPR_HID0, "HID0",
5328 SPR_NOACCESS, SPR_NOACCESS,
5329 &spr_read_generic, &spr_write_generic,
5330 0x00000000);
5331 /* XXX : not implemented */
5332 spr_register(env, SPR_HID1, "HID1",
5333 SPR_NOACCESS, SPR_NOACCESS,
5334 &spr_read_generic, &spr_write_generic,
5335 0x00000000);
5336 /* Memory management */
5337 gen_low_BATs(env);
5338 gen_6xx_7xx_soft_tlb(env, 64, 2);
5339 init_excp_602(env);
5340 env->dcache_line_size = 32;
5341 env->icache_line_size = 32;
5342 /* Allocate hardware IRQ controller */
5343 ppc6xx_irq_init(ppc_env_get_cpu(env));
5346 POWERPC_FAMILY(602)(ObjectClass *oc, void *data)
5348 DeviceClass *dc = DEVICE_CLASS(oc);
5349 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5351 dc->desc = "PowerPC 602";
5352 pcc->init_proc = init_proc_602;
5353 pcc->check_pow = check_pow_hid0;
5354 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5355 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5356 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5357 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5358 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5359 PPC_MEM_TLBIE | PPC_6xx_TLB | PPC_MEM_TLBSYNC |
5360 PPC_SEGMENT | PPC_602_SPEC;
5361 pcc->msr_mask = (1ull << MSR_VSX) |
5362 (1ull << MSR_SA) |
5363 (1ull << MSR_POW) |
5364 (1ull << MSR_TGPR) |
5365 (1ull << MSR_ILE) |
5366 (1ull << MSR_EE) |
5367 (1ull << MSR_PR) |
5368 (1ull << MSR_FP) |
5369 (1ull << MSR_ME) |
5370 (1ull << MSR_FE0) |
5371 (1ull << MSR_SE) |
5372 (1ull << MSR_DE) |
5373 (1ull << MSR_FE1) |
5374 (1ull << MSR_EP) |
5375 (1ull << MSR_IR) |
5376 (1ull << MSR_DR) |
5377 (1ull << MSR_RI) |
5378 (1ull << MSR_LE);
5379 /* XXX: 602 MMU is quite specific. Should add a special case */
5380 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
5381 pcc->excp_model = POWERPC_EXCP_602;
5382 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5383 pcc->bfd_mach = bfd_mach_ppc_602;
5384 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
5385 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
5388 static void init_proc_603(CPUPPCState *env)
5390 gen_spr_ne_601(env);
5391 gen_spr_sdr1(env);
5392 gen_spr_603(env);
5393 /* Time base */
5394 gen_tbl(env);
5395 /* hardware implementation registers */
5396 /* XXX : not implemented */
5397 spr_register(env, SPR_HID0, "HID0",
5398 SPR_NOACCESS, SPR_NOACCESS,
5399 &spr_read_generic, &spr_write_generic,
5400 0x00000000);
5401 /* XXX : not implemented */
5402 spr_register(env, SPR_HID1, "HID1",
5403 SPR_NOACCESS, SPR_NOACCESS,
5404 &spr_read_generic, &spr_write_generic,
5405 0x00000000);
5406 /* Memory management */
5407 gen_low_BATs(env);
5408 gen_6xx_7xx_soft_tlb(env, 64, 2);
5409 init_excp_603(env);
5410 env->dcache_line_size = 32;
5411 env->icache_line_size = 32;
5412 /* Allocate hardware IRQ controller */
5413 ppc6xx_irq_init(ppc_env_get_cpu(env));
5416 POWERPC_FAMILY(603)(ObjectClass *oc, void *data)
5418 DeviceClass *dc = DEVICE_CLASS(oc);
5419 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5421 dc->desc = "PowerPC 603";
5422 pcc->init_proc = init_proc_603;
5423 pcc->check_pow = check_pow_hid0;
5424 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5425 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5426 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5427 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5428 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5429 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
5430 PPC_SEGMENT | PPC_EXTERN;
5431 pcc->msr_mask = (1ull << MSR_POW) |
5432 (1ull << MSR_TGPR) |
5433 (1ull << MSR_ILE) |
5434 (1ull << MSR_EE) |
5435 (1ull << MSR_PR) |
5436 (1ull << MSR_FP) |
5437 (1ull << MSR_ME) |
5438 (1ull << MSR_FE0) |
5439 (1ull << MSR_SE) |
5440 (1ull << MSR_DE) |
5441 (1ull << MSR_FE1) |
5442 (1ull << MSR_EP) |
5443 (1ull << MSR_IR) |
5444 (1ull << MSR_DR) |
5445 (1ull << MSR_RI) |
5446 (1ull << MSR_LE);
5447 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
5448 pcc->excp_model = POWERPC_EXCP_603;
5449 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5450 pcc->bfd_mach = bfd_mach_ppc_603;
5451 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
5452 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
5455 static void init_proc_603E(CPUPPCState *env)
5457 gen_spr_ne_601(env);
5458 gen_spr_sdr1(env);
5459 gen_spr_603(env);
5460 /* Time base */
5461 gen_tbl(env);
5462 /* hardware implementation registers */
5463 /* XXX : not implemented */
5464 spr_register(env, SPR_HID0, "HID0",
5465 SPR_NOACCESS, SPR_NOACCESS,
5466 &spr_read_generic, &spr_write_generic,
5467 0x00000000);
5468 /* XXX : not implemented */
5469 spr_register(env, SPR_HID1, "HID1",
5470 SPR_NOACCESS, SPR_NOACCESS,
5471 &spr_read_generic, &spr_write_generic,
5472 0x00000000);
5473 /* Memory management */
5474 gen_low_BATs(env);
5475 gen_6xx_7xx_soft_tlb(env, 64, 2);
5476 init_excp_603(env);
5477 env->dcache_line_size = 32;
5478 env->icache_line_size = 32;
5479 /* Allocate hardware IRQ controller */
5480 ppc6xx_irq_init(ppc_env_get_cpu(env));
5483 POWERPC_FAMILY(603E)(ObjectClass *oc, void *data)
5485 DeviceClass *dc = DEVICE_CLASS(oc);
5486 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5488 dc->desc = "PowerPC 603e";
5489 pcc->init_proc = init_proc_603E;
5490 pcc->check_pow = check_pow_hid0;
5491 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5492 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5493 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5494 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5495 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5496 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
5497 PPC_SEGMENT | PPC_EXTERN;
5498 pcc->msr_mask = (1ull << MSR_POW) |
5499 (1ull << MSR_TGPR) |
5500 (1ull << MSR_ILE) |
5501 (1ull << MSR_EE) |
5502 (1ull << MSR_PR) |
5503 (1ull << MSR_FP) |
5504 (1ull << MSR_ME) |
5505 (1ull << MSR_FE0) |
5506 (1ull << MSR_SE) |
5507 (1ull << MSR_DE) |
5508 (1ull << MSR_FE1) |
5509 (1ull << MSR_EP) |
5510 (1ull << MSR_IR) |
5511 (1ull << MSR_DR) |
5512 (1ull << MSR_RI) |
5513 (1ull << MSR_LE);
5514 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
5515 pcc->excp_model = POWERPC_EXCP_603E;
5516 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5517 pcc->bfd_mach = bfd_mach_ppc_ec603e;
5518 pcc->flags = POWERPC_FLAG_TGPR | POWERPC_FLAG_SE |
5519 POWERPC_FLAG_BE | POWERPC_FLAG_BUS_CLK;
5522 static void init_proc_604(CPUPPCState *env)
5524 gen_spr_ne_601(env);
5525 gen_spr_sdr1(env);
5526 gen_spr_604(env);
5527 /* Time base */
5528 gen_tbl(env);
5529 /* Hardware implementation registers */
5530 /* XXX : not implemented */
5531 spr_register(env, SPR_HID0, "HID0",
5532 SPR_NOACCESS, SPR_NOACCESS,
5533 &spr_read_generic, &spr_write_generic,
5534 0x00000000);
5535 /* Memory management */
5536 gen_low_BATs(env);
5537 init_excp_604(env);
5538 env->dcache_line_size = 32;
5539 env->icache_line_size = 32;
5540 /* Allocate hardware IRQ controller */
5541 ppc6xx_irq_init(ppc_env_get_cpu(env));
5544 POWERPC_FAMILY(604)(ObjectClass *oc, void *data)
5546 DeviceClass *dc = DEVICE_CLASS(oc);
5547 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5549 dc->desc = "PowerPC 604";
5550 pcc->init_proc = init_proc_604;
5551 pcc->check_pow = check_pow_nocheck;
5552 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5553 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5554 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5555 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5556 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5557 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5558 PPC_SEGMENT | PPC_EXTERN;
5559 pcc->msr_mask = (1ull << MSR_POW) |
5560 (1ull << MSR_ILE) |
5561 (1ull << MSR_EE) |
5562 (1ull << MSR_PR) |
5563 (1ull << MSR_FP) |
5564 (1ull << MSR_ME) |
5565 (1ull << MSR_FE0) |
5566 (1ull << MSR_SE) |
5567 (1ull << MSR_DE) |
5568 (1ull << MSR_FE1) |
5569 (1ull << MSR_EP) |
5570 (1ull << MSR_IR) |
5571 (1ull << MSR_DR) |
5572 (1ull << MSR_PMM) |
5573 (1ull << MSR_RI) |
5574 (1ull << MSR_LE);
5575 pcc->mmu_model = POWERPC_MMU_32B;
5576 #if defined(CONFIG_SOFTMMU)
5577 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5578 #endif
5579 pcc->excp_model = POWERPC_EXCP_604;
5580 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5581 pcc->bfd_mach = bfd_mach_ppc_604;
5582 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
5583 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5586 static void init_proc_604E(CPUPPCState *env)
5588 gen_spr_ne_601(env);
5589 gen_spr_sdr1(env);
5590 gen_spr_604(env);
5591 /* XXX : not implemented */
5592 spr_register(env, SPR_7XX_MMCR1, "MMCR1",
5593 SPR_NOACCESS, SPR_NOACCESS,
5594 &spr_read_generic, &spr_write_generic,
5595 0x00000000);
5596 /* XXX : not implemented */
5597 spr_register(env, SPR_7XX_PMC3, "PMC3",
5598 SPR_NOACCESS, SPR_NOACCESS,
5599 &spr_read_generic, &spr_write_generic,
5600 0x00000000);
5601 /* XXX : not implemented */
5602 spr_register(env, SPR_7XX_PMC4, "PMC4",
5603 SPR_NOACCESS, SPR_NOACCESS,
5604 &spr_read_generic, &spr_write_generic,
5605 0x00000000);
5606 /* Time base */
5607 gen_tbl(env);
5608 /* Hardware implementation registers */
5609 /* XXX : not implemented */
5610 spr_register(env, SPR_HID0, "HID0",
5611 SPR_NOACCESS, SPR_NOACCESS,
5612 &spr_read_generic, &spr_write_generic,
5613 0x00000000);
5614 /* XXX : not implemented */
5615 spr_register(env, SPR_HID1, "HID1",
5616 SPR_NOACCESS, SPR_NOACCESS,
5617 &spr_read_generic, &spr_write_generic,
5618 0x00000000);
5619 /* Memory management */
5620 gen_low_BATs(env);
5621 init_excp_604(env);
5622 env->dcache_line_size = 32;
5623 env->icache_line_size = 32;
5624 /* Allocate hardware IRQ controller */
5625 ppc6xx_irq_init(ppc_env_get_cpu(env));
5628 POWERPC_FAMILY(604E)(ObjectClass *oc, void *data)
5630 DeviceClass *dc = DEVICE_CLASS(oc);
5631 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5633 dc->desc = "PowerPC 604E";
5634 pcc->init_proc = init_proc_604E;
5635 pcc->check_pow = check_pow_nocheck;
5636 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5637 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5638 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5639 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5640 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5641 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5642 PPC_SEGMENT | PPC_EXTERN;
5643 pcc->msr_mask = (1ull << MSR_POW) |
5644 (1ull << MSR_ILE) |
5645 (1ull << MSR_EE) |
5646 (1ull << MSR_PR) |
5647 (1ull << MSR_FP) |
5648 (1ull << MSR_ME) |
5649 (1ull << MSR_FE0) |
5650 (1ull << MSR_SE) |
5651 (1ull << MSR_DE) |
5652 (1ull << MSR_FE1) |
5653 (1ull << MSR_EP) |
5654 (1ull << MSR_IR) |
5655 (1ull << MSR_DR) |
5656 (1ull << MSR_PMM) |
5657 (1ull << MSR_RI) |
5658 (1ull << MSR_LE);
5659 pcc->mmu_model = POWERPC_MMU_32B;
5660 #if defined(CONFIG_SOFTMMU)
5661 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5662 #endif
5663 pcc->excp_model = POWERPC_EXCP_604;
5664 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5665 pcc->bfd_mach = bfd_mach_ppc_604;
5666 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
5667 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5670 static void init_proc_740(CPUPPCState *env)
5672 gen_spr_ne_601(env);
5673 gen_spr_sdr1(env);
5674 gen_spr_7xx(env);
5675 /* Time base */
5676 gen_tbl(env);
5677 /* Thermal management */
5678 gen_spr_thrm(env);
5679 /* Hardware implementation registers */
5680 /* XXX : not implemented */
5681 spr_register(env, SPR_HID0, "HID0",
5682 SPR_NOACCESS, SPR_NOACCESS,
5683 &spr_read_generic, &spr_write_generic,
5684 0x00000000);
5685 /* XXX : not implemented */
5686 spr_register(env, SPR_HID1, "HID1",
5687 SPR_NOACCESS, SPR_NOACCESS,
5688 &spr_read_generic, &spr_write_generic,
5689 0x00000000);
5690 /* Memory management */
5691 gen_low_BATs(env);
5692 init_excp_7x0(env);
5693 env->dcache_line_size = 32;
5694 env->icache_line_size = 32;
5695 /* Allocate hardware IRQ controller */
5696 ppc6xx_irq_init(ppc_env_get_cpu(env));
5699 POWERPC_FAMILY(740)(ObjectClass *oc, void *data)
5701 DeviceClass *dc = DEVICE_CLASS(oc);
5702 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5704 dc->desc = "PowerPC 740";
5705 pcc->init_proc = init_proc_740;
5706 pcc->check_pow = check_pow_hid0;
5707 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5708 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5709 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5710 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5711 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5712 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5713 PPC_SEGMENT | PPC_EXTERN;
5714 pcc->msr_mask = (1ull << MSR_POW) |
5715 (1ull << MSR_ILE) |
5716 (1ull << MSR_EE) |
5717 (1ull << MSR_PR) |
5718 (1ull << MSR_FP) |
5719 (1ull << MSR_ME) |
5720 (1ull << MSR_FE0) |
5721 (1ull << MSR_SE) |
5722 (1ull << MSR_DE) |
5723 (1ull << MSR_FE1) |
5724 (1ull << MSR_EP) |
5725 (1ull << MSR_IR) |
5726 (1ull << MSR_DR) |
5727 (1ull << MSR_PMM) |
5728 (1ull << MSR_RI) |
5729 (1ull << MSR_LE);
5730 pcc->mmu_model = POWERPC_MMU_32B;
5731 #if defined(CONFIG_SOFTMMU)
5732 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5733 #endif
5734 pcc->excp_model = POWERPC_EXCP_7x0;
5735 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5736 pcc->bfd_mach = bfd_mach_ppc_750;
5737 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
5738 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5741 static void init_proc_750(CPUPPCState *env)
5743 gen_spr_ne_601(env);
5744 gen_spr_sdr1(env);
5745 gen_spr_7xx(env);
5746 /* XXX : not implemented */
5747 spr_register(env, SPR_L2CR, "L2CR",
5748 SPR_NOACCESS, SPR_NOACCESS,
5749 &spr_read_generic, spr_access_nop,
5750 0x00000000);
5751 /* Time base */
5752 gen_tbl(env);
5753 /* Thermal management */
5754 gen_spr_thrm(env);
5755 /* Hardware implementation registers */
5756 /* XXX : not implemented */
5757 spr_register(env, SPR_HID0, "HID0",
5758 SPR_NOACCESS, SPR_NOACCESS,
5759 &spr_read_generic, &spr_write_generic,
5760 0x00000000);
5761 /* XXX : not implemented */
5762 spr_register(env, SPR_HID1, "HID1",
5763 SPR_NOACCESS, SPR_NOACCESS,
5764 &spr_read_generic, &spr_write_generic,
5765 0x00000000);
5766 /* Memory management */
5767 gen_low_BATs(env);
5768 /* XXX: high BATs are also present but are known to be bugged on
5769 * die version 1.x
5771 init_excp_7x0(env);
5772 env->dcache_line_size = 32;
5773 env->icache_line_size = 32;
5774 /* Allocate hardware IRQ controller */
5775 ppc6xx_irq_init(ppc_env_get_cpu(env));
5778 POWERPC_FAMILY(750)(ObjectClass *oc, void *data)
5780 DeviceClass *dc = DEVICE_CLASS(oc);
5781 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5783 dc->desc = "PowerPC 750";
5784 pcc->init_proc = init_proc_750;
5785 pcc->check_pow = check_pow_hid0;
5786 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5787 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5788 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5789 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5790 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5791 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5792 PPC_SEGMENT | PPC_EXTERN;
5793 pcc->msr_mask = (1ull << MSR_POW) |
5794 (1ull << MSR_ILE) |
5795 (1ull << MSR_EE) |
5796 (1ull << MSR_PR) |
5797 (1ull << MSR_FP) |
5798 (1ull << MSR_ME) |
5799 (1ull << MSR_FE0) |
5800 (1ull << MSR_SE) |
5801 (1ull << MSR_DE) |
5802 (1ull << MSR_FE1) |
5803 (1ull << MSR_EP) |
5804 (1ull << MSR_IR) |
5805 (1ull << MSR_DR) |
5806 (1ull << MSR_PMM) |
5807 (1ull << MSR_RI) |
5808 (1ull << MSR_LE);
5809 pcc->mmu_model = POWERPC_MMU_32B;
5810 #if defined(CONFIG_SOFTMMU)
5811 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
5812 #endif
5813 pcc->excp_model = POWERPC_EXCP_7x0;
5814 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
5815 pcc->bfd_mach = bfd_mach_ppc_750;
5816 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
5817 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
5820 static void init_proc_750cl(CPUPPCState *env)
5822 gen_spr_ne_601(env);
5823 gen_spr_sdr1(env);
5824 gen_spr_7xx(env);
5825 /* XXX : not implemented */
5826 spr_register(env, SPR_L2CR, "L2CR",
5827 SPR_NOACCESS, SPR_NOACCESS,
5828 &spr_read_generic, spr_access_nop,
5829 0x00000000);
5830 /* Time base */
5831 gen_tbl(env);
5832 /* Thermal management */
5833 /* Those registers are fake on 750CL */
5834 spr_register(env, SPR_THRM1, "THRM1",
5835 SPR_NOACCESS, SPR_NOACCESS,
5836 &spr_read_generic, &spr_write_generic,
5837 0x00000000);
5838 spr_register(env, SPR_THRM2, "THRM2",
5839 SPR_NOACCESS, SPR_NOACCESS,
5840 &spr_read_generic, &spr_write_generic,
5841 0x00000000);
5842 spr_register(env, SPR_THRM3, "THRM3",
5843 SPR_NOACCESS, SPR_NOACCESS,
5844 &spr_read_generic, &spr_write_generic,
5845 0x00000000);
5846 /* XXX: not implemented */
5847 spr_register(env, SPR_750_TDCL, "TDCL",
5848 SPR_NOACCESS, SPR_NOACCESS,
5849 &spr_read_generic, &spr_write_generic,
5850 0x00000000);
5851 spr_register(env, SPR_750_TDCH, "TDCH",
5852 SPR_NOACCESS, SPR_NOACCESS,
5853 &spr_read_generic, &spr_write_generic,
5854 0x00000000);
5855 /* DMA */
5856 /* XXX : not implemented */
5857 spr_register(env, SPR_750_WPAR, "WPAR",
5858 SPR_NOACCESS, SPR_NOACCESS,
5859 &spr_read_generic, &spr_write_generic,
5860 0x00000000);
5861 spr_register(env, SPR_750_DMAL, "DMAL",
5862 SPR_NOACCESS, SPR_NOACCESS,
5863 &spr_read_generic, &spr_write_generic,
5864 0x00000000);
5865 spr_register(env, SPR_750_DMAU, "DMAU",
5866 SPR_NOACCESS, SPR_NOACCESS,
5867 &spr_read_generic, &spr_write_generic,
5868 0x00000000);
5869 /* Hardware implementation registers */
5870 /* XXX : not implemented */
5871 spr_register(env, SPR_HID0, "HID0",
5872 SPR_NOACCESS, SPR_NOACCESS,
5873 &spr_read_generic, &spr_write_generic,
5874 0x00000000);
5875 /* XXX : not implemented */
5876 spr_register(env, SPR_HID1, "HID1",
5877 SPR_NOACCESS, SPR_NOACCESS,
5878 &spr_read_generic, &spr_write_generic,
5879 0x00000000);
5880 /* XXX : not implemented */
5881 spr_register(env, SPR_750CL_HID2, "HID2",
5882 SPR_NOACCESS, SPR_NOACCESS,
5883 &spr_read_generic, &spr_write_generic,
5884 0x00000000);
5885 /* XXX : not implemented */
5886 spr_register(env, SPR_750CL_HID4, "HID4",
5887 SPR_NOACCESS, SPR_NOACCESS,
5888 &spr_read_generic, &spr_write_generic,
5889 0x00000000);
5890 /* Quantization registers */
5891 /* XXX : not implemented */
5892 spr_register(env, SPR_750_GQR0, "GQR0",
5893 SPR_NOACCESS, SPR_NOACCESS,
5894 &spr_read_generic, &spr_write_generic,
5895 0x00000000);
5896 /* XXX : not implemented */
5897 spr_register(env, SPR_750_GQR1, "GQR1",
5898 SPR_NOACCESS, SPR_NOACCESS,
5899 &spr_read_generic, &spr_write_generic,
5900 0x00000000);
5901 /* XXX : not implemented */
5902 spr_register(env, SPR_750_GQR2, "GQR2",
5903 SPR_NOACCESS, SPR_NOACCESS,
5904 &spr_read_generic, &spr_write_generic,
5905 0x00000000);
5906 /* XXX : not implemented */
5907 spr_register(env, SPR_750_GQR3, "GQR3",
5908 SPR_NOACCESS, SPR_NOACCESS,
5909 &spr_read_generic, &spr_write_generic,
5910 0x00000000);
5911 /* XXX : not implemented */
5912 spr_register(env, SPR_750_GQR4, "GQR4",
5913 SPR_NOACCESS, SPR_NOACCESS,
5914 &spr_read_generic, &spr_write_generic,
5915 0x00000000);
5916 /* XXX : not implemented */
5917 spr_register(env, SPR_750_GQR5, "GQR5",
5918 SPR_NOACCESS, SPR_NOACCESS,
5919 &spr_read_generic, &spr_write_generic,
5920 0x00000000);
5921 /* XXX : not implemented */
5922 spr_register(env, SPR_750_GQR6, "GQR6",
5923 SPR_NOACCESS, SPR_NOACCESS,
5924 &spr_read_generic, &spr_write_generic,
5925 0x00000000);
5926 /* XXX : not implemented */
5927 spr_register(env, SPR_750_GQR7, "GQR7",
5928 SPR_NOACCESS, SPR_NOACCESS,
5929 &spr_read_generic, &spr_write_generic,
5930 0x00000000);
5931 /* Memory management */
5932 gen_low_BATs(env);
5933 /* PowerPC 750cl has 8 DBATs and 8 IBATs */
5934 gen_high_BATs(env);
5935 init_excp_750cl(env);
5936 env->dcache_line_size = 32;
5937 env->icache_line_size = 32;
5938 /* Allocate hardware IRQ controller */
5939 ppc6xx_irq_init(ppc_env_get_cpu(env));
5942 POWERPC_FAMILY(750cl)(ObjectClass *oc, void *data)
5944 DeviceClass *dc = DEVICE_CLASS(oc);
5945 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
5947 dc->desc = "PowerPC 750 CL";
5948 pcc->init_proc = init_proc_750cl;
5949 pcc->check_pow = check_pow_hid0;
5950 /* XXX: not implemented:
5951 * cache lock instructions:
5952 * dcbz_l
5953 * floating point paired instructions
5954 * psq_lux
5955 * psq_lx
5956 * psq_stux
5957 * psq_stx
5958 * ps_abs
5959 * ps_add
5960 * ps_cmpo0
5961 * ps_cmpo1
5962 * ps_cmpu0
5963 * ps_cmpu1
5964 * ps_div
5965 * ps_madd
5966 * ps_madds0
5967 * ps_madds1
5968 * ps_merge00
5969 * ps_merge01
5970 * ps_merge10
5971 * ps_merge11
5972 * ps_mr
5973 * ps_msub
5974 * ps_mul
5975 * ps_muls0
5976 * ps_muls1
5977 * ps_nabs
5978 * ps_neg
5979 * ps_nmadd
5980 * ps_nmsub
5981 * ps_res
5982 * ps_rsqrte
5983 * ps_sel
5984 * ps_sub
5985 * ps_sum0
5986 * ps_sum1
5988 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
5989 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
5990 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
5991 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
5992 PPC_MEM_SYNC | PPC_MEM_EIEIO |
5993 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
5994 PPC_SEGMENT | PPC_EXTERN;
5995 pcc->msr_mask = (1ull << MSR_POW) |
5996 (1ull << MSR_ILE) |
5997 (1ull << MSR_EE) |
5998 (1ull << MSR_PR) |
5999 (1ull << MSR_FP) |
6000 (1ull << MSR_ME) |
6001 (1ull << MSR_FE0) |
6002 (1ull << MSR_SE) |
6003 (1ull << MSR_DE) |
6004 (1ull << MSR_FE1) |
6005 (1ull << MSR_EP) |
6006 (1ull << MSR_IR) |
6007 (1ull << MSR_DR) |
6008 (1ull << MSR_PMM) |
6009 (1ull << MSR_RI) |
6010 (1ull << MSR_LE);
6011 pcc->mmu_model = POWERPC_MMU_32B;
6012 #if defined(CONFIG_SOFTMMU)
6013 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
6014 #endif
6015 pcc->excp_model = POWERPC_EXCP_7x0;
6016 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6017 pcc->bfd_mach = bfd_mach_ppc_750;
6018 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
6019 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
6022 static void init_proc_750cx(CPUPPCState *env)
6024 gen_spr_ne_601(env);
6025 gen_spr_sdr1(env);
6026 gen_spr_7xx(env);
6027 /* XXX : not implemented */
6028 spr_register(env, SPR_L2CR, "L2CR",
6029 SPR_NOACCESS, SPR_NOACCESS,
6030 &spr_read_generic, spr_access_nop,
6031 0x00000000);
6032 /* Time base */
6033 gen_tbl(env);
6034 /* Thermal management */
6035 gen_spr_thrm(env);
6036 /* This register is not implemented but is present for compatibility */
6037 spr_register(env, SPR_SDA, "SDA",
6038 SPR_NOACCESS, SPR_NOACCESS,
6039 &spr_read_generic, &spr_write_generic,
6040 0x00000000);
6041 /* Hardware implementation registers */
6042 /* XXX : not implemented */
6043 spr_register(env, SPR_HID0, "HID0",
6044 SPR_NOACCESS, SPR_NOACCESS,
6045 &spr_read_generic, &spr_write_generic,
6046 0x00000000);
6047 /* XXX : not implemented */
6048 spr_register(env, SPR_HID1, "HID1",
6049 SPR_NOACCESS, SPR_NOACCESS,
6050 &spr_read_generic, &spr_write_generic,
6051 0x00000000);
6052 /* Memory management */
6053 gen_low_BATs(env);
6054 /* PowerPC 750cx has 8 DBATs and 8 IBATs */
6055 gen_high_BATs(env);
6056 init_excp_750cx(env);
6057 env->dcache_line_size = 32;
6058 env->icache_line_size = 32;
6059 /* Allocate hardware IRQ controller */
6060 ppc6xx_irq_init(ppc_env_get_cpu(env));
6063 POWERPC_FAMILY(750cx)(ObjectClass *oc, void *data)
6065 DeviceClass *dc = DEVICE_CLASS(oc);
6066 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6068 dc->desc = "PowerPC 750CX";
6069 pcc->init_proc = init_proc_750cx;
6070 pcc->check_pow = check_pow_hid0;
6071 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6072 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6073 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
6074 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
6075 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6076 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6077 PPC_SEGMENT | PPC_EXTERN;
6078 pcc->msr_mask = (1ull << MSR_POW) |
6079 (1ull << MSR_ILE) |
6080 (1ull << MSR_EE) |
6081 (1ull << MSR_PR) |
6082 (1ull << MSR_FP) |
6083 (1ull << MSR_ME) |
6084 (1ull << MSR_FE0) |
6085 (1ull << MSR_SE) |
6086 (1ull << MSR_DE) |
6087 (1ull << MSR_FE1) |
6088 (1ull << MSR_EP) |
6089 (1ull << MSR_IR) |
6090 (1ull << MSR_DR) |
6091 (1ull << MSR_PMM) |
6092 (1ull << MSR_RI) |
6093 (1ull << MSR_LE);
6094 pcc->mmu_model = POWERPC_MMU_32B;
6095 #if defined(CONFIG_SOFTMMU)
6096 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
6097 #endif
6098 pcc->excp_model = POWERPC_EXCP_7x0;
6099 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6100 pcc->bfd_mach = bfd_mach_ppc_750;
6101 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
6102 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
6105 static void init_proc_750fx(CPUPPCState *env)
6107 gen_spr_ne_601(env);
6108 gen_spr_sdr1(env);
6109 gen_spr_7xx(env);
6110 /* XXX : not implemented */
6111 spr_register(env, SPR_L2CR, "L2CR",
6112 SPR_NOACCESS, SPR_NOACCESS,
6113 &spr_read_generic, spr_access_nop,
6114 0x00000000);
6115 /* Time base */
6116 gen_tbl(env);
6117 /* Thermal management */
6118 gen_spr_thrm(env);
6119 /* XXX : not implemented */
6120 spr_register(env, SPR_750_THRM4, "THRM4",
6121 SPR_NOACCESS, SPR_NOACCESS,
6122 &spr_read_generic, &spr_write_generic,
6123 0x00000000);
6124 /* Hardware implementation registers */
6125 /* XXX : not implemented */
6126 spr_register(env, SPR_HID0, "HID0",
6127 SPR_NOACCESS, SPR_NOACCESS,
6128 &spr_read_generic, &spr_write_generic,
6129 0x00000000);
6130 /* XXX : not implemented */
6131 spr_register(env, SPR_HID1, "HID1",
6132 SPR_NOACCESS, SPR_NOACCESS,
6133 &spr_read_generic, &spr_write_generic,
6134 0x00000000);
6135 /* XXX : not implemented */
6136 spr_register(env, SPR_750FX_HID2, "HID2",
6137 SPR_NOACCESS, SPR_NOACCESS,
6138 &spr_read_generic, &spr_write_generic,
6139 0x00000000);
6140 /* Memory management */
6141 gen_low_BATs(env);
6142 /* PowerPC 750fx & 750gx has 8 DBATs and 8 IBATs */
6143 gen_high_BATs(env);
6144 init_excp_7x0(env);
6145 env->dcache_line_size = 32;
6146 env->icache_line_size = 32;
6147 /* Allocate hardware IRQ controller */
6148 ppc6xx_irq_init(ppc_env_get_cpu(env));
6151 POWERPC_FAMILY(750fx)(ObjectClass *oc, void *data)
6153 DeviceClass *dc = DEVICE_CLASS(oc);
6154 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6156 dc->desc = "PowerPC 750FX";
6157 pcc->init_proc = init_proc_750fx;
6158 pcc->check_pow = check_pow_hid0;
6159 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6160 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6161 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
6162 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
6163 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6164 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6165 PPC_SEGMENT | PPC_EXTERN;
6166 pcc->msr_mask = (1ull << MSR_POW) |
6167 (1ull << MSR_ILE) |
6168 (1ull << MSR_EE) |
6169 (1ull << MSR_PR) |
6170 (1ull << MSR_FP) |
6171 (1ull << MSR_ME) |
6172 (1ull << MSR_FE0) |
6173 (1ull << MSR_SE) |
6174 (1ull << MSR_DE) |
6175 (1ull << MSR_FE1) |
6176 (1ull << MSR_EP) |
6177 (1ull << MSR_IR) |
6178 (1ull << MSR_DR) |
6179 (1ull << MSR_PMM) |
6180 (1ull << MSR_RI) |
6181 (1ull << MSR_LE);
6182 pcc->mmu_model = POWERPC_MMU_32B;
6183 #if defined(CONFIG_SOFTMMU)
6184 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
6185 #endif
6186 pcc->excp_model = POWERPC_EXCP_7x0;
6187 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6188 pcc->bfd_mach = bfd_mach_ppc_750;
6189 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
6190 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
6193 static void init_proc_750gx(CPUPPCState *env)
6195 gen_spr_ne_601(env);
6196 gen_spr_sdr1(env);
6197 gen_spr_7xx(env);
6198 /* XXX : not implemented (XXX: different from 750fx) */
6199 spr_register(env, SPR_L2CR, "L2CR",
6200 SPR_NOACCESS, SPR_NOACCESS,
6201 &spr_read_generic, spr_access_nop,
6202 0x00000000);
6203 /* Time base */
6204 gen_tbl(env);
6205 /* Thermal management */
6206 gen_spr_thrm(env);
6207 /* XXX : not implemented */
6208 spr_register(env, SPR_750_THRM4, "THRM4",
6209 SPR_NOACCESS, SPR_NOACCESS,
6210 &spr_read_generic, &spr_write_generic,
6211 0x00000000);
6212 /* Hardware implementation registers */
6213 /* XXX : not implemented (XXX: different from 750fx) */
6214 spr_register(env, SPR_HID0, "HID0",
6215 SPR_NOACCESS, SPR_NOACCESS,
6216 &spr_read_generic, &spr_write_generic,
6217 0x00000000);
6218 /* XXX : not implemented */
6219 spr_register(env, SPR_HID1, "HID1",
6220 SPR_NOACCESS, SPR_NOACCESS,
6221 &spr_read_generic, &spr_write_generic,
6222 0x00000000);
6223 /* XXX : not implemented (XXX: different from 750fx) */
6224 spr_register(env, SPR_750FX_HID2, "HID2",
6225 SPR_NOACCESS, SPR_NOACCESS,
6226 &spr_read_generic, &spr_write_generic,
6227 0x00000000);
6228 /* Memory management */
6229 gen_low_BATs(env);
6230 /* PowerPC 750fx & 750gx has 8 DBATs and 8 IBATs */
6231 gen_high_BATs(env);
6232 init_excp_7x0(env);
6233 env->dcache_line_size = 32;
6234 env->icache_line_size = 32;
6235 /* Allocate hardware IRQ controller */
6236 ppc6xx_irq_init(ppc_env_get_cpu(env));
6239 POWERPC_FAMILY(750gx)(ObjectClass *oc, void *data)
6241 DeviceClass *dc = DEVICE_CLASS(oc);
6242 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6244 dc->desc = "PowerPC 750GX";
6245 pcc->init_proc = init_proc_750gx;
6246 pcc->check_pow = check_pow_hid0;
6247 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6248 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6249 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
6250 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
6251 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6252 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6253 PPC_SEGMENT | PPC_EXTERN;
6254 pcc->msr_mask = (1ull << MSR_POW) |
6255 (1ull << MSR_ILE) |
6256 (1ull << MSR_EE) |
6257 (1ull << MSR_PR) |
6258 (1ull << MSR_FP) |
6259 (1ull << MSR_ME) |
6260 (1ull << MSR_FE0) |
6261 (1ull << MSR_SE) |
6262 (1ull << MSR_DE) |
6263 (1ull << MSR_FE1) |
6264 (1ull << MSR_EP) |
6265 (1ull << MSR_IR) |
6266 (1ull << MSR_DR) |
6267 (1ull << MSR_PMM) |
6268 (1ull << MSR_RI) |
6269 (1ull << MSR_LE);
6270 pcc->mmu_model = POWERPC_MMU_32B;
6271 #if defined(CONFIG_SOFTMMU)
6272 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
6273 #endif
6274 pcc->excp_model = POWERPC_EXCP_7x0;
6275 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6276 pcc->bfd_mach = bfd_mach_ppc_750;
6277 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
6278 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
6281 static void init_proc_745(CPUPPCState *env)
6283 gen_spr_ne_601(env);
6284 gen_spr_sdr1(env);
6285 gen_spr_7xx(env);
6286 gen_spr_G2_755(env);
6287 /* Time base */
6288 gen_tbl(env);
6289 /* Thermal management */
6290 gen_spr_thrm(env);
6291 /* Hardware implementation registers */
6292 /* XXX : not implemented */
6293 spr_register(env, SPR_HID0, "HID0",
6294 SPR_NOACCESS, SPR_NOACCESS,
6295 &spr_read_generic, &spr_write_generic,
6296 0x00000000);
6297 /* XXX : not implemented */
6298 spr_register(env, SPR_HID1, "HID1",
6299 SPR_NOACCESS, SPR_NOACCESS,
6300 &spr_read_generic, &spr_write_generic,
6301 0x00000000);
6302 /* XXX : not implemented */
6303 spr_register(env, SPR_HID2, "HID2",
6304 SPR_NOACCESS, SPR_NOACCESS,
6305 &spr_read_generic, &spr_write_generic,
6306 0x00000000);
6307 /* Memory management */
6308 gen_low_BATs(env);
6309 gen_high_BATs(env);
6310 gen_6xx_7xx_soft_tlb(env, 64, 2);
6311 init_excp_7x5(env);
6312 env->dcache_line_size = 32;
6313 env->icache_line_size = 32;
6314 /* Allocate hardware IRQ controller */
6315 ppc6xx_irq_init(ppc_env_get_cpu(env));
6318 POWERPC_FAMILY(745)(ObjectClass *oc, void *data)
6320 DeviceClass *dc = DEVICE_CLASS(oc);
6321 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6323 dc->desc = "PowerPC 745";
6324 pcc->init_proc = init_proc_745;
6325 pcc->check_pow = check_pow_hid0;
6326 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6327 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6328 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
6329 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
6330 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6331 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
6332 PPC_SEGMENT | PPC_EXTERN;
6333 pcc->msr_mask = (1ull << MSR_POW) |
6334 (1ull << MSR_ILE) |
6335 (1ull << MSR_EE) |
6336 (1ull << MSR_PR) |
6337 (1ull << MSR_FP) |
6338 (1ull << MSR_ME) |
6339 (1ull << MSR_FE0) |
6340 (1ull << MSR_SE) |
6341 (1ull << MSR_DE) |
6342 (1ull << MSR_FE1) |
6343 (1ull << MSR_EP) |
6344 (1ull << MSR_IR) |
6345 (1ull << MSR_DR) |
6346 (1ull << MSR_PMM) |
6347 (1ull << MSR_RI) |
6348 (1ull << MSR_LE);
6349 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
6350 pcc->excp_model = POWERPC_EXCP_7x5;
6351 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6352 pcc->bfd_mach = bfd_mach_ppc_750;
6353 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
6354 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
6357 static void init_proc_755(CPUPPCState *env)
6359 gen_spr_ne_601(env);
6360 gen_spr_sdr1(env);
6361 gen_spr_7xx(env);
6362 gen_spr_G2_755(env);
6363 /* Time base */
6364 gen_tbl(env);
6365 /* L2 cache control */
6366 /* XXX : not implemented */
6367 spr_register(env, SPR_L2CR, "L2CR",
6368 SPR_NOACCESS, SPR_NOACCESS,
6369 &spr_read_generic, spr_access_nop,
6370 0x00000000);
6371 /* XXX : not implemented */
6372 spr_register(env, SPR_L2PMCR, "L2PMCR",
6373 SPR_NOACCESS, SPR_NOACCESS,
6374 &spr_read_generic, &spr_write_generic,
6375 0x00000000);
6376 /* Thermal management */
6377 gen_spr_thrm(env);
6378 /* Hardware implementation registers */
6379 /* XXX : not implemented */
6380 spr_register(env, SPR_HID0, "HID0",
6381 SPR_NOACCESS, SPR_NOACCESS,
6382 &spr_read_generic, &spr_write_generic,
6383 0x00000000);
6384 /* XXX : not implemented */
6385 spr_register(env, SPR_HID1, "HID1",
6386 SPR_NOACCESS, SPR_NOACCESS,
6387 &spr_read_generic, &spr_write_generic,
6388 0x00000000);
6389 /* XXX : not implemented */
6390 spr_register(env, SPR_HID2, "HID2",
6391 SPR_NOACCESS, SPR_NOACCESS,
6392 &spr_read_generic, &spr_write_generic,
6393 0x00000000);
6394 /* Memory management */
6395 gen_low_BATs(env);
6396 gen_high_BATs(env);
6397 gen_6xx_7xx_soft_tlb(env, 64, 2);
6398 init_excp_7x5(env);
6399 env->dcache_line_size = 32;
6400 env->icache_line_size = 32;
6401 /* Allocate hardware IRQ controller */
6402 ppc6xx_irq_init(ppc_env_get_cpu(env));
6405 POWERPC_FAMILY(755)(ObjectClass *oc, void *data)
6407 DeviceClass *dc = DEVICE_CLASS(oc);
6408 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6410 dc->desc = "PowerPC 755";
6411 pcc->init_proc = init_proc_755;
6412 pcc->check_pow = check_pow_hid0;
6413 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6414 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6415 PPC_FLOAT_FRSQRTE | PPC_FLOAT_STFIWX |
6416 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
6417 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6418 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC | PPC_6xx_TLB |
6419 PPC_SEGMENT | PPC_EXTERN;
6420 pcc->msr_mask = (1ull << MSR_POW) |
6421 (1ull << MSR_ILE) |
6422 (1ull << MSR_EE) |
6423 (1ull << MSR_PR) |
6424 (1ull << MSR_FP) |
6425 (1ull << MSR_ME) |
6426 (1ull << MSR_FE0) |
6427 (1ull << MSR_SE) |
6428 (1ull << MSR_DE) |
6429 (1ull << MSR_FE1) |
6430 (1ull << MSR_EP) |
6431 (1ull << MSR_IR) |
6432 (1ull << MSR_DR) |
6433 (1ull << MSR_PMM) |
6434 (1ull << MSR_RI) |
6435 (1ull << MSR_LE);
6436 pcc->mmu_model = POWERPC_MMU_SOFT_6xx;
6437 pcc->excp_model = POWERPC_EXCP_7x5;
6438 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6439 pcc->bfd_mach = bfd_mach_ppc_750;
6440 pcc->flags = POWERPC_FLAG_SE | POWERPC_FLAG_BE |
6441 POWERPC_FLAG_PMM | POWERPC_FLAG_BUS_CLK;
6444 static void init_proc_7400(CPUPPCState *env)
6446 gen_spr_ne_601(env);
6447 gen_spr_sdr1(env);
6448 gen_spr_7xx(env);
6449 /* Time base */
6450 gen_tbl(env);
6451 /* 74xx specific SPR */
6452 gen_spr_74xx(env);
6453 /* XXX : not implemented */
6454 spr_register(env, SPR_UBAMR, "UBAMR",
6455 &spr_read_ureg, SPR_NOACCESS,
6456 &spr_read_ureg, SPR_NOACCESS,
6457 0x00000000);
6458 /* XXX: this seems not implemented on all revisions. */
6459 /* XXX : not implemented */
6460 spr_register(env, SPR_MSSCR1, "MSSCR1",
6461 SPR_NOACCESS, SPR_NOACCESS,
6462 &spr_read_generic, &spr_write_generic,
6463 0x00000000);
6464 /* Thermal management */
6465 gen_spr_thrm(env);
6466 /* Memory management */
6467 gen_low_BATs(env);
6468 init_excp_7400(env);
6469 env->dcache_line_size = 32;
6470 env->icache_line_size = 32;
6471 /* Allocate hardware IRQ controller */
6472 ppc6xx_irq_init(ppc_env_get_cpu(env));
6475 POWERPC_FAMILY(7400)(ObjectClass *oc, void *data)
6477 DeviceClass *dc = DEVICE_CLASS(oc);
6478 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6480 dc->desc = "PowerPC 7400 (aka G4)";
6481 pcc->init_proc = init_proc_7400;
6482 pcc->check_pow = check_pow_hid0;
6483 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6484 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6485 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6486 PPC_FLOAT_STFIWX |
6487 PPC_CACHE | PPC_CACHE_ICBI |
6488 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6489 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6490 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6491 PPC_MEM_TLBIA |
6492 PPC_SEGMENT | PPC_EXTERN |
6493 PPC_ALTIVEC;
6494 pcc->msr_mask = (1ull << MSR_VR) |
6495 (1ull << MSR_POW) |
6496 (1ull << MSR_ILE) |
6497 (1ull << MSR_EE) |
6498 (1ull << MSR_PR) |
6499 (1ull << MSR_FP) |
6500 (1ull << MSR_ME) |
6501 (1ull << MSR_FE0) |
6502 (1ull << MSR_SE) |
6503 (1ull << MSR_DE) |
6504 (1ull << MSR_FE1) |
6505 (1ull << MSR_EP) |
6506 (1ull << MSR_IR) |
6507 (1ull << MSR_DR) |
6508 (1ull << MSR_PMM) |
6509 (1ull << MSR_RI) |
6510 (1ull << MSR_LE);
6511 pcc->mmu_model = POWERPC_MMU_32B;
6512 #if defined(CONFIG_SOFTMMU)
6513 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
6514 #endif
6515 pcc->excp_model = POWERPC_EXCP_74xx;
6516 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6517 pcc->bfd_mach = bfd_mach_ppc_7400;
6518 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
6519 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
6520 POWERPC_FLAG_BUS_CLK;
6523 static void init_proc_7410(CPUPPCState *env)
6525 gen_spr_ne_601(env);
6526 gen_spr_sdr1(env);
6527 gen_spr_7xx(env);
6528 /* Time base */
6529 gen_tbl(env);
6530 /* 74xx specific SPR */
6531 gen_spr_74xx(env);
6532 /* XXX : not implemented */
6533 spr_register(env, SPR_UBAMR, "UBAMR",
6534 &spr_read_ureg, SPR_NOACCESS,
6535 &spr_read_ureg, SPR_NOACCESS,
6536 0x00000000);
6537 /* Thermal management */
6538 gen_spr_thrm(env);
6539 /* L2PMCR */
6540 /* XXX : not implemented */
6541 spr_register(env, SPR_L2PMCR, "L2PMCR",
6542 SPR_NOACCESS, SPR_NOACCESS,
6543 &spr_read_generic, &spr_write_generic,
6544 0x00000000);
6545 /* LDSTDB */
6546 /* XXX : not implemented */
6547 spr_register(env, SPR_LDSTDB, "LDSTDB",
6548 SPR_NOACCESS, SPR_NOACCESS,
6549 &spr_read_generic, &spr_write_generic,
6550 0x00000000);
6551 /* Memory management */
6552 gen_low_BATs(env);
6553 init_excp_7400(env);
6554 env->dcache_line_size = 32;
6555 env->icache_line_size = 32;
6556 /* Allocate hardware IRQ controller */
6557 ppc6xx_irq_init(ppc_env_get_cpu(env));
6560 POWERPC_FAMILY(7410)(ObjectClass *oc, void *data)
6562 DeviceClass *dc = DEVICE_CLASS(oc);
6563 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6565 dc->desc = "PowerPC 7410 (aka G4)";
6566 pcc->init_proc = init_proc_7410;
6567 pcc->check_pow = check_pow_hid0;
6568 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6569 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6570 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6571 PPC_FLOAT_STFIWX |
6572 PPC_CACHE | PPC_CACHE_ICBI |
6573 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6574 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6575 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6576 PPC_MEM_TLBIA |
6577 PPC_SEGMENT | PPC_EXTERN |
6578 PPC_ALTIVEC;
6579 pcc->msr_mask = (1ull << MSR_VR) |
6580 (1ull << MSR_POW) |
6581 (1ull << MSR_ILE) |
6582 (1ull << MSR_EE) |
6583 (1ull << MSR_PR) |
6584 (1ull << MSR_FP) |
6585 (1ull << MSR_ME) |
6586 (1ull << MSR_FE0) |
6587 (1ull << MSR_SE) |
6588 (1ull << MSR_DE) |
6589 (1ull << MSR_FE1) |
6590 (1ull << MSR_EP) |
6591 (1ull << MSR_IR) |
6592 (1ull << MSR_DR) |
6593 (1ull << MSR_PMM) |
6594 (1ull << MSR_RI) |
6595 (1ull << MSR_LE);
6596 pcc->mmu_model = POWERPC_MMU_32B;
6597 #if defined(CONFIG_SOFTMMU)
6598 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
6599 #endif
6600 pcc->excp_model = POWERPC_EXCP_74xx;
6601 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6602 pcc->bfd_mach = bfd_mach_ppc_7400;
6603 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
6604 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
6605 POWERPC_FLAG_BUS_CLK;
6608 static void init_proc_7440(CPUPPCState *env)
6610 gen_spr_ne_601(env);
6611 gen_spr_sdr1(env);
6612 gen_spr_7xx(env);
6613 /* Time base */
6614 gen_tbl(env);
6615 /* 74xx specific SPR */
6616 gen_spr_74xx(env);
6617 /* XXX : not implemented */
6618 spr_register(env, SPR_UBAMR, "UBAMR",
6619 &spr_read_ureg, SPR_NOACCESS,
6620 &spr_read_ureg, SPR_NOACCESS,
6621 0x00000000);
6622 /* LDSTCR */
6623 /* XXX : not implemented */
6624 spr_register(env, SPR_LDSTCR, "LDSTCR",
6625 SPR_NOACCESS, SPR_NOACCESS,
6626 &spr_read_generic, &spr_write_generic,
6627 0x00000000);
6628 /* ICTRL */
6629 /* XXX : not implemented */
6630 spr_register(env, SPR_ICTRL, "ICTRL",
6631 SPR_NOACCESS, SPR_NOACCESS,
6632 &spr_read_generic, &spr_write_generic,
6633 0x00000000);
6634 /* MSSSR0 */
6635 /* XXX : not implemented */
6636 spr_register(env, SPR_MSSSR0, "MSSSR0",
6637 SPR_NOACCESS, SPR_NOACCESS,
6638 &spr_read_generic, &spr_write_generic,
6639 0x00000000);
6640 /* PMC */
6641 /* XXX : not implemented */
6642 spr_register(env, SPR_7XX_PMC5, "PMC5",
6643 SPR_NOACCESS, SPR_NOACCESS,
6644 &spr_read_generic, &spr_write_generic,
6645 0x00000000);
6646 /* XXX : not implemented */
6647 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
6648 &spr_read_ureg, SPR_NOACCESS,
6649 &spr_read_ureg, SPR_NOACCESS,
6650 0x00000000);
6651 /* XXX : not implemented */
6652 spr_register(env, SPR_7XX_PMC6, "PMC6",
6653 SPR_NOACCESS, SPR_NOACCESS,
6654 &spr_read_generic, &spr_write_generic,
6655 0x00000000);
6656 /* XXX : not implemented */
6657 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
6658 &spr_read_ureg, SPR_NOACCESS,
6659 &spr_read_ureg, SPR_NOACCESS,
6660 0x00000000);
6661 /* Memory management */
6662 gen_low_BATs(env);
6663 gen_74xx_soft_tlb(env, 128, 2);
6664 init_excp_7450(env);
6665 env->dcache_line_size = 32;
6666 env->icache_line_size = 32;
6667 /* Allocate hardware IRQ controller */
6668 ppc6xx_irq_init(ppc_env_get_cpu(env));
6671 POWERPC_FAMILY(7440)(ObjectClass *oc, void *data)
6673 DeviceClass *dc = DEVICE_CLASS(oc);
6674 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6676 dc->desc = "PowerPC 7440 (aka G4)";
6677 pcc->init_proc = init_proc_7440;
6678 pcc->check_pow = check_pow_hid0_74xx;
6679 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6680 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6681 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6682 PPC_FLOAT_STFIWX |
6683 PPC_CACHE | PPC_CACHE_ICBI |
6684 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6685 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6686 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6687 PPC_MEM_TLBIA | PPC_74xx_TLB |
6688 PPC_SEGMENT | PPC_EXTERN |
6689 PPC_ALTIVEC;
6690 pcc->msr_mask = (1ull << MSR_VR) |
6691 (1ull << MSR_POW) |
6692 (1ull << MSR_ILE) |
6693 (1ull << MSR_EE) |
6694 (1ull << MSR_PR) |
6695 (1ull << MSR_FP) |
6696 (1ull << MSR_ME) |
6697 (1ull << MSR_FE0) |
6698 (1ull << MSR_SE) |
6699 (1ull << MSR_DE) |
6700 (1ull << MSR_FE1) |
6701 (1ull << MSR_EP) |
6702 (1ull << MSR_IR) |
6703 (1ull << MSR_DR) |
6704 (1ull << MSR_PMM) |
6705 (1ull << MSR_RI) |
6706 (1ull << MSR_LE);
6707 pcc->mmu_model = POWERPC_MMU_SOFT_74xx;
6708 pcc->excp_model = POWERPC_EXCP_74xx;
6709 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6710 pcc->bfd_mach = bfd_mach_ppc_7400;
6711 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
6712 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
6713 POWERPC_FLAG_BUS_CLK;
6716 static void init_proc_7450(CPUPPCState *env)
6718 gen_spr_ne_601(env);
6719 gen_spr_sdr1(env);
6720 gen_spr_7xx(env);
6721 /* Time base */
6722 gen_tbl(env);
6723 /* 74xx specific SPR */
6724 gen_spr_74xx(env);
6725 /* Level 3 cache control */
6726 gen_l3_ctrl(env);
6727 /* L3ITCR1 */
6728 /* XXX : not implemented */
6729 spr_register(env, SPR_L3ITCR1, "L3ITCR1",
6730 SPR_NOACCESS, SPR_NOACCESS,
6731 &spr_read_generic, &spr_write_generic,
6732 0x00000000);
6733 /* L3ITCR2 */
6734 /* XXX : not implemented */
6735 spr_register(env, SPR_L3ITCR2, "L3ITCR2",
6736 SPR_NOACCESS, SPR_NOACCESS,
6737 &spr_read_generic, &spr_write_generic,
6738 0x00000000);
6739 /* L3ITCR3 */
6740 /* XXX : not implemented */
6741 spr_register(env, SPR_L3ITCR3, "L3ITCR3",
6742 SPR_NOACCESS, SPR_NOACCESS,
6743 &spr_read_generic, &spr_write_generic,
6744 0x00000000);
6745 /* L3OHCR */
6746 /* XXX : not implemented */
6747 spr_register(env, SPR_L3OHCR, "L3OHCR",
6748 SPR_NOACCESS, SPR_NOACCESS,
6749 &spr_read_generic, &spr_write_generic,
6750 0x00000000);
6751 /* XXX : not implemented */
6752 spr_register(env, SPR_UBAMR, "UBAMR",
6753 &spr_read_ureg, SPR_NOACCESS,
6754 &spr_read_ureg, SPR_NOACCESS,
6755 0x00000000);
6756 /* LDSTCR */
6757 /* XXX : not implemented */
6758 spr_register(env, SPR_LDSTCR, "LDSTCR",
6759 SPR_NOACCESS, SPR_NOACCESS,
6760 &spr_read_generic, &spr_write_generic,
6761 0x00000000);
6762 /* ICTRL */
6763 /* XXX : not implemented */
6764 spr_register(env, SPR_ICTRL, "ICTRL",
6765 SPR_NOACCESS, SPR_NOACCESS,
6766 &spr_read_generic, &spr_write_generic,
6767 0x00000000);
6768 /* MSSSR0 */
6769 /* XXX : not implemented */
6770 spr_register(env, SPR_MSSSR0, "MSSSR0",
6771 SPR_NOACCESS, SPR_NOACCESS,
6772 &spr_read_generic, &spr_write_generic,
6773 0x00000000);
6774 /* PMC */
6775 /* XXX : not implemented */
6776 spr_register(env, SPR_7XX_PMC5, "PMC5",
6777 SPR_NOACCESS, SPR_NOACCESS,
6778 &spr_read_generic, &spr_write_generic,
6779 0x00000000);
6780 /* XXX : not implemented */
6781 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
6782 &spr_read_ureg, SPR_NOACCESS,
6783 &spr_read_ureg, SPR_NOACCESS,
6784 0x00000000);
6785 /* XXX : not implemented */
6786 spr_register(env, SPR_7XX_PMC6, "PMC6",
6787 SPR_NOACCESS, SPR_NOACCESS,
6788 &spr_read_generic, &spr_write_generic,
6789 0x00000000);
6790 /* XXX : not implemented */
6791 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
6792 &spr_read_ureg, SPR_NOACCESS,
6793 &spr_read_ureg, SPR_NOACCESS,
6794 0x00000000);
6795 /* Memory management */
6796 gen_low_BATs(env);
6797 gen_74xx_soft_tlb(env, 128, 2);
6798 init_excp_7450(env);
6799 env->dcache_line_size = 32;
6800 env->icache_line_size = 32;
6801 /* Allocate hardware IRQ controller */
6802 ppc6xx_irq_init(ppc_env_get_cpu(env));
6805 POWERPC_FAMILY(7450)(ObjectClass *oc, void *data)
6807 DeviceClass *dc = DEVICE_CLASS(oc);
6808 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6810 dc->desc = "PowerPC 7450 (aka G4)";
6811 pcc->init_proc = init_proc_7450;
6812 pcc->check_pow = check_pow_hid0_74xx;
6813 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6814 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6815 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6816 PPC_FLOAT_STFIWX |
6817 PPC_CACHE | PPC_CACHE_ICBI |
6818 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6819 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6820 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6821 PPC_MEM_TLBIA | PPC_74xx_TLB |
6822 PPC_SEGMENT | PPC_EXTERN |
6823 PPC_ALTIVEC;
6824 pcc->msr_mask = (1ull << MSR_VR) |
6825 (1ull << MSR_POW) |
6826 (1ull << MSR_ILE) |
6827 (1ull << MSR_EE) |
6828 (1ull << MSR_PR) |
6829 (1ull << MSR_FP) |
6830 (1ull << MSR_ME) |
6831 (1ull << MSR_FE0) |
6832 (1ull << MSR_SE) |
6833 (1ull << MSR_DE) |
6834 (1ull << MSR_FE1) |
6835 (1ull << MSR_EP) |
6836 (1ull << MSR_IR) |
6837 (1ull << MSR_DR) |
6838 (1ull << MSR_PMM) |
6839 (1ull << MSR_RI) |
6840 (1ull << MSR_LE);
6841 pcc->mmu_model = POWERPC_MMU_SOFT_74xx;
6842 pcc->excp_model = POWERPC_EXCP_74xx;
6843 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6844 pcc->bfd_mach = bfd_mach_ppc_7400;
6845 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
6846 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
6847 POWERPC_FLAG_BUS_CLK;
6850 static void init_proc_7445(CPUPPCState *env)
6852 gen_spr_ne_601(env);
6853 gen_spr_sdr1(env);
6854 gen_spr_7xx(env);
6855 /* Time base */
6856 gen_tbl(env);
6857 /* 74xx specific SPR */
6858 gen_spr_74xx(env);
6859 /* LDSTCR */
6860 /* XXX : not implemented */
6861 spr_register(env, SPR_LDSTCR, "LDSTCR",
6862 SPR_NOACCESS, SPR_NOACCESS,
6863 &spr_read_generic, &spr_write_generic,
6864 0x00000000);
6865 /* ICTRL */
6866 /* XXX : not implemented */
6867 spr_register(env, SPR_ICTRL, "ICTRL",
6868 SPR_NOACCESS, SPR_NOACCESS,
6869 &spr_read_generic, &spr_write_generic,
6870 0x00000000);
6871 /* MSSSR0 */
6872 /* XXX : not implemented */
6873 spr_register(env, SPR_MSSSR0, "MSSSR0",
6874 SPR_NOACCESS, SPR_NOACCESS,
6875 &spr_read_generic, &spr_write_generic,
6876 0x00000000);
6877 /* PMC */
6878 /* XXX : not implemented */
6879 spr_register(env, SPR_7XX_PMC5, "PMC5",
6880 SPR_NOACCESS, SPR_NOACCESS,
6881 &spr_read_generic, &spr_write_generic,
6882 0x00000000);
6883 /* XXX : not implemented */
6884 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
6885 &spr_read_ureg, SPR_NOACCESS,
6886 &spr_read_ureg, SPR_NOACCESS,
6887 0x00000000);
6888 /* XXX : not implemented */
6889 spr_register(env, SPR_7XX_PMC6, "PMC6",
6890 SPR_NOACCESS, SPR_NOACCESS,
6891 &spr_read_generic, &spr_write_generic,
6892 0x00000000);
6893 /* XXX : not implemented */
6894 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
6895 &spr_read_ureg, SPR_NOACCESS,
6896 &spr_read_ureg, SPR_NOACCESS,
6897 0x00000000);
6898 /* SPRGs */
6899 spr_register(env, SPR_SPRG4, "SPRG4",
6900 SPR_NOACCESS, SPR_NOACCESS,
6901 &spr_read_generic, &spr_write_generic,
6902 0x00000000);
6903 spr_register(env, SPR_USPRG4, "USPRG4",
6904 &spr_read_ureg, SPR_NOACCESS,
6905 &spr_read_ureg, SPR_NOACCESS,
6906 0x00000000);
6907 spr_register(env, SPR_SPRG5, "SPRG5",
6908 SPR_NOACCESS, SPR_NOACCESS,
6909 &spr_read_generic, &spr_write_generic,
6910 0x00000000);
6911 spr_register(env, SPR_USPRG5, "USPRG5",
6912 &spr_read_ureg, SPR_NOACCESS,
6913 &spr_read_ureg, SPR_NOACCESS,
6914 0x00000000);
6915 spr_register(env, SPR_SPRG6, "SPRG6",
6916 SPR_NOACCESS, SPR_NOACCESS,
6917 &spr_read_generic, &spr_write_generic,
6918 0x00000000);
6919 spr_register(env, SPR_USPRG6, "USPRG6",
6920 &spr_read_ureg, SPR_NOACCESS,
6921 &spr_read_ureg, SPR_NOACCESS,
6922 0x00000000);
6923 spr_register(env, SPR_SPRG7, "SPRG7",
6924 SPR_NOACCESS, SPR_NOACCESS,
6925 &spr_read_generic, &spr_write_generic,
6926 0x00000000);
6927 spr_register(env, SPR_USPRG7, "USPRG7",
6928 &spr_read_ureg, SPR_NOACCESS,
6929 &spr_read_ureg, SPR_NOACCESS,
6930 0x00000000);
6931 /* Memory management */
6932 gen_low_BATs(env);
6933 gen_high_BATs(env);
6934 gen_74xx_soft_tlb(env, 128, 2);
6935 init_excp_7450(env);
6936 env->dcache_line_size = 32;
6937 env->icache_line_size = 32;
6938 /* Allocate hardware IRQ controller */
6939 ppc6xx_irq_init(ppc_env_get_cpu(env));
6942 POWERPC_FAMILY(7445)(ObjectClass *oc, void *data)
6944 DeviceClass *dc = DEVICE_CLASS(oc);
6945 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
6947 dc->desc = "PowerPC 7445 (aka G4)";
6948 pcc->init_proc = init_proc_7445;
6949 pcc->check_pow = check_pow_hid0_74xx;
6950 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
6951 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
6952 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
6953 PPC_FLOAT_STFIWX |
6954 PPC_CACHE | PPC_CACHE_ICBI |
6955 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
6956 PPC_MEM_SYNC | PPC_MEM_EIEIO |
6957 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
6958 PPC_MEM_TLBIA | PPC_74xx_TLB |
6959 PPC_SEGMENT | PPC_EXTERN |
6960 PPC_ALTIVEC;
6961 pcc->msr_mask = (1ull << MSR_VR) |
6962 (1ull << MSR_POW) |
6963 (1ull << MSR_ILE) |
6964 (1ull << MSR_EE) |
6965 (1ull << MSR_PR) |
6966 (1ull << MSR_FP) |
6967 (1ull << MSR_ME) |
6968 (1ull << MSR_FE0) |
6969 (1ull << MSR_SE) |
6970 (1ull << MSR_DE) |
6971 (1ull << MSR_FE1) |
6972 (1ull << MSR_EP) |
6973 (1ull << MSR_IR) |
6974 (1ull << MSR_DR) |
6975 (1ull << MSR_PMM) |
6976 (1ull << MSR_RI) |
6977 (1ull << MSR_LE);
6978 pcc->mmu_model = POWERPC_MMU_SOFT_74xx;
6979 pcc->excp_model = POWERPC_EXCP_74xx;
6980 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
6981 pcc->bfd_mach = bfd_mach_ppc_7400;
6982 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
6983 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
6984 POWERPC_FLAG_BUS_CLK;
6987 static void init_proc_7455(CPUPPCState *env)
6989 gen_spr_ne_601(env);
6990 gen_spr_sdr1(env);
6991 gen_spr_7xx(env);
6992 /* Time base */
6993 gen_tbl(env);
6994 /* 74xx specific SPR */
6995 gen_spr_74xx(env);
6996 /* Level 3 cache control */
6997 gen_l3_ctrl(env);
6998 /* LDSTCR */
6999 /* XXX : not implemented */
7000 spr_register(env, SPR_LDSTCR, "LDSTCR",
7001 SPR_NOACCESS, SPR_NOACCESS,
7002 &spr_read_generic, &spr_write_generic,
7003 0x00000000);
7004 /* ICTRL */
7005 /* XXX : not implemented */
7006 spr_register(env, SPR_ICTRL, "ICTRL",
7007 SPR_NOACCESS, SPR_NOACCESS,
7008 &spr_read_generic, &spr_write_generic,
7009 0x00000000);
7010 /* MSSSR0 */
7011 /* XXX : not implemented */
7012 spr_register(env, SPR_MSSSR0, "MSSSR0",
7013 SPR_NOACCESS, SPR_NOACCESS,
7014 &spr_read_generic, &spr_write_generic,
7015 0x00000000);
7016 /* PMC */
7017 /* XXX : not implemented */
7018 spr_register(env, SPR_7XX_PMC5, "PMC5",
7019 SPR_NOACCESS, SPR_NOACCESS,
7020 &spr_read_generic, &spr_write_generic,
7021 0x00000000);
7022 /* XXX : not implemented */
7023 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
7024 &spr_read_ureg, SPR_NOACCESS,
7025 &spr_read_ureg, SPR_NOACCESS,
7026 0x00000000);
7027 /* XXX : not implemented */
7028 spr_register(env, SPR_7XX_PMC6, "PMC6",
7029 SPR_NOACCESS, SPR_NOACCESS,
7030 &spr_read_generic, &spr_write_generic,
7031 0x00000000);
7032 /* XXX : not implemented */
7033 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
7034 &spr_read_ureg, SPR_NOACCESS,
7035 &spr_read_ureg, SPR_NOACCESS,
7036 0x00000000);
7037 /* SPRGs */
7038 spr_register(env, SPR_SPRG4, "SPRG4",
7039 SPR_NOACCESS, SPR_NOACCESS,
7040 &spr_read_generic, &spr_write_generic,
7041 0x00000000);
7042 spr_register(env, SPR_USPRG4, "USPRG4",
7043 &spr_read_ureg, SPR_NOACCESS,
7044 &spr_read_ureg, SPR_NOACCESS,
7045 0x00000000);
7046 spr_register(env, SPR_SPRG5, "SPRG5",
7047 SPR_NOACCESS, SPR_NOACCESS,
7048 &spr_read_generic, &spr_write_generic,
7049 0x00000000);
7050 spr_register(env, SPR_USPRG5, "USPRG5",
7051 &spr_read_ureg, SPR_NOACCESS,
7052 &spr_read_ureg, SPR_NOACCESS,
7053 0x00000000);
7054 spr_register(env, SPR_SPRG6, "SPRG6",
7055 SPR_NOACCESS, SPR_NOACCESS,
7056 &spr_read_generic, &spr_write_generic,
7057 0x00000000);
7058 spr_register(env, SPR_USPRG6, "USPRG6",
7059 &spr_read_ureg, SPR_NOACCESS,
7060 &spr_read_ureg, SPR_NOACCESS,
7061 0x00000000);
7062 spr_register(env, SPR_SPRG7, "SPRG7",
7063 SPR_NOACCESS, SPR_NOACCESS,
7064 &spr_read_generic, &spr_write_generic,
7065 0x00000000);
7066 spr_register(env, SPR_USPRG7, "USPRG7",
7067 &spr_read_ureg, SPR_NOACCESS,
7068 &spr_read_ureg, SPR_NOACCESS,
7069 0x00000000);
7070 /* Memory management */
7071 gen_low_BATs(env);
7072 gen_high_BATs(env);
7073 gen_74xx_soft_tlb(env, 128, 2);
7074 init_excp_7450(env);
7075 env->dcache_line_size = 32;
7076 env->icache_line_size = 32;
7077 /* Allocate hardware IRQ controller */
7078 ppc6xx_irq_init(ppc_env_get_cpu(env));
7081 POWERPC_FAMILY(7455)(ObjectClass *oc, void *data)
7083 DeviceClass *dc = DEVICE_CLASS(oc);
7084 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
7086 dc->desc = "PowerPC 7455 (aka G4)";
7087 pcc->init_proc = init_proc_7455;
7088 pcc->check_pow = check_pow_hid0_74xx;
7089 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
7090 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
7091 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
7092 PPC_FLOAT_STFIWX |
7093 PPC_CACHE | PPC_CACHE_ICBI |
7094 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
7095 PPC_MEM_SYNC | PPC_MEM_EIEIO |
7096 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
7097 PPC_MEM_TLBIA | PPC_74xx_TLB |
7098 PPC_SEGMENT | PPC_EXTERN |
7099 PPC_ALTIVEC;
7100 pcc->msr_mask = (1ull << MSR_VR) |
7101 (1ull << MSR_POW) |
7102 (1ull << MSR_ILE) |
7103 (1ull << MSR_EE) |
7104 (1ull << MSR_PR) |
7105 (1ull << MSR_FP) |
7106 (1ull << MSR_ME) |
7107 (1ull << MSR_FE0) |
7108 (1ull << MSR_SE) |
7109 (1ull << MSR_DE) |
7110 (1ull << MSR_FE1) |
7111 (1ull << MSR_EP) |
7112 (1ull << MSR_IR) |
7113 (1ull << MSR_DR) |
7114 (1ull << MSR_PMM) |
7115 (1ull << MSR_RI) |
7116 (1ull << MSR_LE);
7117 pcc->mmu_model = POWERPC_MMU_SOFT_74xx;
7118 pcc->excp_model = POWERPC_EXCP_74xx;
7119 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
7120 pcc->bfd_mach = bfd_mach_ppc_7400;
7121 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
7122 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
7123 POWERPC_FLAG_BUS_CLK;
7126 static void init_proc_7457(CPUPPCState *env)
7128 gen_spr_ne_601(env);
7129 gen_spr_sdr1(env);
7130 gen_spr_7xx(env);
7131 /* Time base */
7132 gen_tbl(env);
7133 /* 74xx specific SPR */
7134 gen_spr_74xx(env);
7135 /* Level 3 cache control */
7136 gen_l3_ctrl(env);
7137 /* L3ITCR1 */
7138 /* XXX : not implemented */
7139 spr_register(env, SPR_L3ITCR1, "L3ITCR1",
7140 SPR_NOACCESS, SPR_NOACCESS,
7141 &spr_read_generic, &spr_write_generic,
7142 0x00000000);
7143 /* L3ITCR2 */
7144 /* XXX : not implemented */
7145 spr_register(env, SPR_L3ITCR2, "L3ITCR2",
7146 SPR_NOACCESS, SPR_NOACCESS,
7147 &spr_read_generic, &spr_write_generic,
7148 0x00000000);
7149 /* L3ITCR3 */
7150 /* XXX : not implemented */
7151 spr_register(env, SPR_L3ITCR3, "L3ITCR3",
7152 SPR_NOACCESS, SPR_NOACCESS,
7153 &spr_read_generic, &spr_write_generic,
7154 0x00000000);
7155 /* L3OHCR */
7156 /* XXX : not implemented */
7157 spr_register(env, SPR_L3OHCR, "L3OHCR",
7158 SPR_NOACCESS, SPR_NOACCESS,
7159 &spr_read_generic, &spr_write_generic,
7160 0x00000000);
7161 /* LDSTCR */
7162 /* XXX : not implemented */
7163 spr_register(env, SPR_LDSTCR, "LDSTCR",
7164 SPR_NOACCESS, SPR_NOACCESS,
7165 &spr_read_generic, &spr_write_generic,
7166 0x00000000);
7167 /* ICTRL */
7168 /* XXX : not implemented */
7169 spr_register(env, SPR_ICTRL, "ICTRL",
7170 SPR_NOACCESS, SPR_NOACCESS,
7171 &spr_read_generic, &spr_write_generic,
7172 0x00000000);
7173 /* MSSSR0 */
7174 /* XXX : not implemented */
7175 spr_register(env, SPR_MSSSR0, "MSSSR0",
7176 SPR_NOACCESS, SPR_NOACCESS,
7177 &spr_read_generic, &spr_write_generic,
7178 0x00000000);
7179 /* PMC */
7180 /* XXX : not implemented */
7181 spr_register(env, SPR_7XX_PMC5, "PMC5",
7182 SPR_NOACCESS, SPR_NOACCESS,
7183 &spr_read_generic, &spr_write_generic,
7184 0x00000000);
7185 /* XXX : not implemented */
7186 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
7187 &spr_read_ureg, SPR_NOACCESS,
7188 &spr_read_ureg, SPR_NOACCESS,
7189 0x00000000);
7190 /* XXX : not implemented */
7191 spr_register(env, SPR_7XX_PMC6, "PMC6",
7192 SPR_NOACCESS, SPR_NOACCESS,
7193 &spr_read_generic, &spr_write_generic,
7194 0x00000000);
7195 /* XXX : not implemented */
7196 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
7197 &spr_read_ureg, SPR_NOACCESS,
7198 &spr_read_ureg, SPR_NOACCESS,
7199 0x00000000);
7200 /* SPRGs */
7201 spr_register(env, SPR_SPRG4, "SPRG4",
7202 SPR_NOACCESS, SPR_NOACCESS,
7203 &spr_read_generic, &spr_write_generic,
7204 0x00000000);
7205 spr_register(env, SPR_USPRG4, "USPRG4",
7206 &spr_read_ureg, SPR_NOACCESS,
7207 &spr_read_ureg, SPR_NOACCESS,
7208 0x00000000);
7209 spr_register(env, SPR_SPRG5, "SPRG5",
7210 SPR_NOACCESS, SPR_NOACCESS,
7211 &spr_read_generic, &spr_write_generic,
7212 0x00000000);
7213 spr_register(env, SPR_USPRG5, "USPRG5",
7214 &spr_read_ureg, SPR_NOACCESS,
7215 &spr_read_ureg, SPR_NOACCESS,
7216 0x00000000);
7217 spr_register(env, SPR_SPRG6, "SPRG6",
7218 SPR_NOACCESS, SPR_NOACCESS,
7219 &spr_read_generic, &spr_write_generic,
7220 0x00000000);
7221 spr_register(env, SPR_USPRG6, "USPRG6",
7222 &spr_read_ureg, SPR_NOACCESS,
7223 &spr_read_ureg, SPR_NOACCESS,
7224 0x00000000);
7225 spr_register(env, SPR_SPRG7, "SPRG7",
7226 SPR_NOACCESS, SPR_NOACCESS,
7227 &spr_read_generic, &spr_write_generic,
7228 0x00000000);
7229 spr_register(env, SPR_USPRG7, "USPRG7",
7230 &spr_read_ureg, SPR_NOACCESS,
7231 &spr_read_ureg, SPR_NOACCESS,
7232 0x00000000);
7233 /* Memory management */
7234 gen_low_BATs(env);
7235 gen_high_BATs(env);
7236 gen_74xx_soft_tlb(env, 128, 2);
7237 init_excp_7450(env);
7238 env->dcache_line_size = 32;
7239 env->icache_line_size = 32;
7240 /* Allocate hardware IRQ controller */
7241 ppc6xx_irq_init(ppc_env_get_cpu(env));
7244 POWERPC_FAMILY(7457)(ObjectClass *oc, void *data)
7246 DeviceClass *dc = DEVICE_CLASS(oc);
7247 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
7249 dc->desc = "PowerPC 7457 (aka G4)";
7250 pcc->init_proc = init_proc_7457;
7251 pcc->check_pow = check_pow_hid0_74xx;
7252 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
7253 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
7254 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
7255 PPC_FLOAT_STFIWX |
7256 PPC_CACHE | PPC_CACHE_ICBI |
7257 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
7258 PPC_MEM_SYNC | PPC_MEM_EIEIO |
7259 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
7260 PPC_MEM_TLBIA | PPC_74xx_TLB |
7261 PPC_SEGMENT | PPC_EXTERN |
7262 PPC_ALTIVEC;
7263 pcc->msr_mask = (1ull << MSR_VR) |
7264 (1ull << MSR_POW) |
7265 (1ull << MSR_ILE) |
7266 (1ull << MSR_EE) |
7267 (1ull << MSR_PR) |
7268 (1ull << MSR_FP) |
7269 (1ull << MSR_ME) |
7270 (1ull << MSR_FE0) |
7271 (1ull << MSR_SE) |
7272 (1ull << MSR_DE) |
7273 (1ull << MSR_FE1) |
7274 (1ull << MSR_EP) |
7275 (1ull << MSR_IR) |
7276 (1ull << MSR_DR) |
7277 (1ull << MSR_PMM) |
7278 (1ull << MSR_RI) |
7279 (1ull << MSR_LE);
7280 pcc->mmu_model = POWERPC_MMU_SOFT_74xx;
7281 pcc->excp_model = POWERPC_EXCP_74xx;
7282 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
7283 pcc->bfd_mach = bfd_mach_ppc_7400;
7284 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
7285 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
7286 POWERPC_FLAG_BUS_CLK;
7289 static void init_proc_e600(CPUPPCState *env)
7291 gen_spr_ne_601(env);
7292 gen_spr_sdr1(env);
7293 gen_spr_7xx(env);
7294 /* Time base */
7295 gen_tbl(env);
7296 /* 74xx specific SPR */
7297 gen_spr_74xx(env);
7298 /* XXX : not implemented */
7299 spr_register(env, SPR_UBAMR, "UBAMR",
7300 &spr_read_ureg, SPR_NOACCESS,
7301 &spr_read_ureg, SPR_NOACCESS,
7302 0x00000000);
7303 /* XXX : not implemented */
7304 spr_register(env, SPR_LDSTCR, "LDSTCR",
7305 SPR_NOACCESS, SPR_NOACCESS,
7306 &spr_read_generic, &spr_write_generic,
7307 0x00000000);
7308 /* XXX : not implemented */
7309 spr_register(env, SPR_ICTRL, "ICTRL",
7310 SPR_NOACCESS, SPR_NOACCESS,
7311 &spr_read_generic, &spr_write_generic,
7312 0x00000000);
7313 /* XXX : not implemented */
7314 spr_register(env, SPR_MSSSR0, "MSSSR0",
7315 SPR_NOACCESS, SPR_NOACCESS,
7316 &spr_read_generic, &spr_write_generic,
7317 0x00000000);
7318 /* XXX : not implemented */
7319 spr_register(env, SPR_7XX_PMC5, "PMC5",
7320 SPR_NOACCESS, SPR_NOACCESS,
7321 &spr_read_generic, &spr_write_generic,
7322 0x00000000);
7323 /* XXX : not implemented */
7324 spr_register(env, SPR_7XX_UPMC5, "UPMC5",
7325 &spr_read_ureg, SPR_NOACCESS,
7326 &spr_read_ureg, SPR_NOACCESS,
7327 0x00000000);
7328 /* XXX : not implemented */
7329 spr_register(env, SPR_7XX_PMC6, "PMC6",
7330 SPR_NOACCESS, SPR_NOACCESS,
7331 &spr_read_generic, &spr_write_generic,
7332 0x00000000);
7333 /* XXX : not implemented */
7334 spr_register(env, SPR_7XX_UPMC6, "UPMC6",
7335 &spr_read_ureg, SPR_NOACCESS,
7336 &spr_read_ureg, SPR_NOACCESS,
7337 0x00000000);
7338 /* SPRGs */
7339 spr_register(env, SPR_SPRG4, "SPRG4",
7340 SPR_NOACCESS, SPR_NOACCESS,
7341 &spr_read_generic, &spr_write_generic,
7342 0x00000000);
7343 spr_register(env, SPR_USPRG4, "USPRG4",
7344 &spr_read_ureg, SPR_NOACCESS,
7345 &spr_read_ureg, SPR_NOACCESS,
7346 0x00000000);
7347 spr_register(env, SPR_SPRG5, "SPRG5",
7348 SPR_NOACCESS, SPR_NOACCESS,
7349 &spr_read_generic, &spr_write_generic,
7350 0x00000000);
7351 spr_register(env, SPR_USPRG5, "USPRG5",
7352 &spr_read_ureg, SPR_NOACCESS,
7353 &spr_read_ureg, SPR_NOACCESS,
7354 0x00000000);
7355 spr_register(env, SPR_SPRG6, "SPRG6",
7356 SPR_NOACCESS, SPR_NOACCESS,
7357 &spr_read_generic, &spr_write_generic,
7358 0x00000000);
7359 spr_register(env, SPR_USPRG6, "USPRG6",
7360 &spr_read_ureg, SPR_NOACCESS,
7361 &spr_read_ureg, SPR_NOACCESS,
7362 0x00000000);
7363 spr_register(env, SPR_SPRG7, "SPRG7",
7364 SPR_NOACCESS, SPR_NOACCESS,
7365 &spr_read_generic, &spr_write_generic,
7366 0x00000000);
7367 spr_register(env, SPR_USPRG7, "USPRG7",
7368 &spr_read_ureg, SPR_NOACCESS,
7369 &spr_read_ureg, SPR_NOACCESS,
7370 0x00000000);
7371 /* Memory management */
7372 gen_low_BATs(env);
7373 gen_high_BATs(env);
7374 gen_74xx_soft_tlb(env, 128, 2);
7375 init_excp_7450(env);
7376 env->dcache_line_size = 32;
7377 env->icache_line_size = 32;
7378 /* Allocate hardware IRQ controller */
7379 ppc6xx_irq_init(ppc_env_get_cpu(env));
7382 POWERPC_FAMILY(e600)(ObjectClass *oc, void *data)
7384 DeviceClass *dc = DEVICE_CLASS(oc);
7385 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
7387 dc->desc = "PowerPC e600";
7388 pcc->init_proc = init_proc_e600;
7389 pcc->check_pow = check_pow_hid0_74xx;
7390 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
7391 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
7392 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
7393 PPC_FLOAT_STFIWX |
7394 PPC_CACHE | PPC_CACHE_ICBI |
7395 PPC_CACHE_DCBA | PPC_CACHE_DCBZ |
7396 PPC_MEM_SYNC | PPC_MEM_EIEIO |
7397 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
7398 PPC_MEM_TLBIA | PPC_74xx_TLB |
7399 PPC_SEGMENT | PPC_EXTERN |
7400 PPC_ALTIVEC;
7401 pcc->insns_flags2 = PPC_NONE;
7402 pcc->msr_mask = (1ull << MSR_VR) |
7403 (1ull << MSR_POW) |
7404 (1ull << MSR_ILE) |
7405 (1ull << MSR_EE) |
7406 (1ull << MSR_PR) |
7407 (1ull << MSR_FP) |
7408 (1ull << MSR_ME) |
7409 (1ull << MSR_FE0) |
7410 (1ull << MSR_SE) |
7411 (1ull << MSR_DE) |
7412 (1ull << MSR_FE1) |
7413 (1ull << MSR_EP) |
7414 (1ull << MSR_IR) |
7415 (1ull << MSR_DR) |
7416 (1ull << MSR_PMM) |
7417 (1ull << MSR_RI) |
7418 (1ull << MSR_LE);
7419 pcc->mmu_model = POWERPC_MMU_32B;
7420 #if defined(CONFIG_SOFTMMU)
7421 pcc->handle_mmu_fault = ppc_hash32_handle_mmu_fault;
7422 #endif
7423 pcc->excp_model = POWERPC_EXCP_74xx;
7424 pcc->bus_model = PPC_FLAGS_INPUT_6xx;
7425 pcc->bfd_mach = bfd_mach_ppc_7400;
7426 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
7427 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
7428 POWERPC_FLAG_BUS_CLK;
7431 #if defined(TARGET_PPC64)
7432 #if defined(CONFIG_USER_ONLY)
7433 #define POWERPC970_HID5_INIT 0x00000080
7434 #else
7435 #define POWERPC970_HID5_INIT 0x00000000
7436 #endif
7438 static void gen_fscr_facility_check(DisasContext *ctx, int facility_sprn,
7439 int bit, int sprn, int cause)
7441 TCGv_i32 t1 = tcg_const_i32(bit);
7442 TCGv_i32 t2 = tcg_const_i32(sprn);
7443 TCGv_i32 t3 = tcg_const_i32(cause);
7445 gen_helper_fscr_facility_check(cpu_env, t1, t2, t3);
7447 tcg_temp_free_i32(t3);
7448 tcg_temp_free_i32(t2);
7449 tcg_temp_free_i32(t1);
7452 static void gen_msr_facility_check(DisasContext *ctx, int facility_sprn,
7453 int bit, int sprn, int cause)
7455 TCGv_i32 t1 = tcg_const_i32(bit);
7456 TCGv_i32 t2 = tcg_const_i32(sprn);
7457 TCGv_i32 t3 = tcg_const_i32(cause);
7459 gen_helper_msr_facility_check(cpu_env, t1, t2, t3);
7461 tcg_temp_free_i32(t3);
7462 tcg_temp_free_i32(t2);
7463 tcg_temp_free_i32(t1);
7466 static void spr_read_prev_upper32(DisasContext *ctx, int gprn, int sprn)
7468 TCGv spr_up = tcg_temp_new();
7469 TCGv spr = tcg_temp_new();
7471 gen_load_spr(spr, sprn - 1);
7472 tcg_gen_shri_tl(spr_up, spr, 32);
7473 tcg_gen_ext32u_tl(cpu_gpr[gprn], spr_up);
7475 tcg_temp_free(spr);
7476 tcg_temp_free(spr_up);
7479 static void spr_write_prev_upper32(DisasContext *ctx, int sprn, int gprn)
7481 TCGv spr = tcg_temp_new();
7483 gen_load_spr(spr, sprn - 1);
7484 tcg_gen_deposit_tl(spr, spr, cpu_gpr[gprn], 32, 32);
7485 gen_store_spr(sprn - 1, spr);
7487 tcg_temp_free(spr);
7490 static int check_pow_970(CPUPPCState *env)
7492 if (env->spr[SPR_HID0] & (HID0_DEEPNAP | HID0_DOZE | HID0_NAP)) {
7493 return 1;
7496 return 0;
7499 static void gen_spr_970_hid(CPUPPCState *env)
7501 /* Hardware implementation registers */
7502 /* XXX : not implemented */
7503 spr_register(env, SPR_HID0, "HID0",
7504 SPR_NOACCESS, SPR_NOACCESS,
7505 &spr_read_generic, &spr_write_clear,
7506 0x60000000);
7507 spr_register(env, SPR_HID1, "HID1",
7508 SPR_NOACCESS, SPR_NOACCESS,
7509 &spr_read_generic, &spr_write_generic,
7510 0x00000000);
7511 spr_register(env, SPR_970_HID5, "HID5",
7512 SPR_NOACCESS, SPR_NOACCESS,
7513 &spr_read_generic, &spr_write_generic,
7514 POWERPC970_HID5_INIT);
7517 static void gen_spr_970_hior(CPUPPCState *env)
7519 spr_register(env, SPR_HIOR, "SPR_HIOR",
7520 SPR_NOACCESS, SPR_NOACCESS,
7521 &spr_read_hior, &spr_write_hior,
7522 0x00000000);
7525 static void gen_spr_book3s_ctrl(CPUPPCState *env)
7527 spr_register(env, SPR_CTRL, "SPR_CTRL",
7528 SPR_NOACCESS, SPR_NOACCESS,
7529 SPR_NOACCESS, &spr_write_generic,
7530 0x00000000);
7531 spr_register(env, SPR_UCTRL, "SPR_UCTRL",
7532 &spr_read_ureg, SPR_NOACCESS,
7533 &spr_read_ureg, SPR_NOACCESS,
7534 0x00000000);
7537 static void gen_spr_book3s_altivec(CPUPPCState *env)
7539 if (!(env->insns_flags & PPC_ALTIVEC)) {
7540 return;
7543 spr_register_kvm(env, SPR_VRSAVE, "VRSAVE",
7544 &spr_read_generic, &spr_write_generic,
7545 &spr_read_generic, &spr_write_generic,
7546 KVM_REG_PPC_VRSAVE, 0x00000000);
7548 /* Can't find information on what this should be on reset. This
7549 * value is the one used by 74xx processors. */
7550 vscr_init(env, 0x00010000);
7553 static void gen_spr_book3s_dbg(CPUPPCState *env)
7556 * TODO: different specs define different scopes for these,
7557 * will have to address this:
7558 * 970: super/write and super/read
7559 * powerisa 2.03..2.04: hypv/write and super/read.
7560 * powerisa 2.05 and newer: hypv/write and hypv/read.
7562 spr_register_kvm(env, SPR_DABR, "DABR",
7563 SPR_NOACCESS, SPR_NOACCESS,
7564 &spr_read_generic, &spr_write_generic,
7565 KVM_REG_PPC_DABR, 0x00000000);
7566 spr_register_kvm(env, SPR_DABRX, "DABRX",
7567 SPR_NOACCESS, SPR_NOACCESS,
7568 &spr_read_generic, &spr_write_generic,
7569 KVM_REG_PPC_DABRX, 0x00000000);
7572 static void gen_spr_book3s_207_dbg(CPUPPCState *env)
7574 spr_register_kvm_hv(env, SPR_DAWR, "DAWR",
7575 SPR_NOACCESS, SPR_NOACCESS,
7576 SPR_NOACCESS, SPR_NOACCESS,
7577 &spr_read_generic, &spr_write_generic,
7578 KVM_REG_PPC_DAWR, 0x00000000);
7579 spr_register_kvm_hv(env, SPR_DAWRX, "DAWRX",
7580 SPR_NOACCESS, SPR_NOACCESS,
7581 SPR_NOACCESS, SPR_NOACCESS,
7582 &spr_read_generic, &spr_write_generic,
7583 KVM_REG_PPC_DAWRX, 0x00000000);
7584 spr_register_kvm_hv(env, SPR_CIABR, "CIABR",
7585 SPR_NOACCESS, SPR_NOACCESS,
7586 SPR_NOACCESS, SPR_NOACCESS,
7587 &spr_read_generic, &spr_write_generic,
7588 KVM_REG_PPC_CIABR, 0x00000000);
7591 static void gen_spr_970_dbg(CPUPPCState *env)
7593 /* Breakpoints */
7594 spr_register(env, SPR_IABR, "IABR",
7595 SPR_NOACCESS, SPR_NOACCESS,
7596 &spr_read_generic, &spr_write_generic,
7597 0x00000000);
7600 static void gen_spr_book3s_pmu_sup(CPUPPCState *env)
7602 spr_register_kvm(env, SPR_POWER_MMCR0, "MMCR0",
7603 SPR_NOACCESS, SPR_NOACCESS,
7604 &spr_read_generic, &spr_write_generic,
7605 KVM_REG_PPC_MMCR0, 0x00000000);
7606 spr_register_kvm(env, SPR_POWER_MMCR1, "MMCR1",
7607 SPR_NOACCESS, SPR_NOACCESS,
7608 &spr_read_generic, &spr_write_generic,
7609 KVM_REG_PPC_MMCR1, 0x00000000);
7610 spr_register_kvm(env, SPR_POWER_MMCRA, "MMCRA",
7611 SPR_NOACCESS, SPR_NOACCESS,
7612 &spr_read_generic, &spr_write_generic,
7613 KVM_REG_PPC_MMCRA, 0x00000000);
7614 spr_register_kvm(env, SPR_POWER_PMC1, "PMC1",
7615 SPR_NOACCESS, SPR_NOACCESS,
7616 &spr_read_generic, &spr_write_generic,
7617 KVM_REG_PPC_PMC1, 0x00000000);
7618 spr_register_kvm(env, SPR_POWER_PMC2, "PMC2",
7619 SPR_NOACCESS, SPR_NOACCESS,
7620 &spr_read_generic, &spr_write_generic,
7621 KVM_REG_PPC_PMC2, 0x00000000);
7622 spr_register_kvm(env, SPR_POWER_PMC3, "PMC3",
7623 SPR_NOACCESS, SPR_NOACCESS,
7624 &spr_read_generic, &spr_write_generic,
7625 KVM_REG_PPC_PMC3, 0x00000000);
7626 spr_register_kvm(env, SPR_POWER_PMC4, "PMC4",
7627 SPR_NOACCESS, SPR_NOACCESS,
7628 &spr_read_generic, &spr_write_generic,
7629 KVM_REG_PPC_PMC4, 0x00000000);
7630 spr_register_kvm(env, SPR_POWER_PMC5, "PMC5",
7631 SPR_NOACCESS, SPR_NOACCESS,
7632 &spr_read_generic, &spr_write_generic,
7633 KVM_REG_PPC_PMC5, 0x00000000);
7634 spr_register_kvm(env, SPR_POWER_PMC6, "PMC6",
7635 SPR_NOACCESS, SPR_NOACCESS,
7636 &spr_read_generic, &spr_write_generic,
7637 KVM_REG_PPC_PMC6, 0x00000000);
7638 spr_register_kvm(env, SPR_POWER_SIAR, "SIAR",
7639 SPR_NOACCESS, SPR_NOACCESS,
7640 &spr_read_generic, &spr_write_generic,
7641 KVM_REG_PPC_SIAR, 0x00000000);
7642 spr_register_kvm(env, SPR_POWER_SDAR, "SDAR",
7643 SPR_NOACCESS, SPR_NOACCESS,
7644 &spr_read_generic, &spr_write_generic,
7645 KVM_REG_PPC_SDAR, 0x00000000);
7648 static void gen_spr_book3s_pmu_user(CPUPPCState *env)
7650 spr_register(env, SPR_POWER_UMMCR0, "UMMCR0",
7651 &spr_read_ureg, SPR_NOACCESS,
7652 &spr_read_ureg, &spr_write_ureg,
7653 0x00000000);
7654 spr_register(env, SPR_POWER_UMMCR1, "UMMCR1",
7655 &spr_read_ureg, SPR_NOACCESS,
7656 &spr_read_ureg, &spr_write_ureg,
7657 0x00000000);
7658 spr_register(env, SPR_POWER_UMMCRA, "UMMCRA",
7659 &spr_read_ureg, SPR_NOACCESS,
7660 &spr_read_ureg, &spr_write_ureg,
7661 0x00000000);
7662 spr_register(env, SPR_POWER_UPMC1, "UPMC1",
7663 &spr_read_ureg, SPR_NOACCESS,
7664 &spr_read_ureg, &spr_write_ureg,
7665 0x00000000);
7666 spr_register(env, SPR_POWER_UPMC2, "UPMC2",
7667 &spr_read_ureg, SPR_NOACCESS,
7668 &spr_read_ureg, &spr_write_ureg,
7669 0x00000000);
7670 spr_register(env, SPR_POWER_UPMC3, "UPMC3",
7671 &spr_read_ureg, SPR_NOACCESS,
7672 &spr_read_ureg, &spr_write_ureg,
7673 0x00000000);
7674 spr_register(env, SPR_POWER_UPMC4, "UPMC4",
7675 &spr_read_ureg, SPR_NOACCESS,
7676 &spr_read_ureg, &spr_write_ureg,
7677 0x00000000);
7678 spr_register(env, SPR_POWER_UPMC5, "UPMC5",
7679 &spr_read_ureg, SPR_NOACCESS,
7680 &spr_read_ureg, &spr_write_ureg,
7681 0x00000000);
7682 spr_register(env, SPR_POWER_UPMC6, "UPMC6",
7683 &spr_read_ureg, SPR_NOACCESS,
7684 &spr_read_ureg, &spr_write_ureg,
7685 0x00000000);
7686 spr_register(env, SPR_POWER_USIAR, "USIAR",
7687 &spr_read_ureg, SPR_NOACCESS,
7688 &spr_read_ureg, &spr_write_ureg,
7689 0x00000000);
7690 spr_register(env, SPR_POWER_USDAR, "USDAR",
7691 &spr_read_ureg, SPR_NOACCESS,
7692 &spr_read_ureg, &spr_write_ureg,
7693 0x00000000);
7696 static void gen_spr_970_pmu_sup(CPUPPCState *env)
7698 spr_register_kvm(env, SPR_970_PMC7, "PMC7",
7699 SPR_NOACCESS, SPR_NOACCESS,
7700 &spr_read_generic, &spr_write_generic,
7701 KVM_REG_PPC_PMC7, 0x00000000);
7702 spr_register_kvm(env, SPR_970_PMC8, "PMC8",
7703 SPR_NOACCESS, SPR_NOACCESS,
7704 &spr_read_generic, &spr_write_generic,
7705 KVM_REG_PPC_PMC8, 0x00000000);
7708 static void gen_spr_970_pmu_user(CPUPPCState *env)
7710 spr_register(env, SPR_970_UPMC7, "UPMC7",
7711 &spr_read_ureg, SPR_NOACCESS,
7712 &spr_read_ureg, &spr_write_ureg,
7713 0x00000000);
7714 spr_register(env, SPR_970_UPMC8, "UPMC8",
7715 &spr_read_ureg, SPR_NOACCESS,
7716 &spr_read_ureg, &spr_write_ureg,
7717 0x00000000);
7720 static void gen_spr_power8_pmu_sup(CPUPPCState *env)
7722 spr_register_kvm(env, SPR_POWER_MMCR2, "MMCR2",
7723 SPR_NOACCESS, SPR_NOACCESS,
7724 &spr_read_generic, &spr_write_generic,
7725 KVM_REG_PPC_MMCR2, 0x00000000);
7726 spr_register_kvm(env, SPR_POWER_MMCRS, "MMCRS",
7727 SPR_NOACCESS, SPR_NOACCESS,
7728 &spr_read_generic, &spr_write_generic,
7729 KVM_REG_PPC_MMCRS, 0x00000000);
7730 spr_register_kvm(env, SPR_POWER_SIER, "SIER",
7731 SPR_NOACCESS, SPR_NOACCESS,
7732 &spr_read_generic, &spr_write_generic,
7733 KVM_REG_PPC_SIER, 0x00000000);
7734 spr_register_kvm(env, SPR_POWER_SPMC1, "SPMC1",
7735 SPR_NOACCESS, SPR_NOACCESS,
7736 &spr_read_generic, &spr_write_generic,
7737 KVM_REG_PPC_SPMC1, 0x00000000);
7738 spr_register_kvm(env, SPR_POWER_SPMC2, "SPMC2",
7739 SPR_NOACCESS, SPR_NOACCESS,
7740 &spr_read_generic, &spr_write_generic,
7741 KVM_REG_PPC_SPMC2, 0x00000000);
7742 spr_register_kvm(env, SPR_TACR, "TACR",
7743 SPR_NOACCESS, SPR_NOACCESS,
7744 &spr_read_generic, &spr_write_generic,
7745 KVM_REG_PPC_TACR, 0x00000000);
7746 spr_register_kvm(env, SPR_TCSCR, "TCSCR",
7747 SPR_NOACCESS, SPR_NOACCESS,
7748 &spr_read_generic, &spr_write_generic,
7749 KVM_REG_PPC_TCSCR, 0x00000000);
7750 spr_register_kvm(env, SPR_CSIGR, "CSIGR",
7751 SPR_NOACCESS, SPR_NOACCESS,
7752 &spr_read_generic, &spr_write_generic,
7753 KVM_REG_PPC_CSIGR, 0x00000000);
7756 static void gen_spr_power8_pmu_user(CPUPPCState *env)
7758 spr_register(env, SPR_POWER_UMMCR2, "UMMCR2",
7759 &spr_read_ureg, SPR_NOACCESS,
7760 &spr_read_ureg, &spr_write_ureg,
7761 0x00000000);
7762 spr_register(env, SPR_POWER_USIER, "USIER",
7763 &spr_read_generic, SPR_NOACCESS,
7764 &spr_read_generic, &spr_write_generic,
7765 0x00000000);
7768 static void gen_spr_power5p_ear(CPUPPCState *env)
7770 /* External access control */
7771 spr_register(env, SPR_EAR, "EAR",
7772 SPR_NOACCESS, SPR_NOACCESS,
7773 &spr_read_generic, &spr_write_generic,
7774 0x00000000);
7777 #if !defined(CONFIG_USER_ONLY)
7778 static void spr_write_hmer(DisasContext *ctx, int sprn, int gprn)
7780 TCGv hmer = tcg_temp_new();
7782 gen_load_spr(hmer, sprn);
7783 tcg_gen_and_tl(hmer, cpu_gpr[gprn], hmer);
7784 gen_store_spr(sprn, hmer);
7785 spr_store_dump_spr(sprn);
7786 tcg_temp_free(hmer);
7789 static void spr_write_lpcr(DisasContext *ctx, int sprn, int gprn)
7791 gen_helper_store_lpcr(cpu_env, cpu_gpr[gprn]);
7794 static void spr_write_970_hid4(DisasContext *ctx, int sprn, int gprn)
7796 #if defined(TARGET_PPC64)
7797 spr_write_generic(ctx, sprn, gprn);
7798 gen_helper_store_lpcr(cpu_env, cpu_gpr[gprn]);
7799 #endif
7802 #endif /* !defined(CONFIG_USER_ONLY) */
7804 static void gen_spr_970_lpar(CPUPPCState *env)
7806 #if !defined(CONFIG_USER_ONLY)
7807 /* Logical partitionning */
7808 /* PPC970: HID4 is effectively the LPCR */
7809 spr_register(env, SPR_970_HID4, "HID4",
7810 SPR_NOACCESS, SPR_NOACCESS,
7811 &spr_read_generic, &spr_write_970_hid4,
7812 0x00000000);
7813 #endif
7816 static void gen_spr_power5p_lpar(CPUPPCState *env)
7818 #if !defined(CONFIG_USER_ONLY)
7819 /* Logical partitionning */
7820 spr_register_kvm_hv(env, SPR_LPCR, "LPCR",
7821 SPR_NOACCESS, SPR_NOACCESS,
7822 SPR_NOACCESS, SPR_NOACCESS,
7823 &spr_read_generic, &spr_write_lpcr,
7824 KVM_REG_PPC_LPCR, LPCR_LPES0 | LPCR_LPES1);
7825 spr_register_hv(env, SPR_HDEC, "HDEC",
7826 SPR_NOACCESS, SPR_NOACCESS,
7827 SPR_NOACCESS, SPR_NOACCESS,
7828 &spr_read_hdecr, &spr_write_hdecr, 0);
7829 #endif
7832 static void gen_spr_book3s_ids(CPUPPCState *env)
7834 /* FIXME: Will need to deal with thread vs core only SPRs */
7836 /* Processor identification */
7837 spr_register_hv(env, SPR_PIR, "PIR",
7838 SPR_NOACCESS, SPR_NOACCESS,
7839 &spr_read_generic, SPR_NOACCESS,
7840 &spr_read_generic, NULL,
7841 0x00000000);
7842 spr_register_hv(env, SPR_HID0, "HID0",
7843 SPR_NOACCESS, SPR_NOACCESS,
7844 SPR_NOACCESS, SPR_NOACCESS,
7845 &spr_read_generic, &spr_write_generic,
7846 0x00000000);
7847 spr_register_hv(env, SPR_TSCR, "TSCR",
7848 SPR_NOACCESS, SPR_NOACCESS,
7849 SPR_NOACCESS, SPR_NOACCESS,
7850 &spr_read_generic, &spr_write_generic,
7851 0x00000000);
7852 spr_register_hv(env, SPR_HMER, "HMER",
7853 SPR_NOACCESS, SPR_NOACCESS,
7854 SPR_NOACCESS, SPR_NOACCESS,
7855 &spr_read_generic, &spr_write_hmer,
7856 0x00000000);
7857 spr_register_hv(env, SPR_HMEER, "HMEER",
7858 SPR_NOACCESS, SPR_NOACCESS,
7859 SPR_NOACCESS, SPR_NOACCESS,
7860 &spr_read_generic, &spr_write_generic,
7861 0x00000000);
7862 spr_register_hv(env, SPR_TFMR, "TFMR",
7863 SPR_NOACCESS, SPR_NOACCESS,
7864 SPR_NOACCESS, SPR_NOACCESS,
7865 &spr_read_generic, &spr_write_generic,
7866 0x00000000);
7867 spr_register_hv(env, SPR_LPIDR, "LPIDR",
7868 SPR_NOACCESS, SPR_NOACCESS,
7869 SPR_NOACCESS, SPR_NOACCESS,
7870 &spr_read_generic, &spr_write_generic,
7871 0x00000000);
7872 spr_register_hv(env, SPR_HFSCR, "HFSCR",
7873 SPR_NOACCESS, SPR_NOACCESS,
7874 SPR_NOACCESS, SPR_NOACCESS,
7875 &spr_read_generic, &spr_write_generic,
7876 0x00000000);
7877 spr_register_hv(env, SPR_MMCRC, "MMCRC",
7878 SPR_NOACCESS, SPR_NOACCESS,
7879 SPR_NOACCESS, SPR_NOACCESS,
7880 &spr_read_generic, &spr_write_generic,
7881 0x00000000);
7882 spr_register_hv(env, SPR_MMCRH, "MMCRH",
7883 SPR_NOACCESS, SPR_NOACCESS,
7884 SPR_NOACCESS, SPR_NOACCESS,
7885 &spr_read_generic, &spr_write_generic,
7886 0x00000000);
7887 spr_register_hv(env, SPR_HSPRG0, "HSPRG0",
7888 SPR_NOACCESS, SPR_NOACCESS,
7889 SPR_NOACCESS, SPR_NOACCESS,
7890 &spr_read_generic, &spr_write_generic,
7891 0x00000000);
7892 spr_register_hv(env, SPR_HSPRG1, "HSPRG1",
7893 SPR_NOACCESS, SPR_NOACCESS,
7894 SPR_NOACCESS, SPR_NOACCESS,
7895 &spr_read_generic, &spr_write_generic,
7896 0x00000000);
7897 spr_register_hv(env, SPR_HSRR0, "HSRR0",
7898 SPR_NOACCESS, SPR_NOACCESS,
7899 SPR_NOACCESS, SPR_NOACCESS,
7900 &spr_read_generic, &spr_write_generic,
7901 0x00000000);
7902 spr_register_hv(env, SPR_HSRR1, "HSRR1",
7903 SPR_NOACCESS, SPR_NOACCESS,
7904 SPR_NOACCESS, SPR_NOACCESS,
7905 &spr_read_generic, &spr_write_generic,
7906 0x00000000);
7907 spr_register_hv(env, SPR_HDAR, "HDAR",
7908 SPR_NOACCESS, SPR_NOACCESS,
7909 SPR_NOACCESS, SPR_NOACCESS,
7910 &spr_read_generic, &spr_write_generic,
7911 0x00000000);
7912 spr_register_hv(env, SPR_HDSISR, "HDSISR",
7913 SPR_NOACCESS, SPR_NOACCESS,
7914 SPR_NOACCESS, SPR_NOACCESS,
7915 &spr_read_generic, &spr_write_generic,
7916 0x00000000);
7917 spr_register_hv(env, SPR_RMOR, "RMOR",
7918 SPR_NOACCESS, SPR_NOACCESS,
7919 SPR_NOACCESS, SPR_NOACCESS,
7920 &spr_read_generic, &spr_write_generic,
7921 0x00000000);
7922 spr_register_hv(env, SPR_HRMOR, "HRMOR",
7923 SPR_NOACCESS, SPR_NOACCESS,
7924 SPR_NOACCESS, SPR_NOACCESS,
7925 &spr_read_generic, &spr_write_generic,
7926 0x00000000);
7929 static void gen_spr_power8_ids(CPUPPCState *env)
7931 /* Thread identification */
7932 spr_register(env, SPR_TIR, "TIR",
7933 SPR_NOACCESS, SPR_NOACCESS,
7934 &spr_read_generic, SPR_NOACCESS,
7935 0x00000000);
7938 static void gen_spr_book3s_purr(CPUPPCState *env)
7940 #if !defined(CONFIG_USER_ONLY)
7941 /* PURR & SPURR: Hack - treat these as aliases for the TB for now */
7942 spr_register_kvm(env, SPR_PURR, "PURR",
7943 &spr_read_purr, SPR_NOACCESS,
7944 &spr_read_purr, SPR_NOACCESS,
7945 KVM_REG_PPC_PURR, 0x00000000);
7946 spr_register_kvm(env, SPR_SPURR, "SPURR",
7947 &spr_read_purr, SPR_NOACCESS,
7948 &spr_read_purr, SPR_NOACCESS,
7949 KVM_REG_PPC_SPURR, 0x00000000);
7950 #endif
7953 static void gen_spr_power6_dbg(CPUPPCState *env)
7955 #if !defined(CONFIG_USER_ONLY)
7956 spr_register(env, SPR_CFAR, "SPR_CFAR",
7957 SPR_NOACCESS, SPR_NOACCESS,
7958 &spr_read_cfar, &spr_write_cfar,
7959 0x00000000);
7960 #endif
7963 static void gen_spr_power5p_common(CPUPPCState *env)
7965 spr_register_kvm(env, SPR_PPR, "PPR",
7966 &spr_read_generic, &spr_write_generic,
7967 &spr_read_generic, &spr_write_generic,
7968 KVM_REG_PPC_PPR, 0x00000000);
7971 static void gen_spr_power6_common(CPUPPCState *env)
7973 #if !defined(CONFIG_USER_ONLY)
7974 spr_register_kvm(env, SPR_DSCR, "SPR_DSCR",
7975 SPR_NOACCESS, SPR_NOACCESS,
7976 &spr_read_generic, &spr_write_generic,
7977 KVM_REG_PPC_DSCR, 0x00000000);
7978 #endif
7980 * Register PCR to report POWERPC_EXCP_PRIV_REG instead of
7981 * POWERPC_EXCP_INVAL_SPR in userspace. Permit hypervisor access.
7983 spr_register_hv(env, SPR_PCR, "PCR",
7984 SPR_NOACCESS, SPR_NOACCESS,
7985 SPR_NOACCESS, SPR_NOACCESS,
7986 &spr_read_generic, &spr_write_pcr,
7987 0x00000000);
7990 static void spr_read_tar(DisasContext *ctx, int gprn, int sprn)
7992 gen_fscr_facility_check(ctx, SPR_FSCR, FSCR_TAR, sprn, FSCR_IC_TAR);
7993 spr_read_generic(ctx, gprn, sprn);
7996 static void spr_write_tar(DisasContext *ctx, int sprn, int gprn)
7998 gen_fscr_facility_check(ctx, SPR_FSCR, FSCR_TAR, sprn, FSCR_IC_TAR);
7999 spr_write_generic(ctx, sprn, gprn);
8002 static void gen_spr_power8_tce_address_control(CPUPPCState *env)
8004 spr_register_kvm(env, SPR_TAR, "TAR",
8005 &spr_read_tar, &spr_write_tar,
8006 &spr_read_generic, &spr_write_generic,
8007 KVM_REG_PPC_TAR, 0x00000000);
8010 static void spr_read_tm(DisasContext *ctx, int gprn, int sprn)
8012 gen_msr_facility_check(ctx, SPR_FSCR, MSR_TM, sprn, FSCR_IC_TM);
8013 spr_read_generic(ctx, gprn, sprn);
8016 static void spr_write_tm(DisasContext *ctx, int sprn, int gprn)
8018 gen_msr_facility_check(ctx, SPR_FSCR, MSR_TM, sprn, FSCR_IC_TM);
8019 spr_write_generic(ctx, sprn, gprn);
8022 static void spr_read_tm_upper32(DisasContext *ctx, int gprn, int sprn)
8024 gen_msr_facility_check(ctx, SPR_FSCR, MSR_TM, sprn, FSCR_IC_TM);
8025 spr_read_prev_upper32(ctx, gprn, sprn);
8028 static void spr_write_tm_upper32(DisasContext *ctx, int sprn, int gprn)
8030 gen_msr_facility_check(ctx, SPR_FSCR, MSR_TM, sprn, FSCR_IC_TM);
8031 spr_write_prev_upper32(ctx, sprn, gprn);
8034 static void gen_spr_power8_tm(CPUPPCState *env)
8036 spr_register_kvm(env, SPR_TFHAR, "TFHAR",
8037 &spr_read_tm, &spr_write_tm,
8038 &spr_read_tm, &spr_write_tm,
8039 KVM_REG_PPC_TFHAR, 0x00000000);
8040 spr_register_kvm(env, SPR_TFIAR, "TFIAR",
8041 &spr_read_tm, &spr_write_tm,
8042 &spr_read_tm, &spr_write_tm,
8043 KVM_REG_PPC_TFIAR, 0x00000000);
8044 spr_register_kvm(env, SPR_TEXASR, "TEXASR",
8045 &spr_read_tm, &spr_write_tm,
8046 &spr_read_tm, &spr_write_tm,
8047 KVM_REG_PPC_TEXASR, 0x00000000);
8048 spr_register(env, SPR_TEXASRU, "TEXASRU",
8049 &spr_read_tm_upper32, &spr_write_tm_upper32,
8050 &spr_read_tm_upper32, &spr_write_tm_upper32,
8051 0x00000000);
8054 static void spr_read_ebb(DisasContext *ctx, int gprn, int sprn)
8056 gen_fscr_facility_check(ctx, SPR_FSCR, FSCR_EBB, sprn, FSCR_IC_EBB);
8057 spr_read_generic(ctx, gprn, sprn);
8060 static void spr_write_ebb(DisasContext *ctx, int sprn, int gprn)
8062 gen_fscr_facility_check(ctx, SPR_FSCR, FSCR_EBB, sprn, FSCR_IC_EBB);
8063 spr_write_generic(ctx, sprn, gprn);
8066 static void spr_read_ebb_upper32(DisasContext *ctx, int gprn, int sprn)
8068 gen_fscr_facility_check(ctx, SPR_FSCR, FSCR_EBB, sprn, FSCR_IC_EBB);
8069 spr_read_prev_upper32(ctx, gprn, sprn);
8072 static void spr_write_ebb_upper32(DisasContext *ctx, int sprn, int gprn)
8074 gen_fscr_facility_check(ctx, SPR_FSCR, FSCR_EBB, sprn, FSCR_IC_EBB);
8075 spr_write_prev_upper32(ctx, sprn, gprn);
8078 static void gen_spr_power8_ebb(CPUPPCState *env)
8080 spr_register(env, SPR_BESCRS, "BESCRS",
8081 &spr_read_ebb, &spr_write_ebb,
8082 &spr_read_generic, &spr_write_generic,
8083 0x00000000);
8084 spr_register(env, SPR_BESCRSU, "BESCRSU",
8085 &spr_read_ebb_upper32, &spr_write_ebb_upper32,
8086 &spr_read_prev_upper32, &spr_write_prev_upper32,
8087 0x00000000);
8088 spr_register(env, SPR_BESCRR, "BESCRR",
8089 &spr_read_ebb, &spr_write_ebb,
8090 &spr_read_generic, &spr_write_generic,
8091 0x00000000);
8092 spr_register(env, SPR_BESCRRU, "BESCRRU",
8093 &spr_read_ebb_upper32, &spr_write_ebb_upper32,
8094 &spr_read_prev_upper32, &spr_write_prev_upper32,
8095 0x00000000);
8096 spr_register_kvm(env, SPR_EBBHR, "EBBHR",
8097 &spr_read_ebb, &spr_write_ebb,
8098 &spr_read_generic, &spr_write_generic,
8099 KVM_REG_PPC_EBBHR, 0x00000000);
8100 spr_register_kvm(env, SPR_EBBRR, "EBBRR",
8101 &spr_read_ebb, &spr_write_ebb,
8102 &spr_read_generic, &spr_write_generic,
8103 KVM_REG_PPC_EBBRR, 0x00000000);
8104 spr_register_kvm(env, SPR_BESCR, "BESCR",
8105 &spr_read_ebb, &spr_write_ebb,
8106 &spr_read_generic, &spr_write_generic,
8107 KVM_REG_PPC_BESCR, 0x00000000);
8110 /* Virtual Time Base */
8111 static void gen_spr_vtb(CPUPPCState *env)
8113 spr_register_kvm(env, SPR_VTB, "VTB",
8114 SPR_NOACCESS, SPR_NOACCESS,
8115 &spr_read_tbl, SPR_NOACCESS,
8116 KVM_REG_PPC_VTB, 0x00000000);
8119 static void gen_spr_power8_fscr(CPUPPCState *env)
8121 #if defined(CONFIG_USER_ONLY)
8122 target_ulong initval = 1ULL << FSCR_TAR;
8123 #else
8124 target_ulong initval = 0;
8125 #endif
8126 spr_register_kvm(env, SPR_FSCR, "FSCR",
8127 SPR_NOACCESS, SPR_NOACCESS,
8128 &spr_read_generic, &spr_write_generic,
8129 KVM_REG_PPC_FSCR, initval);
8132 static void gen_spr_power8_pspb(CPUPPCState *env)
8134 spr_register_kvm(env, SPR_PSPB, "PSPB",
8135 SPR_NOACCESS, SPR_NOACCESS,
8136 &spr_read_generic, &spr_write_generic32,
8137 KVM_REG_PPC_PSPB, 0);
8140 static void gen_spr_power8_ic(CPUPPCState *env)
8142 #if !defined(CONFIG_USER_ONLY)
8143 spr_register_hv(env, SPR_IC, "IC",
8144 SPR_NOACCESS, SPR_NOACCESS,
8145 &spr_read_generic, SPR_NOACCESS,
8146 &spr_read_generic, &spr_write_generic,
8148 #endif
8151 static void gen_spr_power8_book4(CPUPPCState *env)
8153 /* Add a number of P8 book4 registers */
8154 #if !defined(CONFIG_USER_ONLY)
8155 spr_register_kvm(env, SPR_ACOP, "ACOP",
8156 SPR_NOACCESS, SPR_NOACCESS,
8157 &spr_read_generic, &spr_write_generic,
8158 KVM_REG_PPC_ACOP, 0);
8159 spr_register_kvm(env, SPR_BOOKS_PID, "PID",
8160 SPR_NOACCESS, SPR_NOACCESS,
8161 &spr_read_generic, &spr_write_pidr,
8162 KVM_REG_PPC_PID, 0);
8163 spr_register_kvm(env, SPR_WORT, "WORT",
8164 SPR_NOACCESS, SPR_NOACCESS,
8165 &spr_read_generic, &spr_write_generic,
8166 KVM_REG_PPC_WORT, 0);
8167 #endif
8170 static void gen_spr_power7_book4(CPUPPCState *env)
8172 /* Add a number of P7 book4 registers */
8173 #if !defined(CONFIG_USER_ONLY)
8174 spr_register_kvm(env, SPR_ACOP, "ACOP",
8175 SPR_NOACCESS, SPR_NOACCESS,
8176 &spr_read_generic, &spr_write_generic,
8177 KVM_REG_PPC_ACOP, 0);
8178 spr_register_kvm(env, SPR_BOOKS_PID, "PID",
8179 SPR_NOACCESS, SPR_NOACCESS,
8180 &spr_read_generic, &spr_write_generic,
8181 KVM_REG_PPC_PID, 0);
8182 #endif
8185 static void gen_spr_power8_rpr(CPUPPCState *env)
8187 #if !defined(CONFIG_USER_ONLY)
8188 spr_register_hv(env, SPR_RPR, "RPR",
8189 SPR_NOACCESS, SPR_NOACCESS,
8190 SPR_NOACCESS, SPR_NOACCESS,
8191 &spr_read_generic, &spr_write_generic,
8192 0x00000103070F1F3F);
8193 #endif
8196 static void gen_spr_power9_mmu(CPUPPCState *env)
8198 #if !defined(CONFIG_USER_ONLY)
8199 /* Partition Table Control */
8200 spr_register_hv(env, SPR_PTCR, "PTCR",
8201 SPR_NOACCESS, SPR_NOACCESS,
8202 SPR_NOACCESS, SPR_NOACCESS,
8203 &spr_read_generic, &spr_write_ptcr,
8204 0x00000000);
8205 #endif
8208 static void init_proc_book3s_common(CPUPPCState *env)
8210 gen_spr_ne_601(env);
8211 gen_tbl(env);
8212 gen_spr_usprg3(env);
8213 gen_spr_book3s_altivec(env);
8214 gen_spr_book3s_pmu_sup(env);
8215 gen_spr_book3s_pmu_user(env);
8216 gen_spr_book3s_ctrl(env);
8219 static void init_proc_970(CPUPPCState *env)
8221 /* Common Registers */
8222 init_proc_book3s_common(env);
8223 gen_spr_sdr1(env);
8224 gen_spr_book3s_dbg(env);
8226 /* 970 Specific Registers */
8227 gen_spr_970_hid(env);
8228 gen_spr_970_hior(env);
8229 gen_low_BATs(env);
8230 gen_spr_970_pmu_sup(env);
8231 gen_spr_970_pmu_user(env);
8232 gen_spr_970_lpar(env);
8233 gen_spr_970_dbg(env);
8235 /* env variables */
8236 env->dcache_line_size = 128;
8237 env->icache_line_size = 128;
8239 /* Allocate hardware IRQ controller */
8240 init_excp_970(env);
8241 ppc970_irq_init(ppc_env_get_cpu(env));
8244 POWERPC_FAMILY(970)(ObjectClass *oc, void *data)
8246 DeviceClass *dc = DEVICE_CLASS(oc);
8247 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
8249 dc->desc = "PowerPC 970";
8250 pcc->init_proc = init_proc_970;
8251 pcc->check_pow = check_pow_970;
8252 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
8253 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
8254 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
8255 PPC_FLOAT_STFIWX |
8256 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
8257 PPC_MEM_SYNC | PPC_MEM_EIEIO |
8258 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
8259 PPC_64B | PPC_ALTIVEC |
8260 PPC_SEGMENT_64B | PPC_SLBI;
8261 pcc->insns_flags2 = PPC2_FP_CVT_S64;
8262 pcc->msr_mask = (1ull << MSR_SF) |
8263 (1ull << MSR_VR) |
8264 (1ull << MSR_POW) |
8265 (1ull << MSR_EE) |
8266 (1ull << MSR_PR) |
8267 (1ull << MSR_FP) |
8268 (1ull << MSR_ME) |
8269 (1ull << MSR_FE0) |
8270 (1ull << MSR_SE) |
8271 (1ull << MSR_DE) |
8272 (1ull << MSR_FE1) |
8273 (1ull << MSR_IR) |
8274 (1ull << MSR_DR) |
8275 (1ull << MSR_PMM) |
8276 (1ull << MSR_RI);
8277 pcc->mmu_model = POWERPC_MMU_64B;
8278 #if defined(CONFIG_SOFTMMU)
8279 pcc->handle_mmu_fault = ppc_hash64_handle_mmu_fault;
8280 pcc->hash64_opts = &ppc_hash64_opts_basic;
8281 #endif
8282 pcc->excp_model = POWERPC_EXCP_970;
8283 pcc->bus_model = PPC_FLAGS_INPUT_970;
8284 pcc->bfd_mach = bfd_mach_ppc64;
8285 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
8286 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
8287 POWERPC_FLAG_BUS_CLK;
8288 pcc->l1_dcache_size = 0x8000;
8289 pcc->l1_icache_size = 0x10000;
8292 static void init_proc_power5plus(CPUPPCState *env)
8294 /* Common Registers */
8295 init_proc_book3s_common(env);
8296 gen_spr_sdr1(env);
8297 gen_spr_book3s_dbg(env);
8299 /* POWER5+ Specific Registers */
8300 gen_spr_970_hid(env);
8301 gen_spr_970_hior(env);
8302 gen_low_BATs(env);
8303 gen_spr_970_pmu_sup(env);
8304 gen_spr_970_pmu_user(env);
8305 gen_spr_power5p_common(env);
8306 gen_spr_power5p_lpar(env);
8307 gen_spr_power5p_ear(env);
8309 /* env variables */
8310 env->dcache_line_size = 128;
8311 env->icache_line_size = 128;
8313 /* Allocate hardware IRQ controller */
8314 init_excp_970(env);
8315 ppc970_irq_init(ppc_env_get_cpu(env));
8318 POWERPC_FAMILY(POWER5P)(ObjectClass *oc, void *data)
8320 DeviceClass *dc = DEVICE_CLASS(oc);
8321 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
8323 dc->fw_name = "PowerPC,POWER5";
8324 dc->desc = "POWER5+";
8325 pcc->init_proc = init_proc_power5plus;
8326 pcc->check_pow = check_pow_970;
8327 pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
8328 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
8329 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
8330 PPC_FLOAT_STFIWX |
8331 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
8332 PPC_MEM_SYNC | PPC_MEM_EIEIO |
8333 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
8334 PPC_64B |
8335 PPC_SEGMENT_64B | PPC_SLBI;
8336 pcc->insns_flags2 = PPC2_FP_CVT_S64;
8337 pcc->msr_mask = (1ull << MSR_SF) |
8338 (1ull << MSR_VR) |
8339 (1ull << MSR_POW) |
8340 (1ull << MSR_EE) |
8341 (1ull << MSR_PR) |
8342 (1ull << MSR_FP) |
8343 (1ull << MSR_ME) |
8344 (1ull << MSR_FE0) |
8345 (1ull << MSR_SE) |
8346 (1ull << MSR_DE) |
8347 (1ull << MSR_FE1) |
8348 (1ull << MSR_IR) |
8349 (1ull << MSR_DR) |
8350 (1ull << MSR_PMM) |
8351 (1ull << MSR_RI);
8352 pcc->mmu_model = POWERPC_MMU_2_03;
8353 #if defined(CONFIG_SOFTMMU)
8354 pcc->handle_mmu_fault = ppc_hash64_handle_mmu_fault;
8355 pcc->hash64_opts = &ppc_hash64_opts_basic;
8356 #endif
8357 pcc->excp_model = POWERPC_EXCP_970;
8358 pcc->bus_model = PPC_FLAGS_INPUT_970;
8359 pcc->bfd_mach = bfd_mach_ppc64;
8360 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
8361 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
8362 POWERPC_FLAG_BUS_CLK;
8363 pcc->l1_dcache_size = 0x8000;
8364 pcc->l1_icache_size = 0x10000;
8368 * The CPU used to have a "compat" property which set the
8369 * compatibility mode PVR. However, this was conceptually broken - it
8370 * only makes sense on the pseries machine type (otherwise the guest
8371 * owns the PCR and can control the compatibility mode itself). It's
8372 * been replaced with the 'max-cpu-compat' property on the pseries
8373 * machine type. For backwards compatibility, pseries specially
8374 * parses the -cpu parameter and converts old compat= parameters into
8375 * the appropriate machine parameters. This stub implementation of
8376 * the parameter catches any uses on explicitly created CPUs.
8378 static void getset_compat_deprecated(Object *obj, Visitor *v, const char *name,
8379 void *opaque, Error **errp)
8381 QNull *null = NULL;
8383 if (!qtest_enabled()) {
8384 error_report("CPU 'compat' property is deprecated and has no effect; "
8385 "use max-cpu-compat machine property instead");
8387 visit_type_null(v, name, &null, NULL);
8388 qobject_unref(null);
8391 static const PropertyInfo ppc_compat_deprecated_propinfo = {
8392 .name = "str",
8393 .description = "compatibility mode (deprecated)",
8394 .get = getset_compat_deprecated,
8395 .set = getset_compat_deprecated,
8397 static Property powerpc_servercpu_properties[] = {
8399 .name = "compat",
8400 .info = &ppc_compat_deprecated_propinfo,
8402 DEFINE_PROP_END_OF_LIST(),
8405 static void init_proc_POWER7(CPUPPCState *env)
8407 /* Common Registers */
8408 init_proc_book3s_common(env);
8409 gen_spr_sdr1(env);
8410 gen_spr_book3s_dbg(env);
8412 /* POWER7 Specific Registers */
8413 gen_spr_book3s_ids(env);
8414 gen_spr_amr(env);
8415 gen_spr_book3s_purr(env);
8416 gen_spr_power5p_common(env);
8417 gen_spr_power5p_lpar(env);
8418 gen_spr_power5p_ear(env);
8419 gen_spr_power6_common(env);
8420 gen_spr_power6_dbg(env);
8421 gen_spr_power7_book4(env);
8423 /* env variables */
8424 env->dcache_line_size = 128;
8425 env->icache_line_size = 128;
8427 /* Allocate hardware IRQ controller */
8428 init_excp_POWER7(env);
8429 ppcPOWER7_irq_init(ppc_env_get_cpu(env));
8432 static bool ppc_pvr_match_power7(PowerPCCPUClass *pcc, uint32_t pvr)
8434 if ((pvr & CPU_POWERPC_POWER_SERVER_MASK) == CPU_POWERPC_POWER7P_BASE) {
8435 return true;
8437 if ((pvr & CPU_POWERPC_POWER_SERVER_MASK) == CPU_POWERPC_POWER7_BASE) {
8438 return true;
8440 return false;
8443 static bool cpu_has_work_POWER7(CPUState *cs)
8445 PowerPCCPU *cpu = POWERPC_CPU(cs);
8446 CPUPPCState *env = &cpu->env;
8448 if (cs->halted) {
8449 if (!(cs->interrupt_request & CPU_INTERRUPT_HARD)) {
8450 return false;
8452 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_EXT)) &&
8453 (env->spr[SPR_LPCR] & LPCR_P7_PECE0)) {
8454 return true;
8456 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_DECR)) &&
8457 (env->spr[SPR_LPCR] & LPCR_P7_PECE1)) {
8458 return true;
8460 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_MCK)) &&
8461 (env->spr[SPR_LPCR] & LPCR_P7_PECE2)) {
8462 return true;
8464 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_HMI)) &&
8465 (env->spr[SPR_LPCR] & LPCR_P7_PECE2)) {
8466 return true;
8468 if (env->pending_interrupts & (1u << PPC_INTERRUPT_RESET)) {
8469 return true;
8471 return false;
8472 } else {
8473 return msr_ee && (cs->interrupt_request & CPU_INTERRUPT_HARD);
8477 POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data)
8479 DeviceClass *dc = DEVICE_CLASS(oc);
8480 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
8481 CPUClass *cc = CPU_CLASS(oc);
8483 dc->fw_name = "PowerPC,POWER7";
8484 dc->desc = "POWER7";
8485 dc->props = powerpc_servercpu_properties;
8486 pcc->pvr_match = ppc_pvr_match_power7;
8487 pcc->pcr_mask = PCR_VEC_DIS | PCR_VSX_DIS | PCR_COMPAT_2_05;
8488 pcc->pcr_supported = PCR_COMPAT_2_06 | PCR_COMPAT_2_05;
8489 pcc->init_proc = init_proc_POWER7;
8490 pcc->check_pow = check_pow_nocheck;
8491 cc->has_work = cpu_has_work_POWER7;
8492 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
8493 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
8494 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
8495 PPC_FLOAT_FRSQRTES |
8496 PPC_FLOAT_STFIWX |
8497 PPC_FLOAT_EXT |
8498 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
8499 PPC_MEM_SYNC | PPC_MEM_EIEIO |
8500 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
8501 PPC_64B | PPC_64H | PPC_64BX | PPC_ALTIVEC |
8502 PPC_SEGMENT_64B | PPC_SLBI |
8503 PPC_POPCNTB | PPC_POPCNTWD |
8504 PPC_CILDST;
8505 pcc->insns_flags2 = PPC2_VSX | PPC2_DFP | PPC2_DBRX | PPC2_ISA205 |
8506 PPC2_PERM_ISA206 | PPC2_DIVE_ISA206 |
8507 PPC2_ATOMIC_ISA206 | PPC2_FP_CVT_ISA206 |
8508 PPC2_FP_TST_ISA206 | PPC2_FP_CVT_S64 |
8509 PPC2_PM_ISA206;
8510 pcc->msr_mask = (1ull << MSR_SF) |
8511 (1ull << MSR_VR) |
8512 (1ull << MSR_VSX) |
8513 (1ull << MSR_EE) |
8514 (1ull << MSR_PR) |
8515 (1ull << MSR_FP) |
8516 (1ull << MSR_ME) |
8517 (1ull << MSR_FE0) |
8518 (1ull << MSR_SE) |
8519 (1ull << MSR_DE) |
8520 (1ull << MSR_FE1) |
8521 (1ull << MSR_IR) |
8522 (1ull << MSR_DR) |
8523 (1ull << MSR_PMM) |
8524 (1ull << MSR_RI) |
8525 (1ull << MSR_LE);
8526 pcc->mmu_model = POWERPC_MMU_2_06;
8527 #if defined(CONFIG_SOFTMMU)
8528 pcc->handle_mmu_fault = ppc_hash64_handle_mmu_fault;
8529 pcc->hash64_opts = &ppc_hash64_opts_POWER7;
8530 #endif
8531 pcc->excp_model = POWERPC_EXCP_POWER7;
8532 pcc->bus_model = PPC_FLAGS_INPUT_POWER7;
8533 pcc->bfd_mach = bfd_mach_ppc64;
8534 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
8535 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
8536 POWERPC_FLAG_BUS_CLK | POWERPC_FLAG_CFAR |
8537 POWERPC_FLAG_VSX;
8538 pcc->l1_dcache_size = 0x8000;
8539 pcc->l1_icache_size = 0x8000;
8540 pcc->interrupts_big_endian = ppc_cpu_interrupts_big_endian_lpcr;
8541 pcc->lpcr_pm = LPCR_P7_PECE0 | LPCR_P7_PECE1 | LPCR_P7_PECE2;
8544 static void init_proc_POWER8(CPUPPCState *env)
8546 /* Common Registers */
8547 init_proc_book3s_common(env);
8548 gen_spr_sdr1(env);
8549 gen_spr_book3s_207_dbg(env);
8551 /* POWER8 Specific Registers */
8552 gen_spr_book3s_ids(env);
8553 gen_spr_amr(env);
8554 gen_spr_iamr(env);
8555 gen_spr_book3s_purr(env);
8556 gen_spr_power5p_common(env);
8557 gen_spr_power5p_lpar(env);
8558 gen_spr_power5p_ear(env);
8559 gen_spr_power6_common(env);
8560 gen_spr_power6_dbg(env);
8561 gen_spr_power8_tce_address_control(env);
8562 gen_spr_power8_ids(env);
8563 gen_spr_power8_ebb(env);
8564 gen_spr_power8_fscr(env);
8565 gen_spr_power8_pmu_sup(env);
8566 gen_spr_power8_pmu_user(env);
8567 gen_spr_power8_tm(env);
8568 gen_spr_power8_pspb(env);
8569 gen_spr_vtb(env);
8570 gen_spr_power8_ic(env);
8571 gen_spr_power8_book4(env);
8572 gen_spr_power8_rpr(env);
8574 /* env variables */
8575 env->dcache_line_size = 128;
8576 env->icache_line_size = 128;
8578 /* Allocate hardware IRQ controller */
8579 init_excp_POWER8(env);
8580 ppcPOWER7_irq_init(ppc_env_get_cpu(env));
8583 static bool ppc_pvr_match_power8(PowerPCCPUClass *pcc, uint32_t pvr)
8585 if ((pvr & CPU_POWERPC_POWER_SERVER_MASK) == CPU_POWERPC_POWER8NVL_BASE) {
8586 return true;
8588 if ((pvr & CPU_POWERPC_POWER_SERVER_MASK) == CPU_POWERPC_POWER8E_BASE) {
8589 return true;
8591 if ((pvr & CPU_POWERPC_POWER_SERVER_MASK) == CPU_POWERPC_POWER8_BASE) {
8592 return true;
8594 return false;
8597 static bool cpu_has_work_POWER8(CPUState *cs)
8599 PowerPCCPU *cpu = POWERPC_CPU(cs);
8600 CPUPPCState *env = &cpu->env;
8602 if (cs->halted) {
8603 if (!(cs->interrupt_request & CPU_INTERRUPT_HARD)) {
8604 return false;
8606 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_EXT)) &&
8607 (env->spr[SPR_LPCR] & LPCR_P8_PECE2)) {
8608 return true;
8610 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_DECR)) &&
8611 (env->spr[SPR_LPCR] & LPCR_P8_PECE3)) {
8612 return true;
8614 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_MCK)) &&
8615 (env->spr[SPR_LPCR] & LPCR_P8_PECE4)) {
8616 return true;
8618 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_HMI)) &&
8619 (env->spr[SPR_LPCR] & LPCR_P8_PECE4)) {
8620 return true;
8622 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_DOORBELL)) &&
8623 (env->spr[SPR_LPCR] & LPCR_P8_PECE0)) {
8624 return true;
8626 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_HDOORBELL)) &&
8627 (env->spr[SPR_LPCR] & LPCR_P8_PECE1)) {
8628 return true;
8630 if (env->pending_interrupts & (1u << PPC_INTERRUPT_RESET)) {
8631 return true;
8633 return false;
8634 } else {
8635 return msr_ee && (cs->interrupt_request & CPU_INTERRUPT_HARD);
8639 POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data)
8641 DeviceClass *dc = DEVICE_CLASS(oc);
8642 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
8643 CPUClass *cc = CPU_CLASS(oc);
8645 dc->fw_name = "PowerPC,POWER8";
8646 dc->desc = "POWER8";
8647 dc->props = powerpc_servercpu_properties;
8648 pcc->pvr_match = ppc_pvr_match_power8;
8649 pcc->pcr_mask = PCR_TM_DIS | PCR_COMPAT_2_06 | PCR_COMPAT_2_05;
8650 pcc->pcr_supported = PCR_COMPAT_2_07 | PCR_COMPAT_2_06 | PCR_COMPAT_2_05;
8651 pcc->init_proc = init_proc_POWER8;
8652 pcc->check_pow = check_pow_nocheck;
8653 cc->has_work = cpu_has_work_POWER8;
8654 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
8655 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
8656 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
8657 PPC_FLOAT_FRSQRTES |
8658 PPC_FLOAT_STFIWX |
8659 PPC_FLOAT_EXT |
8660 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
8661 PPC_MEM_SYNC | PPC_MEM_EIEIO |
8662 PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
8663 PPC_64B | PPC_64H | PPC_64BX | PPC_ALTIVEC |
8664 PPC_SEGMENT_64B | PPC_SLBI |
8665 PPC_POPCNTB | PPC_POPCNTWD |
8666 PPC_CILDST;
8667 pcc->insns_flags2 = PPC2_VSX | PPC2_VSX207 | PPC2_DFP | PPC2_DBRX |
8668 PPC2_PERM_ISA206 | PPC2_DIVE_ISA206 |
8669 PPC2_ATOMIC_ISA206 | PPC2_FP_CVT_ISA206 |
8670 PPC2_FP_TST_ISA206 | PPC2_BCTAR_ISA207 |
8671 PPC2_LSQ_ISA207 | PPC2_ALTIVEC_207 |
8672 PPC2_ISA205 | PPC2_ISA207S | PPC2_FP_CVT_S64 |
8673 PPC2_TM | PPC2_PM_ISA206;
8674 pcc->msr_mask = (1ull << MSR_SF) |
8675 (1ull << MSR_SHV) |
8676 (1ull << MSR_TM) |
8677 (1ull << MSR_VR) |
8678 (1ull << MSR_VSX) |
8679 (1ull << MSR_EE) |
8680 (1ull << MSR_PR) |
8681 (1ull << MSR_FP) |
8682 (1ull << MSR_ME) |
8683 (1ull << MSR_FE0) |
8684 (1ull << MSR_SE) |
8685 (1ull << MSR_DE) |
8686 (1ull << MSR_FE1) |
8687 (1ull << MSR_IR) |
8688 (1ull << MSR_DR) |
8689 (1ull << MSR_PMM) |
8690 (1ull << MSR_RI) |
8691 (1ull << MSR_TS0) |
8692 (1ull << MSR_TS1) |
8693 (1ull << MSR_LE);
8694 pcc->mmu_model = POWERPC_MMU_2_07;
8695 #if defined(CONFIG_SOFTMMU)
8696 pcc->handle_mmu_fault = ppc_hash64_handle_mmu_fault;
8697 pcc->hash64_opts = &ppc_hash64_opts_POWER7;
8698 #endif
8699 pcc->excp_model = POWERPC_EXCP_POWER8;
8700 pcc->bus_model = PPC_FLAGS_INPUT_POWER7;
8701 pcc->bfd_mach = bfd_mach_ppc64;
8702 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
8703 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
8704 POWERPC_FLAG_BUS_CLK | POWERPC_FLAG_CFAR |
8705 POWERPC_FLAG_VSX | POWERPC_FLAG_TM;
8706 pcc->l1_dcache_size = 0x8000;
8707 pcc->l1_icache_size = 0x8000;
8708 pcc->interrupts_big_endian = ppc_cpu_interrupts_big_endian_lpcr;
8709 pcc->lpcr_pm = LPCR_P8_PECE0 | LPCR_P8_PECE1 | LPCR_P8_PECE2 |
8710 LPCR_P8_PECE3 | LPCR_P8_PECE4;
8713 #ifdef CONFIG_SOFTMMU
8715 * Radix pg sizes and AP encodings for dt node ibm,processor-radix-AP-encodings
8716 * Encoded as array of int_32s in the form:
8717 * 0bxxxyyyyyyyyyyyyyyyyyyyyyyyyyyyyy
8718 * x -> AP encoding
8719 * y -> radix mode supported page size (encoded as a shift)
8721 static struct ppc_radix_page_info POWER9_radix_page_info = {
8722 .count = 4,
8723 .entries = {
8724 0x0000000c, /* 4K - enc: 0x0 */
8725 0xa0000010, /* 64K - enc: 0x5 */
8726 0x20000015, /* 2M - enc: 0x1 */
8727 0x4000001e /* 1G - enc: 0x2 */
8730 #endif /* CONFIG_SOFTMMU */
8732 static void init_proc_POWER9(CPUPPCState *env)
8734 /* Common Registers */
8735 init_proc_book3s_common(env);
8736 gen_spr_book3s_207_dbg(env);
8738 /* POWER8 Specific Registers */
8739 gen_spr_book3s_ids(env);
8740 gen_spr_amr(env);
8741 gen_spr_iamr(env);
8742 gen_spr_book3s_purr(env);
8743 gen_spr_power5p_common(env);
8744 gen_spr_power5p_lpar(env);
8745 gen_spr_power5p_ear(env);
8746 gen_spr_power6_common(env);
8747 gen_spr_power6_dbg(env);
8748 gen_spr_power8_tce_address_control(env);
8749 gen_spr_power8_ids(env);
8750 gen_spr_power8_ebb(env);
8751 gen_spr_power8_fscr(env);
8752 gen_spr_power8_pmu_sup(env);
8753 gen_spr_power8_pmu_user(env);
8754 gen_spr_power8_tm(env);
8755 gen_spr_power8_pspb(env);
8756 gen_spr_vtb(env);
8757 gen_spr_power8_ic(env);
8758 gen_spr_power8_book4(env);
8759 gen_spr_power8_rpr(env);
8760 gen_spr_power9_mmu(env);
8762 /* POWER9 Specific registers */
8763 spr_register_kvm(env, SPR_TIDR, "TIDR", NULL, NULL,
8764 spr_read_generic, spr_write_generic,
8765 KVM_REG_PPC_TIDR, 0);
8767 /* FIXME: Filter fields properly based on privilege level */
8768 spr_register_kvm_hv(env, SPR_PSSCR, "PSSCR", NULL, NULL, NULL, NULL,
8769 spr_read_generic, spr_write_generic,
8770 KVM_REG_PPC_PSSCR, 0);
8772 /* env variables */
8773 env->dcache_line_size = 128;
8774 env->icache_line_size = 128;
8776 /* Allocate hardware IRQ controller */
8777 init_excp_POWER8(env);
8778 ppcPOWER7_irq_init(ppc_env_get_cpu(env));
8781 static bool ppc_pvr_match_power9(PowerPCCPUClass *pcc, uint32_t pvr)
8783 if ((pvr & CPU_POWERPC_POWER_SERVER_MASK) == CPU_POWERPC_POWER9_BASE) {
8784 return true;
8786 return false;
8789 static bool cpu_has_work_POWER9(CPUState *cs)
8791 PowerPCCPU *cpu = POWERPC_CPU(cs);
8792 CPUPPCState *env = &cpu->env;
8794 if (cs->halted) {
8795 if (!(cs->interrupt_request & CPU_INTERRUPT_HARD)) {
8796 return false;
8798 /* External Exception */
8799 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_EXT)) &&
8800 (env->spr[SPR_LPCR] & LPCR_EEE)) {
8801 return true;
8803 /* Decrementer Exception */
8804 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_DECR)) &&
8805 (env->spr[SPR_LPCR] & LPCR_DEE)) {
8806 return true;
8808 /* Machine Check or Hypervisor Maintenance Exception */
8809 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_MCK |
8810 1u << PPC_INTERRUPT_HMI)) && (env->spr[SPR_LPCR] & LPCR_OEE)) {
8811 return true;
8813 /* Privileged Doorbell Exception */
8814 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_DOORBELL)) &&
8815 (env->spr[SPR_LPCR] & LPCR_PDEE)) {
8816 return true;
8818 /* Hypervisor Doorbell Exception */
8819 if ((env->pending_interrupts & (1u << PPC_INTERRUPT_HDOORBELL)) &&
8820 (env->spr[SPR_LPCR] & LPCR_HDEE)) {
8821 return true;
8823 if (env->pending_interrupts & (1u << PPC_INTERRUPT_RESET)) {
8824 return true;
8826 return false;
8827 } else {
8828 return msr_ee && (cs->interrupt_request & CPU_INTERRUPT_HARD);
8832 POWERPC_FAMILY(POWER9)(ObjectClass *oc, void *data)
8834 DeviceClass *dc = DEVICE_CLASS(oc);
8835 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
8836 CPUClass *cc = CPU_CLASS(oc);
8838 dc->fw_name = "PowerPC,POWER9";
8839 dc->desc = "POWER9";
8840 dc->props = powerpc_servercpu_properties;
8841 pcc->pvr_match = ppc_pvr_match_power9;
8842 pcc->pcr_mask = PCR_COMPAT_2_05 | PCR_COMPAT_2_06 | PCR_COMPAT_2_07;
8843 pcc->pcr_supported = PCR_COMPAT_3_00 | PCR_COMPAT_2_07 | PCR_COMPAT_2_06 |
8844 PCR_COMPAT_2_05;
8845 pcc->init_proc = init_proc_POWER9;
8846 pcc->check_pow = check_pow_nocheck;
8847 cc->has_work = cpu_has_work_POWER9;
8848 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
8849 PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
8850 PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
8851 PPC_FLOAT_FRSQRTES |
8852 PPC_FLOAT_STFIWX |
8853 PPC_FLOAT_EXT |
8854 PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
8855 PPC_MEM_SYNC | PPC_MEM_EIEIO |
8856 PPC_MEM_TLBSYNC |
8857 PPC_64B | PPC_64BX | PPC_ALTIVEC |
8858 PPC_SEGMENT_64B | PPC_SLBI |
8859 PPC_POPCNTB | PPC_POPCNTWD |
8860 PPC_CILDST;
8861 pcc->insns_flags2 = PPC2_VSX | PPC2_VSX207 | PPC2_DFP | PPC2_DBRX |
8862 PPC2_PERM_ISA206 | PPC2_DIVE_ISA206 |
8863 PPC2_ATOMIC_ISA206 | PPC2_FP_CVT_ISA206 |
8864 PPC2_FP_TST_ISA206 | PPC2_BCTAR_ISA207 |
8865 PPC2_LSQ_ISA207 | PPC2_ALTIVEC_207 |
8866 PPC2_ISA205 | PPC2_ISA207S | PPC2_FP_CVT_S64 |
8867 PPC2_TM | PPC2_PM_ISA206 | PPC2_ISA300 | PPC2_PRCNTL;
8868 pcc->msr_mask = (1ull << MSR_SF) |
8869 (1ull << MSR_TM) |
8870 (1ull << MSR_VR) |
8871 (1ull << MSR_VSX) |
8872 (1ull << MSR_EE) |
8873 (1ull << MSR_PR) |
8874 (1ull << MSR_FP) |
8875 (1ull << MSR_ME) |
8876 (1ull << MSR_FE0) |
8877 (1ull << MSR_SE) |
8878 (1ull << MSR_DE) |
8879 (1ull << MSR_FE1) |
8880 (1ull << MSR_IR) |
8881 (1ull << MSR_DR) |
8882 (1ull << MSR_PMM) |
8883 (1ull << MSR_RI) |
8884 (1ull << MSR_LE);
8885 pcc->mmu_model = POWERPC_MMU_3_00;
8886 #if defined(CONFIG_SOFTMMU)
8887 pcc->handle_mmu_fault = ppc64_v3_handle_mmu_fault;
8888 /* segment page size remain the same */
8889 pcc->hash64_opts = &ppc_hash64_opts_POWER7;
8890 pcc->radix_page_info = &POWER9_radix_page_info;
8891 #endif
8892 pcc->excp_model = POWERPC_EXCP_POWER8;
8893 pcc->bus_model = PPC_FLAGS_INPUT_POWER7;
8894 pcc->bfd_mach = bfd_mach_ppc64;
8895 pcc->flags = POWERPC_FLAG_VRE | POWERPC_FLAG_SE |
8896 POWERPC_FLAG_BE | POWERPC_FLAG_PMM |
8897 POWERPC_FLAG_BUS_CLK | POWERPC_FLAG_CFAR |
8898 POWERPC_FLAG_VSX | POWERPC_FLAG_TM;
8899 pcc->l1_dcache_size = 0x8000;
8900 pcc->l1_icache_size = 0x8000;
8901 pcc->interrupts_big_endian = ppc_cpu_interrupts_big_endian_lpcr;
8902 pcc->lpcr_pm = LPCR_PDEE | LPCR_HDEE | LPCR_EEE | LPCR_DEE | LPCR_OEE;
8905 #if !defined(CONFIG_USER_ONLY)
8906 void cpu_ppc_set_vhyp(PowerPCCPU *cpu, PPCVirtualHypervisor *vhyp)
8908 CPUPPCState *env = &cpu->env;
8910 cpu->vhyp = vhyp;
8913 * With a virtual hypervisor mode we never allow the CPU to go
8914 * hypervisor mode itself
8916 env->msr_mask &= ~MSR_HVB;
8919 #endif /* !defined(CONFIG_USER_ONLY) */
8921 #endif /* defined(TARGET_PPC64) */
8923 /*****************************************************************************/
8924 /* Generic CPU instantiation routine */
8925 static void init_ppc_proc(PowerPCCPU *cpu)
8927 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
8928 CPUPPCState *env = &cpu->env;
8929 #if !defined(CONFIG_USER_ONLY)
8930 int i;
8932 env->irq_inputs = NULL;
8933 /* Set all exception vectors to an invalid address */
8934 for (i = 0; i < POWERPC_EXCP_NB; i++)
8935 env->excp_vectors[i] = (target_ulong)(-1ULL);
8936 env->ivor_mask = 0x00000000;
8937 env->ivpr_mask = 0x00000000;
8938 /* Default MMU definitions */
8939 env->nb_BATs = 0;
8940 env->nb_tlb = 0;
8941 env->nb_ways = 0;
8942 env->tlb_type = TLB_NONE;
8943 #endif
8944 /* Register SPR common to all PowerPC implementations */
8945 gen_spr_generic(env);
8946 spr_register(env, SPR_PVR, "PVR",
8947 /* Linux permits userspace to read PVR */
8948 #if defined(CONFIG_LINUX_USER)
8949 &spr_read_generic,
8950 #else
8951 SPR_NOACCESS,
8952 #endif
8953 SPR_NOACCESS,
8954 &spr_read_generic, SPR_NOACCESS,
8955 pcc->pvr);
8956 /* Register SVR if it's defined to anything else than POWERPC_SVR_NONE */
8957 if (pcc->svr != POWERPC_SVR_NONE) {
8958 if (pcc->svr & POWERPC_SVR_E500) {
8959 spr_register(env, SPR_E500_SVR, "SVR",
8960 SPR_NOACCESS, SPR_NOACCESS,
8961 &spr_read_generic, SPR_NOACCESS,
8962 pcc->svr & ~POWERPC_SVR_E500);
8963 } else {
8964 spr_register(env, SPR_SVR, "SVR",
8965 SPR_NOACCESS, SPR_NOACCESS,
8966 &spr_read_generic, SPR_NOACCESS,
8967 pcc->svr);
8970 /* PowerPC implementation specific initialisations (SPRs, timers, ...) */
8971 (*pcc->init_proc)(env);
8973 /* MSR bits & flags consistency checks */
8974 if (env->msr_mask & (1 << 25)) {
8975 switch (env->flags & (POWERPC_FLAG_SPE | POWERPC_FLAG_VRE)) {
8976 case POWERPC_FLAG_SPE:
8977 case POWERPC_FLAG_VRE:
8978 break;
8979 default:
8980 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8981 "Should define POWERPC_FLAG_SPE or POWERPC_FLAG_VRE\n");
8982 exit(1);
8984 } else if (env->flags & (POWERPC_FLAG_SPE | POWERPC_FLAG_VRE)) {
8985 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8986 "Should not define POWERPC_FLAG_SPE nor POWERPC_FLAG_VRE\n");
8987 exit(1);
8989 if (env->msr_mask & (1 << 17)) {
8990 switch (env->flags & (POWERPC_FLAG_TGPR | POWERPC_FLAG_CE)) {
8991 case POWERPC_FLAG_TGPR:
8992 case POWERPC_FLAG_CE:
8993 break;
8994 default:
8995 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
8996 "Should define POWERPC_FLAG_TGPR or POWERPC_FLAG_CE\n");
8997 exit(1);
8999 } else if (env->flags & (POWERPC_FLAG_TGPR | POWERPC_FLAG_CE)) {
9000 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
9001 "Should not define POWERPC_FLAG_TGPR nor POWERPC_FLAG_CE\n");
9002 exit(1);
9004 if (env->msr_mask & (1 << 10)) {
9005 switch (env->flags & (POWERPC_FLAG_SE | POWERPC_FLAG_DWE |
9006 POWERPC_FLAG_UBLE)) {
9007 case POWERPC_FLAG_SE:
9008 case POWERPC_FLAG_DWE:
9009 case POWERPC_FLAG_UBLE:
9010 break;
9011 default:
9012 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
9013 "Should define POWERPC_FLAG_SE or POWERPC_FLAG_DWE or "
9014 "POWERPC_FLAG_UBLE\n");
9015 exit(1);
9017 } else if (env->flags & (POWERPC_FLAG_SE | POWERPC_FLAG_DWE |
9018 POWERPC_FLAG_UBLE)) {
9019 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
9020 "Should not define POWERPC_FLAG_SE nor POWERPC_FLAG_DWE nor "
9021 "POWERPC_FLAG_UBLE\n");
9022 exit(1);
9024 if (env->msr_mask & (1 << 9)) {
9025 switch (env->flags & (POWERPC_FLAG_BE | POWERPC_FLAG_DE)) {
9026 case POWERPC_FLAG_BE:
9027 case POWERPC_FLAG_DE:
9028 break;
9029 default:
9030 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
9031 "Should define POWERPC_FLAG_BE or POWERPC_FLAG_DE\n");
9032 exit(1);
9034 } else if (env->flags & (POWERPC_FLAG_BE | POWERPC_FLAG_DE)) {
9035 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
9036 "Should not define POWERPC_FLAG_BE nor POWERPC_FLAG_DE\n");
9037 exit(1);
9039 if (env->msr_mask & (1 << 2)) {
9040 switch (env->flags & (POWERPC_FLAG_PX | POWERPC_FLAG_PMM)) {
9041 case POWERPC_FLAG_PX:
9042 case POWERPC_FLAG_PMM:
9043 break;
9044 default:
9045 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
9046 "Should define POWERPC_FLAG_PX or POWERPC_FLAG_PMM\n");
9047 exit(1);
9049 } else if (env->flags & (POWERPC_FLAG_PX | POWERPC_FLAG_PMM)) {
9050 fprintf(stderr, "PowerPC MSR definition inconsistency\n"
9051 "Should not define POWERPC_FLAG_PX nor POWERPC_FLAG_PMM\n");
9052 exit(1);
9054 if ((env->flags & (POWERPC_FLAG_RTC_CLK | POWERPC_FLAG_BUS_CLK)) == 0) {
9055 fprintf(stderr, "PowerPC flags inconsistency\n"
9056 "Should define the time-base and decrementer clock source\n");
9057 exit(1);
9059 /* Allocate TLBs buffer when needed */
9060 #if !defined(CONFIG_USER_ONLY)
9061 if (env->nb_tlb != 0) {
9062 int nb_tlb = env->nb_tlb;
9063 if (env->id_tlbs != 0)
9064 nb_tlb *= 2;
9065 switch (env->tlb_type) {
9066 case TLB_6XX:
9067 env->tlb.tlb6 = g_malloc0(nb_tlb * sizeof(ppc6xx_tlb_t));
9068 break;
9069 case TLB_EMB:
9070 env->tlb.tlbe = g_malloc0(nb_tlb * sizeof(ppcemb_tlb_t));
9071 break;
9072 case TLB_MAS:
9073 env->tlb.tlbm = g_malloc0(nb_tlb * sizeof(ppcmas_tlb_t));
9074 break;
9076 /* Pre-compute some useful values */
9077 env->tlb_per_way = env->nb_tlb / env->nb_ways;
9079 if (env->irq_inputs == NULL) {
9080 warn_report("no internal IRQ controller registered."
9081 " Attempt QEMU to crash very soon !");
9083 #endif
9084 if (env->check_pow == NULL) {
9085 warn_report("no power management check handler registered."
9086 " Attempt QEMU to crash very soon !");
9090 #if defined(PPC_DUMP_CPU)
9091 static void dump_ppc_sprs(CPUPPCState *env)
9093 ppc_spr_t *spr;
9094 #if !defined(CONFIG_USER_ONLY)
9095 uint32_t sr, sw;
9096 #endif
9097 uint32_t ur, uw;
9098 int i, j, n;
9100 printf("Special purpose registers:\n");
9101 for (i = 0; i < 32; i++) {
9102 for (j = 0; j < 32; j++) {
9103 n = (i << 5) | j;
9104 spr = &env->spr_cb[n];
9105 uw = spr->uea_write != NULL && spr->uea_write != SPR_NOACCESS;
9106 ur = spr->uea_read != NULL && spr->uea_read != SPR_NOACCESS;
9107 #if !defined(CONFIG_USER_ONLY)
9108 sw = spr->oea_write != NULL && spr->oea_write != SPR_NOACCESS;
9109 sr = spr->oea_read != NULL && spr->oea_read != SPR_NOACCESS;
9110 if (sw || sr || uw || ur) {
9111 printf("SPR: %4d (%03x) %-8s s%c%c u%c%c\n",
9112 (i << 5) | j, (i << 5) | j, spr->name,
9113 sw ? 'w' : '-', sr ? 'r' : '-',
9114 uw ? 'w' : '-', ur ? 'r' : '-');
9116 #else
9117 if (uw || ur) {
9118 printf("SPR: %4d (%03x) %-8s u%c%c\n",
9119 (i << 5) | j, (i << 5) | j, spr->name,
9120 uw ? 'w' : '-', ur ? 'r' : '-');
9122 #endif
9125 fflush(stdout);
9126 fflush(stderr);
9128 #endif
9130 /*****************************************************************************/
9132 /* Opcode types */
9133 enum {
9134 PPC_DIRECT = 0, /* Opcode routine */
9135 PPC_INDIRECT = 1, /* Indirect opcode table */
9138 #define PPC_OPCODE_MASK 0x3
9140 static inline int is_indirect_opcode(void *handler)
9142 return ((uintptr_t)handler & PPC_OPCODE_MASK) == PPC_INDIRECT;
9145 static inline opc_handler_t **ind_table(void *handler)
9147 return (opc_handler_t **)((uintptr_t)handler & ~PPC_OPCODE_MASK);
9150 /* Instruction table creation */
9151 /* Opcodes tables creation */
9152 static void fill_new_table(opc_handler_t **table, int len)
9154 int i;
9156 for (i = 0; i < len; i++)
9157 table[i] = &invalid_handler;
9160 static int create_new_table(opc_handler_t **table, unsigned char idx)
9162 opc_handler_t **tmp;
9164 tmp = g_new(opc_handler_t *, PPC_CPU_INDIRECT_OPCODES_LEN);
9165 fill_new_table(tmp, PPC_CPU_INDIRECT_OPCODES_LEN);
9166 table[idx] = (opc_handler_t *)((uintptr_t)tmp | PPC_INDIRECT);
9168 return 0;
9171 static int insert_in_table(opc_handler_t **table, unsigned char idx,
9172 opc_handler_t *handler)
9174 if (table[idx] != &invalid_handler)
9175 return -1;
9176 table[idx] = handler;
9178 return 0;
9181 static int register_direct_insn(opc_handler_t **ppc_opcodes,
9182 unsigned char idx, opc_handler_t *handler)
9184 if (insert_in_table(ppc_opcodes, idx, handler) < 0) {
9185 printf("*** ERROR: opcode %02x already assigned in main "
9186 "opcode table\n", idx);
9187 #if defined(DO_PPC_STATISTICS) || defined(PPC_DUMP_CPU)
9188 printf(" Registered handler '%s' - new handler '%s'\n",
9189 ppc_opcodes[idx]->oname, handler->oname);
9190 #endif
9191 return -1;
9194 return 0;
9197 static int register_ind_in_table(opc_handler_t **table,
9198 unsigned char idx1, unsigned char idx2,
9199 opc_handler_t *handler)
9201 if (table[idx1] == &invalid_handler) {
9202 if (create_new_table(table, idx1) < 0) {
9203 printf("*** ERROR: unable to create indirect table "
9204 "idx=%02x\n", idx1);
9205 return -1;
9207 } else {
9208 if (!is_indirect_opcode(table[idx1])) {
9209 printf("*** ERROR: idx %02x already assigned to a direct "
9210 "opcode\n", idx1);
9211 #if defined(DO_PPC_STATISTICS) || defined(PPC_DUMP_CPU)
9212 printf(" Registered handler '%s' - new handler '%s'\n",
9213 ind_table(table[idx1])[idx2]->oname, handler->oname);
9214 #endif
9215 return -1;
9218 if (handler != NULL &&
9219 insert_in_table(ind_table(table[idx1]), idx2, handler) < 0) {
9220 printf("*** ERROR: opcode %02x already assigned in "
9221 "opcode table %02x\n", idx2, idx1);
9222 #if defined(DO_PPC_STATISTICS) || defined(PPC_DUMP_CPU)
9223 printf(" Registered handler '%s' - new handler '%s'\n",
9224 ind_table(table[idx1])[idx2]->oname, handler->oname);
9225 #endif
9226 return -1;
9229 return 0;
9232 static int register_ind_insn(opc_handler_t **ppc_opcodes,
9233 unsigned char idx1, unsigned char idx2,
9234 opc_handler_t *handler)
9236 return register_ind_in_table(ppc_opcodes, idx1, idx2, handler);
9239 static int register_dblind_insn(opc_handler_t **ppc_opcodes,
9240 unsigned char idx1, unsigned char idx2,
9241 unsigned char idx3, opc_handler_t *handler)
9243 if (register_ind_in_table(ppc_opcodes, idx1, idx2, NULL) < 0) {
9244 printf("*** ERROR: unable to join indirect table idx "
9245 "[%02x-%02x]\n", idx1, idx2);
9246 return -1;
9248 if (register_ind_in_table(ind_table(ppc_opcodes[idx1]), idx2, idx3,
9249 handler) < 0) {
9250 printf("*** ERROR: unable to insert opcode "
9251 "[%02x-%02x-%02x]\n", idx1, idx2, idx3);
9252 return -1;
9255 return 0;
9258 static int register_trplind_insn(opc_handler_t **ppc_opcodes,
9259 unsigned char idx1, unsigned char idx2,
9260 unsigned char idx3, unsigned char idx4,
9261 opc_handler_t *handler)
9263 opc_handler_t **table;
9265 if (register_ind_in_table(ppc_opcodes, idx1, idx2, NULL) < 0) {
9266 printf("*** ERROR: unable to join indirect table idx "
9267 "[%02x-%02x]\n", idx1, idx2);
9268 return -1;
9270 table = ind_table(ppc_opcodes[idx1]);
9271 if (register_ind_in_table(table, idx2, idx3, NULL) < 0) {
9272 printf("*** ERROR: unable to join 2nd-level indirect table idx "
9273 "[%02x-%02x-%02x]\n", idx1, idx2, idx3);
9274 return -1;
9276 table = ind_table(table[idx2]);
9277 if (register_ind_in_table(table, idx3, idx4, handler) < 0) {
9278 printf("*** ERROR: unable to insert opcode "
9279 "[%02x-%02x-%02x-%02x]\n", idx1, idx2, idx3, idx4);
9280 return -1;
9282 return 0;
9284 static int register_insn(opc_handler_t **ppc_opcodes, opcode_t *insn)
9286 if (insn->opc2 != 0xFF) {
9287 if (insn->opc3 != 0xFF) {
9288 if (insn->opc4 != 0xFF) {
9289 if (register_trplind_insn(ppc_opcodes, insn->opc1, insn->opc2,
9290 insn->opc3, insn->opc4,
9291 &insn->handler) < 0) {
9292 return -1;
9294 } else {
9295 if (register_dblind_insn(ppc_opcodes, insn->opc1, insn->opc2,
9296 insn->opc3, &insn->handler) < 0)
9297 return -1;
9299 } else {
9300 if (register_ind_insn(ppc_opcodes, insn->opc1,
9301 insn->opc2, &insn->handler) < 0)
9302 return -1;
9304 } else {
9305 if (register_direct_insn(ppc_opcodes, insn->opc1, &insn->handler) < 0)
9306 return -1;
9309 return 0;
9312 static int test_opcode_table(opc_handler_t **table, int len)
9314 int i, count, tmp;
9316 for (i = 0, count = 0; i < len; i++) {
9317 /* Consistency fixup */
9318 if (table[i] == NULL)
9319 table[i] = &invalid_handler;
9320 if (table[i] != &invalid_handler) {
9321 if (is_indirect_opcode(table[i])) {
9322 tmp = test_opcode_table(ind_table(table[i]),
9323 PPC_CPU_INDIRECT_OPCODES_LEN);
9324 if (tmp == 0) {
9325 free(table[i]);
9326 table[i] = &invalid_handler;
9327 } else {
9328 count++;
9330 } else {
9331 count++;
9336 return count;
9339 static void fix_opcode_tables(opc_handler_t **ppc_opcodes)
9341 if (test_opcode_table(ppc_opcodes, PPC_CPU_OPCODES_LEN) == 0)
9342 printf("*** WARNING: no opcode defined !\n");
9345 /*****************************************************************************/
9346 static void create_ppc_opcodes(PowerPCCPU *cpu, Error **errp)
9348 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
9349 CPUPPCState *env = &cpu->env;
9350 opcode_t *opc;
9352 fill_new_table(env->opcodes, PPC_CPU_OPCODES_LEN);
9353 for (opc = opcodes; opc < &opcodes[ARRAY_SIZE(opcodes)]; opc++) {
9354 if (((opc->handler.type & pcc->insns_flags) != 0) ||
9355 ((opc->handler.type2 & pcc->insns_flags2) != 0)) {
9356 if (register_insn(env->opcodes, opc) < 0) {
9357 error_setg(errp, "ERROR initializing PowerPC instruction "
9358 "0x%02x 0x%02x 0x%02x", opc->opc1, opc->opc2,
9359 opc->opc3);
9360 return;
9364 fix_opcode_tables(env->opcodes);
9365 fflush(stdout);
9366 fflush(stderr);
9369 #if defined(PPC_DUMP_CPU)
9370 static void dump_ppc_insns(CPUPPCState *env)
9372 opc_handler_t **table, *handler;
9373 const char *p, *q;
9374 uint8_t opc1, opc2, opc3, opc4;
9376 printf("Instructions set:\n");
9377 /* opc1 is 6 bits long */
9378 for (opc1 = 0x00; opc1 < PPC_CPU_OPCODES_LEN; opc1++) {
9379 table = env->opcodes;
9380 handler = table[opc1];
9381 if (is_indirect_opcode(handler)) {
9382 /* opc2 is 5 bits long */
9383 for (opc2 = 0; opc2 < PPC_CPU_INDIRECT_OPCODES_LEN; opc2++) {
9384 table = env->opcodes;
9385 handler = env->opcodes[opc1];
9386 table = ind_table(handler);
9387 handler = table[opc2];
9388 if (is_indirect_opcode(handler)) {
9389 table = ind_table(handler);
9390 /* opc3 is 5 bits long */
9391 for (opc3 = 0; opc3 < PPC_CPU_INDIRECT_OPCODES_LEN;
9392 opc3++) {
9393 handler = table[opc3];
9394 if (is_indirect_opcode(handler)) {
9395 table = ind_table(handler);
9396 /* opc4 is 5 bits long */
9397 for (opc4 = 0; opc4 < PPC_CPU_INDIRECT_OPCODES_LEN;
9398 opc4++) {
9399 handler = table[opc4];
9400 if (handler->handler != &gen_invalid) {
9401 printf("INSN: %02x %02x %02x %02x -- "
9402 "(%02d %04d %02d) : %s\n",
9403 opc1, opc2, opc3, opc4,
9404 opc1, (opc3 << 5) | opc2, opc4,
9405 handler->oname);
9408 } else {
9409 if (handler->handler != &gen_invalid) {
9410 /* Special hack to properly dump SPE insns */
9411 p = strchr(handler->oname, '_');
9412 if (p == NULL) {
9413 printf("INSN: %02x %02x %02x (%02d %04d) : "
9414 "%s\n",
9415 opc1, opc2, opc3, opc1,
9416 (opc3 << 5) | opc2,
9417 handler->oname);
9418 } else {
9419 q = "speundef";
9420 if ((p - handler->oname) != strlen(q)
9421 || (memcmp(handler->oname, q, strlen(q))
9422 != 0)) {
9423 /* First instruction */
9424 printf("INSN: %02x %02x %02x"
9425 "(%02d %04d) : %.*s\n",
9426 opc1, opc2 << 1, opc3, opc1,
9427 (opc3 << 6) | (opc2 << 1),
9428 (int)(p - handler->oname),
9429 handler->oname);
9431 if (strcmp(p + 1, q) != 0) {
9432 /* Second instruction */
9433 printf("INSN: %02x %02x %02x "
9434 "(%02d %04d) : %s\n", opc1,
9435 (opc2 << 1) | 1, opc3, opc1,
9436 (opc3 << 6) | (opc2 << 1) | 1,
9437 p + 1);
9443 } else {
9444 if (handler->handler != &gen_invalid) {
9445 printf("INSN: %02x %02x -- (%02d %04d) : %s\n",
9446 opc1, opc2, opc1, opc2, handler->oname);
9450 } else {
9451 if (handler->handler != &gen_invalid) {
9452 printf("INSN: %02x -- -- (%02d ----) : %s\n",
9453 opc1, opc1, handler->oname);
9458 #endif
9460 static bool avr_need_swap(CPUPPCState *env)
9462 #ifdef HOST_WORDS_BIGENDIAN
9463 return msr_le;
9464 #else
9465 return !msr_le;
9466 #endif
9469 static int gdb_get_float_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
9471 if (n < 32) {
9472 stfq_p(mem_buf, env->fpr[n]);
9473 ppc_maybe_bswap_register(env, mem_buf, 8);
9474 return 8;
9476 if (n == 32) {
9477 stl_p(mem_buf, env->fpscr);
9478 ppc_maybe_bswap_register(env, mem_buf, 4);
9479 return 4;
9481 return 0;
9484 static int gdb_set_float_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
9486 if (n < 32) {
9487 ppc_maybe_bswap_register(env, mem_buf, 8);
9488 env->fpr[n] = ldfq_p(mem_buf);
9489 return 8;
9491 if (n == 32) {
9492 ppc_maybe_bswap_register(env, mem_buf, 4);
9493 helper_store_fpscr(env, ldl_p(mem_buf), 0xffffffff);
9494 return 4;
9496 return 0;
9499 static int gdb_get_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
9501 if (n < 32) {
9502 if (!avr_need_swap(env)) {
9503 stq_p(mem_buf, env->avr[n].u64[0]);
9504 stq_p(mem_buf+8, env->avr[n].u64[1]);
9505 } else {
9506 stq_p(mem_buf, env->avr[n].u64[1]);
9507 stq_p(mem_buf+8, env->avr[n].u64[0]);
9509 ppc_maybe_bswap_register(env, mem_buf, 8);
9510 ppc_maybe_bswap_register(env, mem_buf + 8, 8);
9511 return 16;
9513 if (n == 32) {
9514 stl_p(mem_buf, env->vscr);
9515 ppc_maybe_bswap_register(env, mem_buf, 4);
9516 return 4;
9518 if (n == 33) {
9519 stl_p(mem_buf, (uint32_t)env->spr[SPR_VRSAVE]);
9520 ppc_maybe_bswap_register(env, mem_buf, 4);
9521 return 4;
9523 return 0;
9526 static int gdb_set_avr_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
9528 if (n < 32) {
9529 ppc_maybe_bswap_register(env, mem_buf, 8);
9530 ppc_maybe_bswap_register(env, mem_buf + 8, 8);
9531 if (!avr_need_swap(env)) {
9532 env->avr[n].u64[0] = ldq_p(mem_buf);
9533 env->avr[n].u64[1] = ldq_p(mem_buf+8);
9534 } else {
9535 env->avr[n].u64[1] = ldq_p(mem_buf);
9536 env->avr[n].u64[0] = ldq_p(mem_buf+8);
9538 return 16;
9540 if (n == 32) {
9541 ppc_maybe_bswap_register(env, mem_buf, 4);
9542 env->vscr = ldl_p(mem_buf);
9543 return 4;
9545 if (n == 33) {
9546 ppc_maybe_bswap_register(env, mem_buf, 4);
9547 env->spr[SPR_VRSAVE] = (target_ulong)ldl_p(mem_buf);
9548 return 4;
9550 return 0;
9553 static int gdb_get_spe_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
9555 if (n < 32) {
9556 #if defined(TARGET_PPC64)
9557 stl_p(mem_buf, env->gpr[n] >> 32);
9558 ppc_maybe_bswap_register(env, mem_buf, 4);
9559 #else
9560 stl_p(mem_buf, env->gprh[n]);
9561 #endif
9562 return 4;
9564 if (n == 32) {
9565 stq_p(mem_buf, env->spe_acc);
9566 ppc_maybe_bswap_register(env, mem_buf, 8);
9567 return 8;
9569 if (n == 33) {
9570 stl_p(mem_buf, env->spe_fscr);
9571 ppc_maybe_bswap_register(env, mem_buf, 4);
9572 return 4;
9574 return 0;
9577 static int gdb_set_spe_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
9579 if (n < 32) {
9580 #if defined(TARGET_PPC64)
9581 target_ulong lo = (uint32_t)env->gpr[n];
9582 target_ulong hi;
9584 ppc_maybe_bswap_register(env, mem_buf, 4);
9586 hi = (target_ulong)ldl_p(mem_buf) << 32;
9587 env->gpr[n] = lo | hi;
9588 #else
9589 env->gprh[n] = ldl_p(mem_buf);
9590 #endif
9591 return 4;
9593 if (n == 32) {
9594 ppc_maybe_bswap_register(env, mem_buf, 8);
9595 env->spe_acc = ldq_p(mem_buf);
9596 return 8;
9598 if (n == 33) {
9599 ppc_maybe_bswap_register(env, mem_buf, 4);
9600 env->spe_fscr = ldl_p(mem_buf);
9601 return 4;
9603 return 0;
9606 static int gdb_get_vsx_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
9608 if (n < 32) {
9609 stq_p(mem_buf, env->vsr[n]);
9610 ppc_maybe_bswap_register(env, mem_buf, 8);
9611 return 8;
9613 return 0;
9616 static int gdb_set_vsx_reg(CPUPPCState *env, uint8_t *mem_buf, int n)
9618 if (n < 32) {
9619 ppc_maybe_bswap_register(env, mem_buf, 8);
9620 env->vsr[n] = ldq_p(mem_buf);
9621 return 8;
9623 return 0;
9626 static int ppc_fixup_cpu(PowerPCCPU *cpu)
9628 CPUPPCState *env = &cpu->env;
9630 /* TCG doesn't (yet) emulate some groups of instructions that
9631 * are implemented on some otherwise supported CPUs (e.g. VSX
9632 * and decimal floating point instructions on POWER7). We
9633 * remove unsupported instruction groups from the cpu state's
9634 * instruction masks and hope the guest can cope. For at
9635 * least the pseries machine, the unavailability of these
9636 * instructions can be advertised to the guest via the device
9637 * tree. */
9638 if ((env->insns_flags & ~PPC_TCG_INSNS)
9639 || (env->insns_flags2 & ~PPC_TCG_INSNS2)) {
9640 warn_report("Disabling some instructions which are not "
9641 "emulated by TCG (0x%" PRIx64 ", 0x%" PRIx64 ")",
9642 env->insns_flags & ~PPC_TCG_INSNS,
9643 env->insns_flags2 & ~PPC_TCG_INSNS2);
9645 env->insns_flags &= PPC_TCG_INSNS;
9646 env->insns_flags2 &= PPC_TCG_INSNS2;
9647 return 0;
9650 static void ppc_cpu_realize(DeviceState *dev, Error **errp)
9652 CPUState *cs = CPU(dev);
9653 PowerPCCPU *cpu = POWERPC_CPU(dev);
9654 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
9655 Error *local_err = NULL;
9657 cpu_exec_realizefn(cs, &local_err);
9658 if (local_err != NULL) {
9659 error_propagate(errp, local_err);
9660 return;
9662 if (cpu->vcpu_id == UNASSIGNED_CPU_INDEX) {
9663 cpu->vcpu_id = cs->cpu_index;
9666 if (tcg_enabled()) {
9667 if (ppc_fixup_cpu(cpu) != 0) {
9668 error_setg(errp, "Unable to emulate selected CPU with TCG");
9669 goto unrealize;
9673 create_ppc_opcodes(cpu, &local_err);
9674 if (local_err != NULL) {
9675 error_propagate(errp, local_err);
9676 goto unrealize;
9678 init_ppc_proc(cpu);
9680 if (pcc->insns_flags & PPC_FLOAT) {
9681 gdb_register_coprocessor(cs, gdb_get_float_reg, gdb_set_float_reg,
9682 33, "power-fpu.xml", 0);
9684 if (pcc->insns_flags & PPC_ALTIVEC) {
9685 gdb_register_coprocessor(cs, gdb_get_avr_reg, gdb_set_avr_reg,
9686 34, "power-altivec.xml", 0);
9688 if (pcc->insns_flags & PPC_SPE) {
9689 gdb_register_coprocessor(cs, gdb_get_spe_reg, gdb_set_spe_reg,
9690 34, "power-spe.xml", 0);
9692 if (pcc->insns_flags2 & PPC2_VSX) {
9693 gdb_register_coprocessor(cs, gdb_get_vsx_reg, gdb_set_vsx_reg,
9694 32, "power-vsx.xml", 0);
9697 qemu_init_vcpu(cs);
9699 pcc->parent_realize(dev, errp);
9701 #if defined(PPC_DUMP_CPU)
9703 CPUPPCState *env = &cpu->env;
9704 const char *mmu_model, *excp_model, *bus_model;
9705 switch (env->mmu_model) {
9706 case POWERPC_MMU_32B:
9707 mmu_model = "PowerPC 32";
9708 break;
9709 case POWERPC_MMU_SOFT_6xx:
9710 mmu_model = "PowerPC 6xx/7xx with software driven TLBs";
9711 break;
9712 case POWERPC_MMU_SOFT_74xx:
9713 mmu_model = "PowerPC 74xx with software driven TLBs";
9714 break;
9715 case POWERPC_MMU_SOFT_4xx:
9716 mmu_model = "PowerPC 4xx with software driven TLBs";
9717 break;
9718 case POWERPC_MMU_SOFT_4xx_Z:
9719 mmu_model = "PowerPC 4xx with software driven TLBs "
9720 "and zones protections";
9721 break;
9722 case POWERPC_MMU_REAL:
9723 mmu_model = "PowerPC real mode only";
9724 break;
9725 case POWERPC_MMU_MPC8xx:
9726 mmu_model = "PowerPC MPC8xx";
9727 break;
9728 case POWERPC_MMU_BOOKE:
9729 mmu_model = "PowerPC BookE";
9730 break;
9731 case POWERPC_MMU_BOOKE206:
9732 mmu_model = "PowerPC BookE 2.06";
9733 break;
9734 case POWERPC_MMU_601:
9735 mmu_model = "PowerPC 601";
9736 break;
9737 #if defined(TARGET_PPC64)
9738 case POWERPC_MMU_64B:
9739 mmu_model = "PowerPC 64";
9740 break;
9741 #endif
9742 default:
9743 mmu_model = "Unknown or invalid";
9744 break;
9746 switch (env->excp_model) {
9747 case POWERPC_EXCP_STD:
9748 excp_model = "PowerPC";
9749 break;
9750 case POWERPC_EXCP_40x:
9751 excp_model = "PowerPC 40x";
9752 break;
9753 case POWERPC_EXCP_601:
9754 excp_model = "PowerPC 601";
9755 break;
9756 case POWERPC_EXCP_602:
9757 excp_model = "PowerPC 602";
9758 break;
9759 case POWERPC_EXCP_603:
9760 excp_model = "PowerPC 603";
9761 break;
9762 case POWERPC_EXCP_603E:
9763 excp_model = "PowerPC 603e";
9764 break;
9765 case POWERPC_EXCP_604:
9766 excp_model = "PowerPC 604";
9767 break;
9768 case POWERPC_EXCP_7x0:
9769 excp_model = "PowerPC 740/750";
9770 break;
9771 case POWERPC_EXCP_7x5:
9772 excp_model = "PowerPC 745/755";
9773 break;
9774 case POWERPC_EXCP_74xx:
9775 excp_model = "PowerPC 74xx";
9776 break;
9777 case POWERPC_EXCP_BOOKE:
9778 excp_model = "PowerPC BookE";
9779 break;
9780 #if defined(TARGET_PPC64)
9781 case POWERPC_EXCP_970:
9782 excp_model = "PowerPC 970";
9783 break;
9784 #endif
9785 default:
9786 excp_model = "Unknown or invalid";
9787 break;
9789 switch (env->bus_model) {
9790 case PPC_FLAGS_INPUT_6xx:
9791 bus_model = "PowerPC 6xx";
9792 break;
9793 case PPC_FLAGS_INPUT_BookE:
9794 bus_model = "PowerPC BookE";
9795 break;
9796 case PPC_FLAGS_INPUT_405:
9797 bus_model = "PowerPC 405";
9798 break;
9799 case PPC_FLAGS_INPUT_401:
9800 bus_model = "PowerPC 401/403";
9801 break;
9802 case PPC_FLAGS_INPUT_RCPU:
9803 bus_model = "RCPU / MPC8xx";
9804 break;
9805 #if defined(TARGET_PPC64)
9806 case PPC_FLAGS_INPUT_970:
9807 bus_model = "PowerPC 970";
9808 break;
9809 #endif
9810 default:
9811 bus_model = "Unknown or invalid";
9812 break;
9814 printf("PowerPC %-12s : PVR %08x MSR %016" PRIx64 "\n"
9815 " MMU model : %s\n",
9816 object_class_get_name(OBJECT_CLASS(pcc)),
9817 pcc->pvr, pcc->msr_mask, mmu_model);
9818 #if !defined(CONFIG_USER_ONLY)
9819 if (env->tlb.tlb6) {
9820 printf(" %d %s TLB in %d ways\n",
9821 env->nb_tlb, env->id_tlbs ? "splitted" : "merged",
9822 env->nb_ways);
9824 #endif
9825 printf(" Exceptions model : %s\n"
9826 " Bus model : %s\n",
9827 excp_model, bus_model);
9828 printf(" MSR features :\n");
9829 if (env->flags & POWERPC_FLAG_SPE)
9830 printf(" signal processing engine enable"
9831 "\n");
9832 else if (env->flags & POWERPC_FLAG_VRE)
9833 printf(" vector processor enable\n");
9834 if (env->flags & POWERPC_FLAG_TGPR)
9835 printf(" temporary GPRs\n");
9836 else if (env->flags & POWERPC_FLAG_CE)
9837 printf(" critical input enable\n");
9838 if (env->flags & POWERPC_FLAG_SE)
9839 printf(" single-step trace mode\n");
9840 else if (env->flags & POWERPC_FLAG_DWE)
9841 printf(" debug wait enable\n");
9842 else if (env->flags & POWERPC_FLAG_UBLE)
9843 printf(" user BTB lock enable\n");
9844 if (env->flags & POWERPC_FLAG_BE)
9845 printf(" branch-step trace mode\n");
9846 else if (env->flags & POWERPC_FLAG_DE)
9847 printf(" debug interrupt enable\n");
9848 if (env->flags & POWERPC_FLAG_PX)
9849 printf(" inclusive protection\n");
9850 else if (env->flags & POWERPC_FLAG_PMM)
9851 printf(" performance monitor mark\n");
9852 if (env->flags == POWERPC_FLAG_NONE)
9853 printf(" none\n");
9854 printf(" Time-base/decrementer clock source: %s\n",
9855 env->flags & POWERPC_FLAG_RTC_CLK ? "RTC clock" : "bus clock");
9856 dump_ppc_insns(env);
9857 dump_ppc_sprs(env);
9858 fflush(stdout);
9860 #endif
9861 return;
9863 unrealize:
9864 cpu_exec_unrealizefn(cs);
9867 static void ppc_cpu_unrealize(DeviceState *dev, Error **errp)
9869 PowerPCCPU *cpu = POWERPC_CPU(dev);
9870 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
9871 CPUPPCState *env = &cpu->env;
9872 Error *local_err = NULL;
9873 opc_handler_t **table, **table_2;
9874 int i, j, k;
9876 pcc->parent_unrealize(dev, &local_err);
9877 if (local_err != NULL) {
9878 error_propagate(errp, local_err);
9879 return;
9882 for (i = 0; i < PPC_CPU_OPCODES_LEN; i++) {
9883 if (env->opcodes[i] == &invalid_handler) {
9884 continue;
9886 if (is_indirect_opcode(env->opcodes[i])) {
9887 table = ind_table(env->opcodes[i]);
9888 for (j = 0; j < PPC_CPU_INDIRECT_OPCODES_LEN; j++) {
9889 if (table[j] == &invalid_handler) {
9890 continue;
9892 if (is_indirect_opcode(table[j])) {
9893 table_2 = ind_table(table[j]);
9894 for (k = 0; k < PPC_CPU_INDIRECT_OPCODES_LEN; k++) {
9895 if (table_2[k] != &invalid_handler &&
9896 is_indirect_opcode(table_2[k])) {
9897 g_free((opc_handler_t *)((uintptr_t)table_2[k] &
9898 ~PPC_INDIRECT));
9901 g_free((opc_handler_t *)((uintptr_t)table[j] &
9902 ~PPC_INDIRECT));
9905 g_free((opc_handler_t *)((uintptr_t)env->opcodes[i] &
9906 ~PPC_INDIRECT));
9911 static gint ppc_cpu_compare_class_pvr(gconstpointer a, gconstpointer b)
9913 ObjectClass *oc = (ObjectClass *)a;
9914 uint32_t pvr = *(uint32_t *)b;
9915 PowerPCCPUClass *pcc = (PowerPCCPUClass *)a;
9917 /* -cpu host does a PVR lookup during construction */
9918 if (unlikely(strcmp(object_class_get_name(oc),
9919 TYPE_HOST_POWERPC_CPU) == 0)) {
9920 return -1;
9923 return pcc->pvr == pvr ? 0 : -1;
9926 PowerPCCPUClass *ppc_cpu_class_by_pvr(uint32_t pvr)
9928 GSList *list, *item;
9929 PowerPCCPUClass *pcc = NULL;
9931 list = object_class_get_list(TYPE_POWERPC_CPU, false);
9932 item = g_slist_find_custom(list, &pvr, ppc_cpu_compare_class_pvr);
9933 if (item != NULL) {
9934 pcc = POWERPC_CPU_CLASS(item->data);
9936 g_slist_free(list);
9938 return pcc;
9941 static gint ppc_cpu_compare_class_pvr_mask(gconstpointer a, gconstpointer b)
9943 ObjectClass *oc = (ObjectClass *)a;
9944 uint32_t pvr = *(uint32_t *)b;
9945 PowerPCCPUClass *pcc = (PowerPCCPUClass *)a;
9947 /* -cpu host does a PVR lookup during construction */
9948 if (unlikely(strcmp(object_class_get_name(oc),
9949 TYPE_HOST_POWERPC_CPU) == 0)) {
9950 return -1;
9953 if (pcc->pvr_match(pcc, pvr)) {
9954 return 0;
9957 return -1;
9960 PowerPCCPUClass *ppc_cpu_class_by_pvr_mask(uint32_t pvr)
9962 GSList *list, *item;
9963 PowerPCCPUClass *pcc = NULL;
9965 list = object_class_get_list(TYPE_POWERPC_CPU, true);
9966 item = g_slist_find_custom(list, &pvr, ppc_cpu_compare_class_pvr_mask);
9967 if (item != NULL) {
9968 pcc = POWERPC_CPU_CLASS(item->data);
9970 g_slist_free(list);
9972 return pcc;
9975 static const char *ppc_cpu_lookup_alias(const char *alias)
9977 int ai;
9979 for (ai = 0; ppc_cpu_aliases[ai].alias != NULL; ai++) {
9980 if (strcmp(ppc_cpu_aliases[ai].alias, alias) == 0) {
9981 return ppc_cpu_aliases[ai].model;
9985 return NULL;
9988 static ObjectClass *ppc_cpu_class_by_name(const char *name)
9990 char *cpu_model, *typename;
9991 ObjectClass *oc;
9992 const char *p;
9993 unsigned long pvr;
9995 /* Lookup by PVR if cpu_model is valid 8 digit hex number
9996 * (excl: 0x prefix if present)
9998 if (!qemu_strtoul(name, &p, 16, &pvr)) {
9999 int len = p - name;
10000 len = (len == 10) && (name[1] == 'x') ? len - 2 : len;
10001 if ((len == 8) && (*p == '\0')) {
10002 return OBJECT_CLASS(ppc_cpu_class_by_pvr(pvr));
10006 cpu_model = g_ascii_strdown(name, -1);
10007 p = ppc_cpu_lookup_alias(cpu_model);
10008 if (p) {
10009 g_free(cpu_model);
10010 cpu_model = g_strdup(p);
10013 typename = g_strdup_printf("%s" POWERPC_CPU_TYPE_SUFFIX, cpu_model);
10014 oc = object_class_by_name(typename);
10015 g_free(typename);
10016 g_free(cpu_model);
10018 return oc;
10021 static void ppc_cpu_parse_featurestr(const char *type, char *features,
10022 Error **errp)
10024 Object *machine = qdev_get_machine();
10025 const PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(object_class_by_name(type));
10027 if (!features) {
10028 return;
10031 if (object_property_find(machine, "max-cpu-compat", NULL)) {
10032 int i;
10033 char **inpieces;
10034 char *s = features;
10035 Error *local_err = NULL;
10036 char *compat_str = NULL;
10039 * Backwards compatibility hack:
10041 * CPUs had a "compat=" property which didn't make sense for
10042 * anything except pseries. It was replaced by "max-cpu-compat"
10043 * machine option. This supports old command lines like
10044 * -cpu POWER8,compat=power7
10045 * By stripping the compat option and applying it to the machine
10046 * before passing it on to the cpu level parser.
10048 inpieces = g_strsplit(features, ",", 0);
10049 *s = '\0';
10050 for (i = 0; inpieces[i]; i++) {
10051 if (g_str_has_prefix(inpieces[i], "compat=")) {
10052 compat_str = inpieces[i];
10053 continue;
10055 if ((i != 0) && (s != features)) {
10056 s = g_stpcpy(s, ",");
10058 s = g_stpcpy(s, inpieces[i]);
10061 if (compat_str) {
10062 char *v = compat_str + strlen("compat=");
10063 object_property_set_str(machine, v, "max-cpu-compat", &local_err);
10065 g_strfreev(inpieces);
10066 if (local_err) {
10067 error_propagate(errp, local_err);
10068 return;
10072 /* do property processing with generic handler */
10073 pcc->parent_parse_features(type, features, errp);
10076 PowerPCCPUClass *ppc_cpu_get_family_class(PowerPCCPUClass *pcc)
10078 ObjectClass *oc = OBJECT_CLASS(pcc);
10080 while (oc && !object_class_is_abstract(oc)) {
10081 oc = object_class_get_parent(oc);
10083 assert(oc);
10085 return POWERPC_CPU_CLASS(oc);
10088 /* Sort by PVR, ordering special case "host" last. */
10089 static gint ppc_cpu_list_compare(gconstpointer a, gconstpointer b)
10091 ObjectClass *oc_a = (ObjectClass *)a;
10092 ObjectClass *oc_b = (ObjectClass *)b;
10093 PowerPCCPUClass *pcc_a = POWERPC_CPU_CLASS(oc_a);
10094 PowerPCCPUClass *pcc_b = POWERPC_CPU_CLASS(oc_b);
10095 const char *name_a = object_class_get_name(oc_a);
10096 const char *name_b = object_class_get_name(oc_b);
10098 if (strcmp(name_a, TYPE_HOST_POWERPC_CPU) == 0) {
10099 return 1;
10100 } else if (strcmp(name_b, TYPE_HOST_POWERPC_CPU) == 0) {
10101 return -1;
10102 } else {
10103 /* Avoid an integer overflow during subtraction */
10104 if (pcc_a->pvr < pcc_b->pvr) {
10105 return -1;
10106 } else if (pcc_a->pvr > pcc_b->pvr) {
10107 return 1;
10108 } else {
10109 return 0;
10114 static void ppc_cpu_list_entry(gpointer data, gpointer user_data)
10116 ObjectClass *oc = data;
10117 CPUListState *s = user_data;
10118 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
10119 DeviceClass *family = DEVICE_CLASS(ppc_cpu_get_family_class(pcc));
10120 const char *typename = object_class_get_name(oc);
10121 char *name;
10122 int i;
10124 if (unlikely(strcmp(typename, TYPE_HOST_POWERPC_CPU) == 0)) {
10125 return;
10128 name = g_strndup(typename,
10129 strlen(typename) - strlen(POWERPC_CPU_TYPE_SUFFIX));
10130 (*s->cpu_fprintf)(s->file, "PowerPC %-16s PVR %08x\n",
10131 name, pcc->pvr);
10132 for (i = 0; ppc_cpu_aliases[i].alias != NULL; i++) {
10133 PowerPCCPUAlias *alias = &ppc_cpu_aliases[i];
10134 ObjectClass *alias_oc = ppc_cpu_class_by_name(alias->model);
10136 if (alias_oc != oc) {
10137 continue;
10140 * If running with KVM, we might update the family alias later, so
10141 * avoid printing the wrong alias here and use "preferred" instead
10143 if (strcmp(alias->alias, family->desc) == 0) {
10144 (*s->cpu_fprintf)(s->file,
10145 "PowerPC %-16s (alias for preferred %s CPU)\n",
10146 alias->alias, family->desc);
10147 } else {
10148 (*s->cpu_fprintf)(s->file, "PowerPC %-16s (alias for %s)\n",
10149 alias->alias, name);
10152 g_free(name);
10155 void ppc_cpu_list(FILE *f, fprintf_function cpu_fprintf)
10157 CPUListState s = {
10158 .file = f,
10159 .cpu_fprintf = cpu_fprintf,
10161 GSList *list;
10163 list = object_class_get_list(TYPE_POWERPC_CPU, false);
10164 list = g_slist_sort(list, ppc_cpu_list_compare);
10165 g_slist_foreach(list, ppc_cpu_list_entry, &s);
10166 g_slist_free(list);
10168 #ifdef CONFIG_KVM
10169 cpu_fprintf(f, "\n");
10170 cpu_fprintf(f, "PowerPC %-16s\n", "host");
10171 #endif
10174 static void ppc_cpu_defs_entry(gpointer data, gpointer user_data)
10176 ObjectClass *oc = data;
10177 CpuDefinitionInfoList **first = user_data;
10178 const char *typename;
10179 CpuDefinitionInfoList *entry;
10180 CpuDefinitionInfo *info;
10182 typename = object_class_get_name(oc);
10183 info = g_malloc0(sizeof(*info));
10184 info->name = g_strndup(typename,
10185 strlen(typename) - strlen(POWERPC_CPU_TYPE_SUFFIX));
10187 entry = g_malloc0(sizeof(*entry));
10188 entry->value = info;
10189 entry->next = *first;
10190 *first = entry;
10193 CpuDefinitionInfoList *arch_query_cpu_definitions(Error **errp)
10195 CpuDefinitionInfoList *cpu_list = NULL;
10196 GSList *list;
10197 int i;
10199 list = object_class_get_list(TYPE_POWERPC_CPU, false);
10200 g_slist_foreach(list, ppc_cpu_defs_entry, &cpu_list);
10201 g_slist_free(list);
10203 for (i = 0; ppc_cpu_aliases[i].alias != NULL; i++) {
10204 PowerPCCPUAlias *alias = &ppc_cpu_aliases[i];
10205 ObjectClass *oc;
10206 CpuDefinitionInfoList *entry;
10207 CpuDefinitionInfo *info;
10209 oc = ppc_cpu_class_by_name(alias->model);
10210 if (oc == NULL) {
10211 continue;
10214 info = g_malloc0(sizeof(*info));
10215 info->name = g_strdup(alias->alias);
10216 info->q_typename = g_strdup(object_class_get_name(oc));
10218 entry = g_malloc0(sizeof(*entry));
10219 entry->value = info;
10220 entry->next = cpu_list;
10221 cpu_list = entry;
10224 return cpu_list;
10227 static void ppc_cpu_set_pc(CPUState *cs, vaddr value)
10229 PowerPCCPU *cpu = POWERPC_CPU(cs);
10231 cpu->env.nip = value;
10234 static bool ppc_cpu_has_work(CPUState *cs)
10236 PowerPCCPU *cpu = POWERPC_CPU(cs);
10237 CPUPPCState *env = &cpu->env;
10239 return msr_ee && (cs->interrupt_request & CPU_INTERRUPT_HARD);
10242 /* CPUClass::reset() */
10243 static void ppc_cpu_reset(CPUState *s)
10245 PowerPCCPU *cpu = POWERPC_CPU(s);
10246 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
10247 CPUPPCState *env = &cpu->env;
10248 target_ulong msr;
10249 int i;
10251 pcc->parent_reset(s);
10253 msr = (target_ulong)0;
10254 msr |= (target_ulong)MSR_HVB;
10255 msr |= (target_ulong)0 << MSR_AP; /* TO BE CHECKED */
10256 msr |= (target_ulong)0 << MSR_SA; /* TO BE CHECKED */
10257 msr |= (target_ulong)1 << MSR_EP;
10258 #if defined(DO_SINGLE_STEP) && 0
10259 /* Single step trace mode */
10260 msr |= (target_ulong)1 << MSR_SE;
10261 msr |= (target_ulong)1 << MSR_BE;
10262 #endif
10263 #if defined(CONFIG_USER_ONLY)
10264 msr |= (target_ulong)1 << MSR_FP; /* Allow floating point usage */
10265 msr |= (target_ulong)1 << MSR_FE0; /* Allow floating point exceptions */
10266 msr |= (target_ulong)1 << MSR_FE1;
10267 msr |= (target_ulong)1 << MSR_VR; /* Allow altivec usage */
10268 msr |= (target_ulong)1 << MSR_VSX; /* Allow VSX usage */
10269 msr |= (target_ulong)1 << MSR_SPE; /* Allow SPE usage */
10270 msr |= (target_ulong)1 << MSR_PR;
10271 #if defined(TARGET_PPC64)
10272 msr |= (target_ulong)1 << MSR_TM; /* Transactional memory */
10273 #endif
10274 #if !defined(TARGET_WORDS_BIGENDIAN)
10275 msr |= (target_ulong)1 << MSR_LE; /* Little-endian user mode */
10276 if (!((env->msr_mask >> MSR_LE) & 1)) {
10277 fprintf(stderr, "Selected CPU does not support little-endian.\n");
10278 exit(1);
10280 #endif
10281 #endif
10283 #if defined(TARGET_PPC64)
10284 if (env->mmu_model & POWERPC_MMU_64) {
10285 msr |= (1ULL << MSR_SF);
10287 #endif
10289 hreg_store_msr(env, msr, 1);
10291 #if !defined(CONFIG_USER_ONLY)
10292 env->nip = env->hreset_vector | env->excp_prefix;
10293 if (env->mmu_model != POWERPC_MMU_REAL) {
10294 ppc_tlb_invalidate_all(env);
10296 #endif
10298 hreg_compute_hflags(env);
10299 env->reserve_addr = (target_ulong)-1ULL;
10300 /* Be sure no exception or interrupt is pending */
10301 env->pending_interrupts = 0;
10302 s->exception_index = POWERPC_EXCP_NONE;
10303 env->error_code = 0;
10305 for (i = 0; i < ARRAY_SIZE(env->spr_cb); i++) {
10306 ppc_spr_t *spr = &env->spr_cb[i];
10308 if (!spr->name) {
10309 continue;
10311 env->spr[i] = spr->default_value;
10315 #ifndef CONFIG_USER_ONLY
10316 static bool ppc_cpu_is_big_endian(CPUState *cs)
10318 PowerPCCPU *cpu = POWERPC_CPU(cs);
10319 CPUPPCState *env = &cpu->env;
10321 cpu_synchronize_state(cs);
10323 return !msr_le;
10325 #endif
10327 static void ppc_cpu_instance_init(Object *obj)
10329 CPUState *cs = CPU(obj);
10330 PowerPCCPU *cpu = POWERPC_CPU(obj);
10331 PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
10332 CPUPPCState *env = &cpu->env;
10334 cs->env_ptr = env;
10335 cpu->vcpu_id = UNASSIGNED_CPU_INDEX;
10337 env->msr_mask = pcc->msr_mask;
10338 env->mmu_model = pcc->mmu_model;
10339 env->excp_model = pcc->excp_model;
10340 env->bus_model = pcc->bus_model;
10341 env->insns_flags = pcc->insns_flags;
10342 env->insns_flags2 = pcc->insns_flags2;
10343 env->flags = pcc->flags;
10344 env->bfd_mach = pcc->bfd_mach;
10345 env->check_pow = pcc->check_pow;
10347 /* Mark HV mode as supported if the CPU has an MSR_HV bit
10348 * in the msr_mask. The mask can later be cleared by PAPR
10349 * mode but the hv mode support will remain, thus enforcing
10350 * that we cannot use priv. instructions in guest in PAPR
10351 * mode. For 970 we currently simply don't set HV in msr_mask
10352 * thus simulating an "Apple mode" 970. If we ever want to
10353 * support 970 HV mode, we'll have to add a processor attribute
10354 * of some sort.
10356 #if !defined(CONFIG_USER_ONLY)
10357 env->has_hv_mode = !!(env->msr_mask & MSR_HVB);
10358 #endif
10360 ppc_hash64_init(cpu);
10363 static void ppc_cpu_instance_finalize(Object *obj)
10365 PowerPCCPU *cpu = POWERPC_CPU(obj);
10367 ppc_hash64_finalize(cpu);
10370 static bool ppc_pvr_match_default(PowerPCCPUClass *pcc, uint32_t pvr)
10372 return pcc->pvr == pvr;
10375 static gchar *ppc_gdb_arch_name(CPUState *cs)
10377 #if defined(TARGET_PPC64)
10378 return g_strdup("powerpc:common64");
10379 #else
10380 return g_strdup("powerpc:common");
10381 #endif
10384 static void ppc_disas_set_info(CPUState *cs, disassemble_info *info)
10386 PowerPCCPU *cpu = POWERPC_CPU(cs);
10387 CPUPPCState *env = &cpu->env;
10389 if ((env->hflags >> MSR_LE) & 1) {
10390 info->endian = BFD_ENDIAN_LITTLE;
10392 info->mach = env->bfd_mach;
10393 if (!env->bfd_mach) {
10394 #ifdef TARGET_PPC64
10395 info->mach = bfd_mach_ppc64;
10396 #else
10397 info->mach = bfd_mach_ppc;
10398 #endif
10400 info->disassembler_options = (char *)"any";
10401 info->print_insn = print_insn_ppc;
10403 info->cap_arch = CS_ARCH_PPC;
10404 #ifdef TARGET_PPC64
10405 info->cap_mode = CS_MODE_64;
10406 #endif
10409 static Property ppc_cpu_properties[] = {
10410 DEFINE_PROP_BOOL("pre-2.8-migration", PowerPCCPU, pre_2_8_migration, false),
10411 DEFINE_PROP_BOOL("pre-2.10-migration", PowerPCCPU, pre_2_10_migration,
10412 false),
10413 DEFINE_PROP_BOOL("pre-3.0-migration", PowerPCCPU, pre_3_0_migration,
10414 false),
10415 DEFINE_PROP_END_OF_LIST(),
10418 static void ppc_cpu_class_init(ObjectClass *oc, void *data)
10420 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
10421 CPUClass *cc = CPU_CLASS(oc);
10422 DeviceClass *dc = DEVICE_CLASS(oc);
10424 device_class_set_parent_realize(dc, ppc_cpu_realize,
10425 &pcc->parent_realize);
10426 device_class_set_parent_unrealize(dc, ppc_cpu_unrealize,
10427 &pcc->parent_unrealize);
10428 pcc->pvr_match = ppc_pvr_match_default;
10429 pcc->interrupts_big_endian = ppc_cpu_interrupts_big_endian_always;
10430 dc->props = ppc_cpu_properties;
10432 pcc->parent_reset = cc->reset;
10433 cc->reset = ppc_cpu_reset;
10435 cc->class_by_name = ppc_cpu_class_by_name;
10436 pcc->parent_parse_features = cc->parse_features;
10437 cc->parse_features = ppc_cpu_parse_featurestr;
10438 cc->has_work = ppc_cpu_has_work;
10439 cc->do_interrupt = ppc_cpu_do_interrupt;
10440 cc->cpu_exec_interrupt = ppc_cpu_exec_interrupt;
10441 cc->dump_state = ppc_cpu_dump_state;
10442 cc->dump_statistics = ppc_cpu_dump_statistics;
10443 cc->set_pc = ppc_cpu_set_pc;
10444 cc->gdb_read_register = ppc_cpu_gdb_read_register;
10445 cc->gdb_write_register = ppc_cpu_gdb_write_register;
10446 cc->do_unaligned_access = ppc_cpu_do_unaligned_access;
10447 #ifdef CONFIG_USER_ONLY
10448 cc->handle_mmu_fault = ppc_cpu_handle_mmu_fault;
10449 #else
10450 cc->get_phys_page_debug = ppc_cpu_get_phys_page_debug;
10451 cc->vmsd = &vmstate_ppc_cpu;
10452 #endif
10453 #if defined(CONFIG_SOFTMMU)
10454 cc->write_elf64_note = ppc64_cpu_write_elf64_note;
10455 cc->write_elf32_note = ppc32_cpu_write_elf32_note;
10456 #endif
10458 cc->gdb_num_core_regs = 71;
10460 #ifdef USE_APPLE_GDB
10461 cc->gdb_read_register = ppc_cpu_gdb_read_register_apple;
10462 cc->gdb_write_register = ppc_cpu_gdb_write_register_apple;
10463 cc->gdb_num_core_regs = 71 + 32;
10464 #endif
10466 cc->gdb_arch_name = ppc_gdb_arch_name;
10467 #if defined(TARGET_PPC64)
10468 cc->gdb_core_xml_file = "power64-core.xml";
10469 #else
10470 cc->gdb_core_xml_file = "power-core.xml";
10471 #endif
10472 #ifndef CONFIG_USER_ONLY
10473 cc->virtio_is_big_endian = ppc_cpu_is_big_endian;
10474 #endif
10475 #ifdef CONFIG_TCG
10476 cc->tcg_initialize = ppc_translate_init;
10477 #endif
10478 cc->disas_set_info = ppc_disas_set_info;
10480 dc->fw_name = "PowerPC,UNKNOWN";
10483 static const TypeInfo ppc_cpu_type_info = {
10484 .name = TYPE_POWERPC_CPU,
10485 .parent = TYPE_CPU,
10486 .instance_size = sizeof(PowerPCCPU),
10487 .instance_init = ppc_cpu_instance_init,
10488 .instance_finalize = ppc_cpu_instance_finalize,
10489 .abstract = true,
10490 .class_size = sizeof(PowerPCCPUClass),
10491 .class_init = ppc_cpu_class_init,
10494 static const TypeInfo ppc_vhyp_type_info = {
10495 .name = TYPE_PPC_VIRTUAL_HYPERVISOR,
10496 .parent = TYPE_INTERFACE,
10497 .class_size = sizeof(PPCVirtualHypervisorClass),
10500 static void ppc_cpu_register_types(void)
10502 type_register_static(&ppc_cpu_type_info);
10503 type_register_static(&ppc_vhyp_type_info);
10506 type_init(ppc_cpu_register_types)