aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlexey Kardashevskiy <aik@ozlabs.ru>2014-06-04 22:50:40 +1000
committerAlexander Graf <agraf@suse.de>2014-06-16 13:24:42 +0200
commitfd51ff6328e3d981582436d1040f648c8da4a41f (patch)
treecadef35869b93962afd75222ddc112354e9888d4
parenteb16dd9cc98694cdd904770a82267d5bbfc8f8af (diff)
target-ppc: Copy and split gen_spr_7xx() for 970
This stops using 7xx common SPRs init function and adds separate set of helpers for 970. This does not copy ICTC SPR as neither 970 manual nor PowerISA mention it. This defines 970/book3s PMU SPRs constants as they differs from the ones used for 7XX. This creates 2 helpers for PMU SPRs, one for supermode privileged SPRs and one for user privileged SPRs as "sup" versions can be shared across the family while "user" versions will behave different starting POWER8 (which will be addressed later). This allows writing to Uxxxx SPRs from supermode. spr_write_ureg() is implemented for this as a copy of already existing spr_read_ureg(). This allows writing to supervisor's SIAR - it used to be disabled when gen_spr_7xx() was used. Signed-off-by: Alexey Kardashevskiy <aik@ozlabs.ru> Signed-off-by: Alexander Graf <agraf@suse.de>
-rw-r--r--target-ppc/cpu.h20
-rw-r--r--target-ppc/translate_init.c106
2 files changed, 125 insertions, 1 deletions
diff --git a/target-ppc/cpu.h b/target-ppc/cpu.h
index ce3c7903fb..fef8651626 100644
--- a/target-ppc/cpu.h
+++ b/target-ppc/cpu.h
@@ -1466,15 +1466,21 @@ static inline int cpu_mmu_index (CPUPPCState *env)
#define SPR_PERF3 (0x303)
#define SPR_RCPU_MI_RBA3 (0x303)
#define SPR_MPC_MI_EPN (0x303)
+#define SPR_POWER_UPMC1 (0x303)
#define SPR_PERF4 (0x304)
+#define SPR_POWER_UPMC2 (0x304)
#define SPR_PERF5 (0x305)
#define SPR_MPC_MI_TWC (0x305)
+#define SPR_POWER_UPMC3 (0x305)
#define SPR_PERF6 (0x306)
#define SPR_MPC_MI_RPN (0x306)
+#define SPR_POWER_UPMC4 (0x306)
#define SPR_PERF7 (0x307)
+#define SPR_POWER_UPMC5 (0x307)
#define SPR_PERF8 (0x308)
#define SPR_RCPU_L2U_RBA0 (0x308)
#define SPR_MPC_MD_CTR (0x308)
+#define SPR_POWER_UPMC6 (0x308)
#define SPR_PERF9 (0x309)
#define SPR_RCPU_L2U_RBA1 (0x309)
#define SPR_MPC_MD_CASID (0x309)
@@ -1484,29 +1490,43 @@ static inline int cpu_mmu_index (CPUPPCState *env)
#define SPR_PERFB (0x30B)
#define SPR_RCPU_L2U_RBA3 (0x30B)
#define SPR_MPC_MD_EPN (0x30B)
+#define SPR_POWER_UMMCR0 (0X30B)
#define SPR_PERFC (0x30C)
#define SPR_MPC_MD_TWB (0x30C)
+#define SPR_POWER_USIAR (0X30C)
#define SPR_PERFD (0x30D)
#define SPR_MPC_MD_TWC (0x30D)
+#define SPR_POWER_USDAR (0X30D)
#define SPR_PERFE (0x30E)
#define SPR_MPC_MD_RPN (0x30E)
+#define SPR_POWER_UMMCR1 (0X30E)
#define SPR_PERFF (0x30F)
#define SPR_MPC_MD_TW (0x30F)
#define SPR_UPERF0 (0x310)
#define SPR_UPERF1 (0x311)
#define SPR_UPERF2 (0x312)
#define SPR_UPERF3 (0x313)
+#define SPR_POWER_PMC1 (0X313)
#define SPR_UPERF4 (0x314)
+#define SPR_POWER_PMC2 (0X314)
#define SPR_UPERF5 (0x315)
+#define SPR_POWER_PMC3 (0X315)
#define SPR_UPERF6 (0x316)
+#define SPR_POWER_PMC4 (0X316)
#define SPR_UPERF7 (0x317)
+#define SPR_POWER_PMC5 (0X317)
#define SPR_UPERF8 (0x318)
+#define SPR_POWER_PMC6 (0X318)
#define SPR_UPERF9 (0x319)
#define SPR_UPERFA (0x31A)
#define SPR_UPERFB (0x31B)
+#define SPR_POWER_MMCR0 (0X31B)
#define SPR_UPERFC (0x31C)
+#define SPR_POWER_SIAR (0X31C)
#define SPR_UPERFD (0x31D)
+#define SPR_POWER_SDAR (0X31D)
#define SPR_UPERFE (0x31E)
+#define SPR_POWER_MMCR1 (0X31E)
#define SPR_UPERFF (0x31F)
#define SPR_RCPU_MI_RA0 (0x320)
#define SPR_MPC_MI_DBCAM (0x320)
diff --git a/target-ppc/translate_init.c b/target-ppc/translate_init.c
index 8b83b28656..def40742f3 100644
--- a/target-ppc/translate_init.c
+++ b/target-ppc/translate_init.c
@@ -175,6 +175,13 @@ static void spr_read_ureg (void *opaque, int gprn, int sprn)
gen_load_spr(cpu_gpr[gprn], sprn + 0x10);
}
+#if defined(TARGET_PPC64) && !defined(CONFIG_USER_ONLY)
+static void spr_write_ureg(void *opaque, int sprn, int gprn)
+{
+ gen_store_spr(sprn + 0x10, cpu_gpr[gprn]);
+}
+#endif
+
/* SPR common to all non-embedded PowerPC */
/* DECR */
#if !defined(CONFIG_USER_ONLY)
@@ -7329,16 +7336,113 @@ static void gen_spr_book3s_altivec(CPUPPCState *env)
vscr_init(env, 0x00010000);
}
+static void gen_spr_book3s_dbg(CPUPPCState *env)
+{
+ spr_register_kvm(env, SPR_DABR, "DABR",
+ SPR_NOACCESS, SPR_NOACCESS,
+ &spr_read_generic, &spr_write_generic,
+ KVM_REG_PPC_DABR, 0x00000000);
+}
+
+static void gen_spr_970_dbg(CPUPPCState *env)
+{
+ /* Breakpoints */
+ spr_register(env, SPR_IABR, "IABR",
+ SPR_NOACCESS, SPR_NOACCESS,
+ &spr_read_generic, &spr_write_generic,
+ 0x00000000);
+}
+
+static void gen_spr_book3s_pmu_sup(CPUPPCState *env)
+{
+ spr_register(env, SPR_POWER_MMCR0, "MMCR0",
+ SPR_NOACCESS, SPR_NOACCESS,
+ &spr_read_generic, &spr_write_generic,
+ 0x00000000);
+ spr_register(env, SPR_POWER_MMCR1, "MMCR1",
+ SPR_NOACCESS, SPR_NOACCESS,
+ &spr_read_generic, &spr_write_generic,
+ 0x00000000);
+ spr_register(env, SPR_POWER_PMC1, "PMC1",
+ SPR_NOACCESS, SPR_NOACCESS,
+ &spr_read_generic, &spr_write_generic,
+ 0x00000000);
+ spr_register(env, SPR_POWER_PMC2, "PMC2",
+ SPR_NOACCESS, SPR_NOACCESS,
+ &spr_read_generic, &spr_write_generic,
+ 0x00000000);
+ spr_register(env, SPR_POWER_PMC3, "PMC3",
+ SPR_NOACCESS, SPR_NOACCESS,
+ &spr_read_generic, &spr_write_generic,
+ 0x00000000);
+ spr_register(env, SPR_POWER_PMC4, "PMC4",
+ SPR_NOACCESS, SPR_NOACCESS,
+ &spr_read_generic, &spr_write_generic,
+ 0x00000000);
+ spr_register(env, SPR_POWER_SIAR, "SIAR",
+ SPR_NOACCESS, SPR_NOACCESS,
+ &spr_read_generic, &spr_write_generic,
+ 0x00000000);
+}
+
+static void gen_spr_book3s_pmu_user(CPUPPCState *env)
+{
+ spr_register(env, SPR_POWER_UMMCR0, "UMMCR0",
+ &spr_read_ureg, SPR_NOACCESS,
+ &spr_read_ureg, &spr_write_ureg,
+ 0x00000000);
+ spr_register(env, SPR_POWER_UMMCR1, "UMMCR1",
+ &spr_read_ureg, SPR_NOACCESS,
+ &spr_read_ureg, &spr_write_ureg,
+ 0x00000000);
+ spr_register(env, SPR_POWER_UPMC1, "UPMC1",
+ &spr_read_ureg, SPR_NOACCESS,
+ &spr_read_ureg, &spr_write_ureg,
+ 0x00000000);
+ spr_register(env, SPR_POWER_UPMC2, "UPMC2",
+ &spr_read_ureg, SPR_NOACCESS,
+ &spr_read_ureg, &spr_write_ureg,
+ 0x00000000);
+ spr_register(env, SPR_POWER_UPMC3, "UPMC3",
+ &spr_read_ureg, SPR_NOACCESS,
+ &spr_read_ureg, &spr_write_ureg,
+ 0x00000000);
+ spr_register(env, SPR_POWER_UPMC4, "UPMC4",
+ &spr_read_ureg, SPR_NOACCESS,
+ &spr_read_ureg, &spr_write_ureg,
+ 0x00000000);
+ spr_register(env, SPR_POWER_USIAR, "USIAR",
+ &spr_read_ureg, SPR_NOACCESS,
+ &spr_read_ureg, &spr_write_ureg,
+ 0x00000000);
+}
+
+static void gen_spr_power5p_ear(CPUPPCState *env)
+{
+ /* External access control */
+ spr_register(env, SPR_EAR, "EAR",
+ SPR_NOACCESS, SPR_NOACCESS,
+ &spr_read_generic, &spr_write_generic,
+ 0x00000000);
+}
+
static void init_proc_970 (CPUPPCState *env)
{
gen_spr_ne_601(env);
- gen_spr_7xx(env);
gen_tbl(env);
gen_spr_book3s_altivec(env);
+ gen_spr_book3s_pmu_sup(env);
+ gen_spr_book3s_pmu_user(env);
+ gen_spr_book3s_dbg(env);
+
gen_spr_970_hid(env);
gen_spr_970_hior(env);
gen_low_BATs(env);
gen_spr_book3s_common(env);
+
+ gen_spr_power5p_ear(env);
+
+ gen_spr_970_dbg(env);
#if !defined(CONFIG_USER_ONLY)
env->slb_nr = 64;
#endif