This patch implements the dense math registers (DMR) that are introduced
in RFC 02653 for ISA 3.2 as part of the dense math facility (DMF).
Also adds a new hflag for the same.

DMR which are 1024 bits long are implemented as an array of 'rows' which
are 128 bits each. DMF instructions manipulate DMRs in the granularity
of these rows.

Signed-off-by: Chinmay Rath <[email protected]>
---
 target/ppc/cpu.h         | 13 +++++++++++++
 target/ppc/helper_regs.c |  4 ++++
 target/ppc/translate.c   |  2 ++
 3 files changed, 19 insertions(+)

diff --git a/target/ppc/cpu.h b/target/ppc/cpu.h
index 09b511030b..1cd379810a 100644
--- a/target/ppc/cpu.h
+++ b/target/ppc/cpu.h
@@ -355,6 +355,11 @@ typedef union _ppc_vsr_t {
 typedef ppc_vsr_t ppc_avr_t;
 typedef ppc_vsr_t ppc_fprp_t;
 typedef ppc_vsr_t ppc_acc_t;
+typedef ppc_vsr_t ppc_dmr_row_t;
+
+typedef struct ppc_dmr_t {
+    ppc_dmr_row_t row[8];
+} ppc_dmr_t;
 
 #if !defined(CONFIG_USER_ONLY)
 /* Software TLB cache */
@@ -449,6 +454,7 @@ typedef enum {
 #define MSR_SEM5 PPC_BIT_NR(38) /* SIB Error Mask Bit 5 (PPE42)              */
 #define MSR_SEM6 PPC_BIT_NR(39) /* SIB Error Mask Bit 6 (PPE42)              */
 #define MSR_VSX  PPC_BIT_NR(40) /* Vector Scalar Extension (>= 2.06)x hflags */
+#define MSR_DM   PPC_BIT_NR(39) /* Dense Math Facility (>= 3.2)     x hflags */
 #define MSR_IS0  PPC_BIT_NR(40) /* Instance Specific Bit 0 (PPE42)           */
 #define MSR_S    PPC_BIT_NR(41) /* Secure state                              */
 #define MSR_SIBRC0 PPC_BIT_NR(41) /* Last SIB return code Bit 0 (PPE42)      */
@@ -743,6 +749,7 @@ FIELD(MSR, SIBRCA, MSR_SIBRCA7, 8)
 #define FSCR_IC_EBB         7
 #define FSCR_IC_TAR         8
 #define FSCR_IC_SCV        12
+#define FSCR_IC_DM         14
 
 /* Exception state register bits definition                                  */
 #define ESR_PIL   PPC_BIT(36) /* Illegal Instruction                    */
@@ -844,6 +851,8 @@ enum {
     POWERPC_FLAG_BHRB      = 0x01000000,
     /* Use PPE42-specific behavior                                           */
     POWERPC_FLAG_PPE42     = 0x02000000,
+    /* Has DMF                                                               */
+    POWERPC_FLAG_DM        = 0x04000000,
 };
 
 /*
@@ -873,6 +882,7 @@ enum {
     HFLAGS_INSN_CNT = 19, /* PMU instruction count enabled */
     HFLAGS_BHRB_ENABLE = 20, /* Summary flag for enabling BHRB */
     HFLAGS_VSX = 23, /* MSR_VSX if cpu has VSX */
+    HFLAGS_DM = 24, /* MSR_DM */
     HFLAGS_VR = 25,  /* MSR_VR if cpu has VRE */
 
     HFLAGS_IMMU_IDX = 26, /* 26..28 -- the composite immu_idx */
@@ -1364,6 +1374,9 @@ struct CPUArchState {
     float_status fp_status; /* Floating point execution context */
     target_ulong fpscr;     /* Floating point status and control register */
 
+    /* DMF registers */
+    ppc_dmr_t dmr[8] QEMU_ALIGNED(16);
+
     /* Internal devices resources */
     ppc_tb_t *tb_env;      /* Time base and decrementer */
     ppc_dcr_t *dcr_env;    /* Device control registers */
diff --git a/target/ppc/helper_regs.c b/target/ppc/helper_regs.c
index acf74c543a..75a97f8795 100644
--- a/target/ppc/helper_regs.c
+++ b/target/ppc/helper_regs.c
@@ -189,6 +189,10 @@ static uint32_t hreg_compute_hflags_value(CPUPPCState *env)
         /* PPE42 has a single address space and no problem state */
         msr = 0;
     }
+    if (ppc_flags & POWERPC_FLAG_DM) {
+        QEMU_BUILD_BUG_ON(MSR_DM != HFLAGS_DM);
+        msr_mask |= 1 << MSR_DM;
+    }
 
 #ifndef CONFIG_USER_ONLY
     if (!env->has_hv_mode || (msr & (1ull << MSR_HV))) {
diff --git a/target/ppc/translate.c b/target/ppc/translate.c
index 467b8f3d4e..48e5903214 100644
--- a/target/ppc/translate.c
+++ b/target/ppc/translate.c
@@ -187,6 +187,7 @@ struct DisasContext {
     bool fpu_enabled;
     bool altivec_enabled;
     bool vsx_enabled;
+    bool dm_enabled;
     bool spe_enabled;
     bool tm_enabled;
     bool gtse;
@@ -5023,6 +5024,7 @@ static void ppc_tr_init_disas_context(DisasContextBase 
*dcbase, CPUState *cs)
     ctx->spe_enabled = (hflags >> HFLAGS_SPE) & 1;
     ctx->altivec_enabled = (hflags >> HFLAGS_VR) & 1;
     ctx->vsx_enabled = (hflags >> HFLAGS_VSX) & 1;
+    ctx->dm_enabled = (hflags >> HFLAGS_DM) & 1;
     ctx->tm_enabled = (hflags >> HFLAGS_TM) & 1;
     ctx->gtse = (hflags >> HFLAGS_GTSE) & 1;
     ctx->hr = (hflags >> HFLAGS_HR) & 1;
-- 
2.55.0


Reply via email to