target-mips: add MSA defines and data structure

add defines and data structure for MIPS SIMD Architecture

Reviewed-by: James Hogan <james.hogan@imgtec.com>
Signed-off-by: Yongbok Kim <yongbok.kim@imgtec.com>
Signed-off-by: Leon Alrae <leon.alrae@imgtec.com>
This commit is contained in:
Yongbok Kim 2014-11-01 05:28:35 +00:00 committed by Leon Alrae
parent 2d9e48bc04
commit e97a391d20
3 changed files with 52 additions and 2 deletions

View File

@ -58,12 +58,32 @@ struct CPUMIPSTLBContext {
}; };
#endif #endif
/* MSA Context */
#define MSA_WRLEN (128)
enum CPUMIPSMSADataFormat {
DF_BYTE = 0,
DF_HALF,
DF_WORD,
DF_DOUBLE
};
typedef union wr_t wr_t;
union wr_t {
int8_t b[MSA_WRLEN/8];
int16_t h[MSA_WRLEN/16];
int32_t w[MSA_WRLEN/32];
int64_t d[MSA_WRLEN/64];
};
typedef union fpr_t fpr_t; typedef union fpr_t fpr_t;
union fpr_t { union fpr_t {
float64 fd; /* ieee double precision */ float64 fd; /* ieee double precision */
float32 fs[2];/* ieee single precision */ float32 fs[2];/* ieee single precision */
uint64_t d; /* binary double fixed-point */ uint64_t d; /* binary double fixed-point */
uint32_t w[2]; /* binary single fixed-point */ uint32_t w[2]; /* binary single fixed-point */
/* FPU/MSA register mapping is not tested on big-endian hosts. */
wr_t wr; /* vector data */
}; };
/* define FP_ENDIAN_IDX to access the same location /* define FP_ENDIAN_IDX to access the same location
* in the fpr_t union regardless of the host endianness * in the fpr_t union regardless of the host endianness
@ -177,6 +197,21 @@ struct TCState {
target_ulong CP0_TCScheFBack; target_ulong CP0_TCScheFBack;
int32_t CP0_Debug_tcstatus; int32_t CP0_Debug_tcstatus;
target_ulong CP0_UserLocal; target_ulong CP0_UserLocal;
int32_t msacsr;
#define MSACSR_FS 24
#define MSACSR_FS_MASK (1 << MSACSR_FS)
#define MSACSR_NX 18
#define MSACSR_NX_MASK (1 << MSACSR_NX)
#define MSACSR_CEF 2
#define MSACSR_CEF_MASK (0xffff << MSACSR_CEF)
#define MSACSR_RM 0
#define MSACSR_RM_MASK (0x3 << MSACSR_RM)
#define MSACSR_MASK (MSACSR_RM_MASK | MSACSR_CEF_MASK | MSACSR_NX_MASK | \
MSACSR_FS_MASK)
float_status msa_fp_status;
}; };
typedef struct CPUMIPSState CPUMIPSState; typedef struct CPUMIPSState CPUMIPSState;
@ -192,6 +227,10 @@ struct CPUMIPSState {
target_ulong SEGMask; target_ulong SEGMask;
target_ulong PAMask; target_ulong PAMask;
int32_t msair;
#define MSAIR_ProcID 8
#define MSAIR_Rev 0
int32_t CP0_Index; int32_t CP0_Index;
/* CP0_MVP* are per MVP registers. */ /* CP0_MVP* are per MVP registers. */
int32_t CP0_Random; int32_t CP0_Random;
@ -385,6 +424,7 @@ struct CPUMIPSState {
#define CP0C2_SA 0 #define CP0C2_SA 0
int32_t CP0_Config3; int32_t CP0_Config3;
#define CP0C3_M 31 #define CP0C3_M 31
#define CP0C3_MSAP 28
#define CP0C3_BP 27 #define CP0C3_BP 27
#define CP0C3_BI 26 #define CP0C3_BI 26
#define CP0C3_ISA_ON_EXC 16 #define CP0C3_ISA_ON_EXC 16
@ -462,7 +502,7 @@ struct CPUMIPSState {
#define EXCP_INST_NOTAVAIL 0x2 /* No valid instruction word for BadInstr */ #define EXCP_INST_NOTAVAIL 0x2 /* No valid instruction word for BadInstr */
uint32_t hflags; /* CPU State */ uint32_t hflags; /* CPU State */
/* TMASK defines different execution modes */ /* TMASK defines different execution modes */
#define MIPS_HFLAG_TMASK 0x5807FF #define MIPS_HFLAG_TMASK 0x15807FF
#define MIPS_HFLAG_MODE 0x00007 /* execution modes */ #define MIPS_HFLAG_MODE 0x00007 /* execution modes */
/* The KSU flags must be the lowest bits in hflags. The flag order /* The KSU flags must be the lowest bits in hflags. The flag order
must be the same as defined for CP0 Status. This allows to use must be the same as defined for CP0 Status. This allows to use
@ -508,6 +548,7 @@ struct CPUMIPSState {
#define MIPS_HFLAG_HWRENA_ULR 0x200000 /* ULR bit from HWREna is set. */ #define MIPS_HFLAG_HWRENA_ULR 0x200000 /* ULR bit from HWREna is set. */
#define MIPS_HFLAG_SBRI 0x400000 /* R6 SDBBP causes RI excpt. in user mode */ #define MIPS_HFLAG_SBRI 0x400000 /* R6 SDBBP causes RI excpt. in user mode */
#define MIPS_HFLAG_FBNSLOT 0x800000 /* Forbidden slot */ #define MIPS_HFLAG_FBNSLOT 0x800000 /* Forbidden slot */
#define MIPS_HFLAG_MSA 0x1000000
target_ulong btarget; /* Jump / branch target */ target_ulong btarget; /* Jump / branch target */
target_ulong bcond; /* Branch condition (if needed) */ target_ulong bcond; /* Branch condition (if needed) */
@ -663,6 +704,8 @@ enum {
EXCP_C2E, EXCP_C2E,
EXCP_CACHE, /* 32 */ EXCP_CACHE, /* 32 */
EXCP_DSPDIS, EXCP_DSPDIS,
EXCP_MSADIS,
EXCP_MSAFPE,
EXCP_TLBXI, EXCP_TLBXI,
EXCP_TLBRI, EXCP_TLBRI,
@ -764,7 +807,7 @@ static inline void compute_hflags(CPUMIPSState *env)
env->hflags &= ~(MIPS_HFLAG_COP1X | MIPS_HFLAG_64 | MIPS_HFLAG_CP0 | env->hflags &= ~(MIPS_HFLAG_COP1X | MIPS_HFLAG_64 | MIPS_HFLAG_CP0 |
MIPS_HFLAG_F64 | MIPS_HFLAG_FPU | MIPS_HFLAG_KSU | MIPS_HFLAG_F64 | MIPS_HFLAG_FPU | MIPS_HFLAG_KSU |
MIPS_HFLAG_AWRAP | MIPS_HFLAG_DSP | MIPS_HFLAG_DSPR2 | MIPS_HFLAG_AWRAP | MIPS_HFLAG_DSP | MIPS_HFLAG_DSPR2 |
MIPS_HFLAG_SBRI); MIPS_HFLAG_SBRI | MIPS_HFLAG_MSA);
if (!(env->CP0_Status & (1 << CP0St_EXL)) && if (!(env->CP0_Status & (1 << CP0St_EXL)) &&
!(env->CP0_Status & (1 << CP0St_ERL)) && !(env->CP0_Status & (1 << CP0St_ERL)) &&
!(env->hflags & MIPS_HFLAG_DM)) { !(env->hflags & MIPS_HFLAG_DM)) {
@ -837,6 +880,11 @@ static inline void compute_hflags(CPUMIPSState *env)
env->hflags |= MIPS_HFLAG_COP1X; env->hflags |= MIPS_HFLAG_COP1X;
} }
} }
if (env->insn_flags & ASE_MSA) {
if (env->CP0_Config5 & (1 << CP0C5_MSAEn)) {
env->hflags |= MIPS_HFLAG_MSA;
}
}
} }
#endif /* !defined (__MIPS_CPU_H__) */ #endif /* !defined (__MIPS_CPU_H__) */

View File

@ -45,6 +45,7 @@
#define ASE_MT 0x00200000 #define ASE_MT 0x00200000
#define ASE_SMARTMIPS 0x00400000 #define ASE_SMARTMIPS 0x00400000
#define ASE_MICROMIPS 0x00800000 #define ASE_MICROMIPS 0x00800000
#define ASE_MSA 0x01000000
/* Chip specific instructions. */ /* Chip specific instructions. */
#define INSN_LOONGSON2E 0x20000000 #define INSN_LOONGSON2E 0x20000000

View File

@ -1589,6 +1589,7 @@ void helper_mtc0_config5(CPUMIPSState *env, target_ulong arg1)
{ {
env->CP0_Config5 = (env->CP0_Config5 & (~env->CP0_Config5_rw_bitmask)) | env->CP0_Config5 = (env->CP0_Config5 & (~env->CP0_Config5_rw_bitmask)) |
(arg1 & env->CP0_Config5_rw_bitmask); (arg1 & env->CP0_Config5_rw_bitmask);
compute_hflags(env);
} }
void helper_mtc0_lladdr(CPUMIPSState *env, target_ulong arg1) void helper_mtc0_lladdr(CPUMIPSState *env, target_ulong arg1)