* [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE
@ 2018-01-23 3:53 Richard Henderson
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 1/5] target/arm: Expand vector registers " Richard Henderson
` (5 more replies)
0 siblings, 6 replies; 16+ messages in thread
From: Richard Henderson @ 2018-01-23 3:53 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, alex.bennee
Based on PMM's target-arm.next branch, which now has most of v2.
While looking again at ZCR_ELx, I think that there's an existing
bug in the FPCR/FPSR system registers, wherein we do not have an
access function for when the FPU is disabled.
r~
Richard Henderson (5):
target/arm: Expand vector registers for SVE
target/arm: Add predicate registers for SVE
target/arm: Add SVE to migration state
target/arm: Add ZCR_ELx
target/arm: Add SVE state to TB->FLAGS
target/arm/cpu.h | 84 ++++++++++++++++++------
target/arm/translate.h | 2 +
target/arm/helper.c | 156 ++++++++++++++++++++++++++++++++++++++++++++-
target/arm/machine.c | 88 ++++++++++++++++++++++++-
target/arm/translate-a64.c | 10 +--
target/arm/translate.c | 7 +-
6 files changed, 318 insertions(+), 29 deletions(-)
--
2.14.3
^ permalink raw reply [flat|nested] 16+ messages in thread
* [Qemu-devel] [PATCH v3 1/5] target/arm: Expand vector registers for SVE
2018-01-23 3:53 [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE Richard Henderson
@ 2018-01-23 3:53 ` Richard Henderson
2018-01-29 17:30 ` Peter Maydell
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 2/5] target/arm: Add predicate " Richard Henderson
` (4 subsequent siblings)
5 siblings, 1 reply; 16+ messages in thread
From: Richard Henderson @ 2018-01-23 3:53 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, alex.bennee
Change vfp.regs as a uint64_t to vfp.zregs as an ARMVectorReg.
The previous patches have made the change in representation
relatively painless.
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
target/arm/cpu.h | 59 +++++++++++++++++++++++++++++++---------------
target/arm/machine.c | 35 ++++++++++++++++++++++++++-
target/arm/translate-a64.c | 8 +++----
target/arm/translate.c | 7 +++---
4 files changed, 81 insertions(+), 28 deletions(-)
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
index d2bb59eded..1854fe51a8 100644
--- a/target/arm/cpu.h
+++ b/target/arm/cpu.h
@@ -153,6 +153,42 @@ typedef struct {
uint32_t base_mask;
} TCR;
+/* Define a maximum sized vector register.
+ * For 32-bit, this is a 128-bit NEON/AdvSIMD register.
+ * For 64-bit, this is a 2048-bit SVE register.
+ *
+ * Note that the mapping between S, D, and Q views of the register bank
+ * differs between AArch64 and AArch32.
+ * In AArch32:
+ * Qn = regs[n].d[1]:regs[n].d[0]
+ * Dn = regs[n / 2].d[n & 1]
+ * Sn = regs[n / 4].d[n % 4 / 2],
+ * bits 31..0 for even n, and bits 63..32 for odd n
+ * (and regs[16] to regs[31] are inaccessible)
+ * In AArch64:
+ * Zn = regs[n].d[*]
+ * Qn = regs[n].d[1]:regs[n].d[0]
+ * Dn = regs[n].d[0]
+ * Sn = regs[n].d[0] bits 31..0
+ *
+ * This corresponds to the architecturally defined mapping between
+ * the two execution states, and means we do not need to explicitly
+ * map these registers when changing states.
+ *
+ * Align the data for use with TCG host vector operations.
+ */
+
+#ifdef TARGET_AARCH64
+# define ARM_MAX_VQ 16
+#else
+# define ARM_MAX_VQ 1
+#endif
+
+typedef struct ARMVectorReg {
+ uint64_t d[2 * ARM_MAX_VQ] QEMU_ALIGNED(16);
+} ARMVectorReg;
+
+
typedef struct CPUARMState {
/* Regs for current mode. */
uint32_t regs[16];
@@ -477,22 +513,7 @@ typedef struct CPUARMState {
/* VFP coprocessor state. */
struct {
- /* VFP/Neon register state. Note that the mapping between S, D and Q
- * views of the register bank differs between AArch64 and AArch32:
- * In AArch32:
- * Qn = regs[2n+1]:regs[2n]
- * Dn = regs[n]
- * Sn = regs[n/2] bits 31..0 for even n, and bits 63..32 for odd n
- * (and regs[32] to regs[63] are inaccessible)
- * In AArch64:
- * Qn = regs[2n+1]:regs[2n]
- * Dn = regs[2n]
- * Sn = regs[2n] bits 31..0
- * This corresponds to the architecturally defined mapping between
- * the two execution states, and means we do not need to explicitly
- * map these registers when changing states.
- */
- uint64_t regs[64];
+ ARMVectorReg zregs[32];
uint32_t xregs[16];
/* We store these fpcsr fields separately for convenience. */
@@ -2769,7 +2790,7 @@ static inline void *arm_get_el_change_hook_opaque(ARMCPU *cpu)
*/
static inline uint64_t *aa32_vfp_dreg(CPUARMState *env, unsigned regno)
{
- return &env->vfp.regs[regno];
+ return &env->vfp.zregs[regno >> 1].d[regno & 1];
}
/**
@@ -2778,7 +2799,7 @@ static inline uint64_t *aa32_vfp_dreg(CPUARMState *env, unsigned regno)
*/
static inline uint64_t *aa32_vfp_qreg(CPUARMState *env, unsigned regno)
{
- return &env->vfp.regs[2 * regno];
+ return &env->vfp.zregs[regno].d[0];
}
/**
@@ -2787,7 +2808,7 @@ static inline uint64_t *aa32_vfp_qreg(CPUARMState *env, unsigned regno)
*/
static inline uint64_t *aa64_vfp_qreg(CPUARMState *env, unsigned regno)
{
- return &env->vfp.regs[2 * regno];
+ return &env->vfp.zregs[regno].d[0];
}
#endif
diff --git a/target/arm/machine.c b/target/arm/machine.c
index a85c2430d3..cb0e1c92bb 100644
--- a/target/arm/machine.c
+++ b/target/arm/machine.c
@@ -50,7 +50,40 @@ static const VMStateDescription vmstate_vfp = {
.minimum_version_id = 3,
.needed = vfp_needed,
.fields = (VMStateField[]) {
- VMSTATE_UINT64_ARRAY(env.vfp.regs, ARMCPU, 64),
+ /* For compatibility, store Qn out of Zn here. */
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[0].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[1].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[2].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[3].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[4].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[5].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[6].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[7].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[8].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[9].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[10].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[11].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[12].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[13].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[14].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[15].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[16].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[17].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[18].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[19].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[20].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[21].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[22].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[23].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[24].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[25].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[26].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[27].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[28].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[29].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[30].d, ARMCPU, 0, 2),
+ VMSTATE_UINT64_SUB_ARRAY(env.vfp.zregs[31].d, ARMCPU, 0, 2),
+
/* The xregs array is a little awkward because element 1 (FPSCR)
* requires a specific accessor, so we have to split it up in
* the vmstate:
diff --git a/target/arm/translate-a64.c b/target/arm/translate-a64.c
index eed64c73e5..10eef870fe 100644
--- a/target/arm/translate-a64.c
+++ b/target/arm/translate-a64.c
@@ -517,8 +517,8 @@ static inline int vec_reg_offset(DisasContext *s, int regno,
{
int offs = 0;
#ifdef HOST_WORDS_BIGENDIAN
- /* This is complicated slightly because vfp.regs[2n] is
- * still the low half and vfp.regs[2n+1] the high half
+ /* This is complicated slightly because vfp.zregs[n].d[0] is
+ * still the low half and vfp.zregs[n].d[1] the high half
* of the 128 bit vector, even on big endian systems.
* Calculate the offset assuming a fully bigendian 128 bits,
* then XOR to account for the order of the two 64 bit halves.
@@ -528,7 +528,7 @@ static inline int vec_reg_offset(DisasContext *s, int regno,
#else
offs += element * (1 << size);
#endif
- offs += offsetof(CPUARMState, vfp.regs[regno * 2]);
+ offs += offsetof(CPUARMState, vfp.zregs[regno]);
assert_fp_access_checked(s);
return offs;
}
@@ -537,7 +537,7 @@ static inline int vec_reg_offset(DisasContext *s, int regno,
static inline int vec_full_reg_offset(DisasContext *s, int regno)
{
assert_fp_access_checked(s);
- return offsetof(CPUARMState, vfp.regs[regno * 2]);
+ return offsetof(CPUARMState, vfp.zregs[regno]);
}
/* Return a newly allocated pointer to the vector register. */
diff --git a/target/arm/translate.c b/target/arm/translate.c
index 55826b7e5a..a8c13d3758 100644
--- a/target/arm/translate.c
+++ b/target/arm/translate.c
@@ -1512,13 +1512,12 @@ static inline void gen_vfp_st(DisasContext *s, int dp, TCGv_i32 addr)
}
}
-static inline long
-vfp_reg_offset (int dp, int reg)
+static inline long vfp_reg_offset(bool dp, unsigned reg)
{
if (dp) {
- return offsetof(CPUARMState, vfp.regs[reg]);
+ return offsetof(CPUARMState, vfp.zregs[reg >> 1].d[reg & 1]);
} else {
- long ofs = offsetof(CPUARMState, vfp.regs[reg >> 1]);
+ long ofs = offsetof(CPUARMState, vfp.zregs[reg >> 2].d[(reg >> 1) & 1]);
if (reg & 1) {
ofs += offsetof(CPU_DoubleU, l.upper);
} else {
--
2.14.3
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [Qemu-devel] [PATCH v3 2/5] target/arm: Add predicate registers for SVE
2018-01-23 3:53 [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE Richard Henderson
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 1/5] target/arm: Expand vector registers " Richard Henderson
@ 2018-01-23 3:53 ` Richard Henderson
2018-01-23 11:46 ` Alex Bennée
2018-01-29 17:30 ` Peter Maydell
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 3/5] target/arm: Add SVE to migration state Richard Henderson
` (3 subsequent siblings)
5 siblings, 2 replies; 16+ messages in thread
From: Richard Henderson @ 2018-01-23 3:53 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, alex.bennee
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
target/arm/cpu.h | 12 ++++++++++++
1 file changed, 12 insertions(+)
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
index 1854fe51a8..3f4f6b6144 100644
--- a/target/arm/cpu.h
+++ b/target/arm/cpu.h
@@ -188,6 +188,13 @@ typedef struct ARMVectorReg {
uint64_t d[2 * ARM_MAX_VQ] QEMU_ALIGNED(16);
} ARMVectorReg;
+/* In AArch32 mode, predicate registers do not exist at all. */
+#ifdef TARGET_AARCH64
+typedef struct ARMPredicateReg {
+ uint64_t p[2 * ARM_MAX_VQ / 8] QEMU_ALIGNED(16);
+} ARMPredicateReg;
+#endif
+
typedef struct CPUARMState {
/* Regs for current mode. */
@@ -515,6 +522,11 @@ typedef struct CPUARMState {
struct {
ARMVectorReg zregs[32];
+#ifdef TARGET_AARCH64
+ /* Store FFR as pregs[16] to make it easier to treat as any other. */
+ ARMPredicateReg pregs[17];
+#endif
+
uint32_t xregs[16];
/* We store these fpcsr fields separately for convenience. */
int vec_len;
--
2.14.3
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [Qemu-devel] [PATCH v3 3/5] target/arm: Add SVE to migration state
2018-01-23 3:53 [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE Richard Henderson
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 1/5] target/arm: Expand vector registers " Richard Henderson
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 2/5] target/arm: Add predicate " Richard Henderson
@ 2018-01-23 3:53 ` Richard Henderson
2018-01-26 15:05 ` Alex Bennée
2018-01-29 17:32 ` Peter Maydell
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 4/5] target/arm: Add ZCR_ELx Richard Henderson
` (2 subsequent siblings)
5 siblings, 2 replies; 16+ messages in thread
From: Richard Henderson @ 2018-01-23 3:53 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, alex.bennee
Save the high parts of the Zregs and all of the Pregs.
The ZCR_ELx registers are migrated via the CP mechanism.
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
target/arm/machine.c | 53 ++++++++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 53 insertions(+)
diff --git a/target/arm/machine.c b/target/arm/machine.c
index cb0e1c92bb..2c8b43062f 100644
--- a/target/arm/machine.c
+++ b/target/arm/machine.c
@@ -122,6 +122,56 @@ static const VMStateDescription vmstate_iwmmxt = {
}
};
+#ifdef TARGET_AARCH64
+/* The expression ARM_MAX_VQ - 2 is 0 for pure AArch32 build,
+ * and ARMPredicateReg is actively empty. This triggers errors
+ * in the expansion of the VMSTATE macros.
+ */
+
+static bool sve_needed(void *opaque)
+{
+ ARMCPU *cpu = opaque;
+ CPUARMState *env = &cpu->env;
+
+ return arm_feature(env, ARM_FEATURE_SVE);
+}
+
+/* The first two words of each Zreg is stored in VFP state. */
+static const VMStateDescription vmstate_zreg_hi_reg = {
+ .name = "cpu/sve/zreg_hi",
+ .version_id = 1,
+ .minimum_version_id = 1,
+ .fields = (VMStateField[]) {
+ VMSTATE_UINT64_SUB_ARRAY(d, ARMVectorReg, 2, ARM_MAX_VQ - 2),
+ VMSTATE_END_OF_LIST()
+ }
+};
+
+static const VMStateDescription vmstate_preg_reg = {
+ .name = "cpu/sve/preg",
+ .version_id = 1,
+ .minimum_version_id = 1,
+ .fields = (VMStateField[]) {
+ VMSTATE_UINT64_ARRAY(p, ARMPredicateReg, 2 * ARM_MAX_VQ / 8),
+ VMSTATE_END_OF_LIST()
+ }
+};
+
+static const VMStateDescription vmstate_sve = {
+ .name = "cpu/sve",
+ .version_id = 1,
+ .minimum_version_id = 1,
+ .needed = sve_needed,
+ .fields = (VMStateField[]) {
+ VMSTATE_STRUCT_ARRAY(env.vfp.zregs, ARMCPU, 32, 0,
+ vmstate_zreg_hi_reg, ARMVectorReg),
+ VMSTATE_STRUCT_ARRAY(env.vfp.pregs, ARMCPU, 17, 0,
+ vmstate_preg_reg, ARMPredicateReg),
+ VMSTATE_END_OF_LIST()
+ }
+};
+#endif /* AARCH64 */
+
static bool m_needed(void *opaque)
{
ARMCPU *cpu = opaque;
@@ -586,6 +636,9 @@ const VMStateDescription vmstate_arm_cpu = {
&vmstate_pmsav7,
&vmstate_pmsav8,
&vmstate_m_security,
+#ifdef TARGET_AARCH64
+ &vmstate_sve,
+#endif
NULL
}
};
--
2.14.3
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [Qemu-devel] [PATCH v3 4/5] target/arm: Add ZCR_ELx
2018-01-23 3:53 [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE Richard Henderson
` (2 preceding siblings ...)
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 3/5] target/arm: Add SVE to migration state Richard Henderson
@ 2018-01-23 3:53 ` Richard Henderson
2018-01-23 16:23 ` Richard Henderson
2018-01-29 17:48 ` Peter Maydell
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 5/5] target/arm: Add SVE state to TB->FLAGS Richard Henderson
2018-02-08 14:34 ` [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE Peter Maydell
5 siblings, 2 replies; 16+ messages in thread
From: Richard Henderson @ 2018-01-23 3:53 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, alex.bennee
Define ZCR_EL[1-3].
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
target/arm/cpu.h | 5 ++
target/arm/helper.c | 131 ++++++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 136 insertions(+)
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
index 3f4f6b6144..17955ad3ef 100644
--- a/target/arm/cpu.h
+++ b/target/arm/cpu.h
@@ -549,6 +549,9 @@ typedef struct CPUARMState {
*/
float_status fp_status;
float_status standard_fp_status;
+
+ /* ZCR_EL[1-3] */
+ uint64_t zcr_el[4];
} vfp;
uint64_t exclusive_addr;
uint64_t exclusive_val;
@@ -923,6 +926,8 @@ void pmccntr_sync(CPUARMState *env);
#define CPTR_TCPAC (1U << 31)
#define CPTR_TTA (1U << 20)
#define CPTR_TFP (1U << 10)
+#define CPTR_TZ (1U << 8) /* CPTR_EL2 */
+#define CPTR_EZ (1U << 8) /* CPTR_EL3 */
#define MDCR_EPMAD (1U << 21)
#define MDCR_EDAD (1U << 20)
diff --git a/target/arm/helper.c b/target/arm/helper.c
index bfce09643b..db67e8ac72 100644
--- a/target/arm/helper.c
+++ b/target/arm/helper.c
@@ -4266,6 +4266,125 @@ static const ARMCPRegInfo debug_lpae_cp_reginfo[] = {
REGINFO_SENTINEL
};
+/* Return the exception level to which SVE-disabled exceptions should
+ * be taken, or 0 if SVE is enabled.
+ */
+static int sve_exception_el(CPUARMState *env)
+{
+#ifndef CONFIG_USER_ONLY
+ unsigned current_el = arm_current_el(env);
+
+ /* The CPACR.ZEN controls traps to EL1:
+ * 0, 2 : trap EL0 and EL1 accesses
+ * 1 : trap only EL0 accesses
+ * 3 : trap no accesses
+ */
+ switch (extract32(env->cp15.cpacr_el1, 16, 2)) {
+ default:
+ if (current_el <= 1) {
+ /* Trap to PL1, which might be EL1 or EL3 */
+ if (arm_is_secure(env) && !arm_el_is_aa64(env, 3)) {
+ return 3;
+ }
+ return 1;
+ }
+ break;
+ case 1:
+ if (current_el == 0) {
+ return 1;
+ }
+ break;
+ case 3:
+ break;
+ }
+
+ /* Similarly for CPACR.FPEN, after having checked ZEN. */
+ switch (extract32(env->cp15.cpacr_el1, 20, 2)) {
+ default:
+ if (current_el <= 1) {
+ if (arm_is_secure(env) && !arm_el_is_aa64(env, 3)) {
+ return 3;
+ }
+ return 1;
+ }
+ break;
+ case 1:
+ if (current_el == 0) {
+ return 1;
+ }
+ break;
+ case 3:
+ break;
+ }
+
+ /* CPTR_EL2. Check both TZ and TFP. */
+ if (current_el <= 2
+ && (env->cp15.cptr_el[2] & (CPTR_TFP | CPTR_TZ))
+ && !arm_is_secure_below_el3(env)) {
+ return 2;
+ }
+
+ /* CPTR_EL3. Check both EZ and TFP. */
+ if (!(env->cp15.cptr_el[3] & CPTR_EZ)
+ || (env->cp15.cptr_el[3] & CPTR_TFP)) {
+ return 3;
+ }
+#endif
+ return 0;
+}
+
+static CPAccessResult zcr_access(CPUARMState *env, const ARMCPRegInfo *ri,
+ bool isread)
+{
+ switch (sve_exception_el(env)) {
+ case 3:
+ return CP_ACCESS_TRAP_EL3;
+ case 2:
+ return CP_ACCESS_TRAP_EL2;
+ case 1:
+ return CP_ACCESS_TRAP;
+ }
+ return CP_ACCESS_OK;
+}
+
+static void zcr_write(CPUARMState *env, const ARMCPRegInfo *ri,
+ uint64_t value)
+{
+ /* Bits other than [3:0] are RAZ/WI. */
+ raw_write(env, ri, value & 0xf);
+}
+
+static const ARMCPRegInfo zcr_el1_reginfo = {
+ .name = "ZCR_EL1", .state = ARM_CP_STATE_AA64,
+ .opc0 = 3, .opc1 = 0, .crn = 1, .crm = 2, .opc2 = 0,
+ .access = PL1_RW, .accessfn = zcr_access, .type = ARM_CP_64BIT,
+ .fieldoffset = offsetof(CPUARMState, vfp.zcr_el[1]),
+ .writefn = zcr_write, .raw_writefn = raw_write
+};
+
+static const ARMCPRegInfo zcr_el2_reginfo = {
+ .name = "ZCR_EL2", .state = ARM_CP_STATE_AA64,
+ .opc0 = 3, .opc1 = 4, .crn = 1, .crm = 2, .opc2 = 0,
+ .access = PL2_RW, .accessfn = zcr_access, .type = ARM_CP_64BIT,
+ .fieldoffset = offsetof(CPUARMState, vfp.zcr_el[2]),
+ .writefn = zcr_write, .raw_writefn = raw_write
+};
+
+static const ARMCPRegInfo zcr_no_el2_reginfo = {
+ .name = "ZCR_EL2", .state = ARM_CP_STATE_AA64,
+ .opc0 = 3, .opc1 = 4, .crn = 1, .crm = 2, .opc2 = 0,
+ .access = PL2_RW, .type = ARM_CP_64BIT,
+ .readfn = arm_cp_read_zero, .writefn = arm_cp_write_ignore
+};
+
+static const ARMCPRegInfo zcr_el3_reginfo = {
+ .name = "ZCR_EL3", .state = ARM_CP_STATE_AA64,
+ .opc0 = 3, .opc1 = 6, .crn = 1, .crm = 2, .opc2 = 0,
+ .access = PL3_RW, .accessfn = zcr_access, .type = ARM_CP_64BIT,
+ .fieldoffset = offsetof(CPUARMState, vfp.zcr_el[3]),
+ .writefn = zcr_write, .raw_writefn = raw_write
+};
+
void hw_watchpoint_update(ARMCPU *cpu, int n)
{
CPUARMState *env = &cpu->env;
@@ -5332,6 +5451,18 @@ void register_cp_regs_for_features(ARMCPU *cpu)
}
define_one_arm_cp_reg(cpu, &sctlr);
}
+
+ if (arm_feature(env, ARM_FEATURE_SVE)) {
+ define_one_arm_cp_reg(cpu, &zcr_el1_reginfo);
+ if (arm_feature(env, ARM_FEATURE_EL2)) {
+ define_one_arm_cp_reg(cpu, &zcr_el2_reginfo);
+ } else {
+ define_one_arm_cp_reg(cpu, &zcr_no_el2_reginfo);
+ }
+ if (arm_feature(env, ARM_FEATURE_EL3)) {
+ define_one_arm_cp_reg(cpu, &zcr_el3_reginfo);
+ }
+ }
}
void arm_cpu_register_gdb_regs_for_features(ARMCPU *cpu)
--
2.14.3
^ permalink raw reply related [flat|nested] 16+ messages in thread
* [Qemu-devel] [PATCH v3 5/5] target/arm: Add SVE state to TB->FLAGS
2018-01-23 3:53 [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE Richard Henderson
` (3 preceding siblings ...)
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 4/5] target/arm: Add ZCR_ELx Richard Henderson
@ 2018-01-23 3:53 ` Richard Henderson
2018-01-29 18:01 ` Peter Maydell
2018-02-08 14:34 ` [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE Peter Maydell
5 siblings, 1 reply; 16+ messages in thread
From: Richard Henderson @ 2018-01-23 3:53 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, alex.bennee
Add both SVE exception state and vector length.
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
---
target/arm/cpu.h | 8 ++++++++
target/arm/translate.h | 2 ++
target/arm/helper.c | 25 ++++++++++++++++++++++++-
target/arm/translate-a64.c | 2 ++
4 files changed, 36 insertions(+), 1 deletion(-)
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
index 17955ad3ef..a311d4e327 100644
--- a/target/arm/cpu.h
+++ b/target/arm/cpu.h
@@ -2648,6 +2648,10 @@ static inline bool arm_cpu_data_is_big_endian(CPUARMState *env)
#define ARM_TBFLAG_TBI0_MASK (0x1ull << ARM_TBFLAG_TBI0_SHIFT)
#define ARM_TBFLAG_TBI1_SHIFT 1 /* TBI1 for EL0/1 */
#define ARM_TBFLAG_TBI1_MASK (0x1ull << ARM_TBFLAG_TBI1_SHIFT)
+#define ARM_TBFLAG_SVEEXC_EL_SHIFT 2
+#define ARM_TBFLAG_SVEEXC_EL_MASK (0x3 << ARM_TBFLAG_SVEEXC_EL_SHIFT)
+#define ARM_TBFLAG_ZCR_LEN_SHIFT 4
+#define ARM_TBFLAG_ZCR_LEN_MASK (0xf << ARM_TBFLAG_ZCR_LEN_SHIFT)
/* some convenience accessor macros */
#define ARM_TBFLAG_AARCH64_STATE(F) \
@@ -2684,6 +2688,10 @@ static inline bool arm_cpu_data_is_big_endian(CPUARMState *env)
(((F) & ARM_TBFLAG_TBI0_MASK) >> ARM_TBFLAG_TBI0_SHIFT)
#define ARM_TBFLAG_TBI1(F) \
(((F) & ARM_TBFLAG_TBI1_MASK) >> ARM_TBFLAG_TBI1_SHIFT)
+#define ARM_TBFLAG_SVEEXC_EL(F) \
+ (((F) & ARM_TBFLAG_SVEEXC_EL_MASK) >> ARM_TBFLAG_SVEEXC_EL_SHIFT)
+#define ARM_TBFLAG_ZCR_LEN(F) \
+ (((F) & ARM_TBFLAG_ZCR_LEN_MASK) >> ARM_TBFLAG_ZCR_LEN_SHIFT)
static inline bool bswap_code(bool sctlr_b)
{
diff --git a/target/arm/translate.h b/target/arm/translate.h
index 3f4df91e5e..c47febf99d 100644
--- a/target/arm/translate.h
+++ b/target/arm/translate.h
@@ -29,6 +29,8 @@ typedef struct DisasContext {
bool tbi1; /* TBI1 for EL0/1, not used for EL2/3 */
bool ns; /* Use non-secure CPREG bank on access */
int fp_excp_el; /* FP exception EL or 0 if enabled */
+ int sve_excp_el; /* SVE exception EL or 0 if enabled */
+ int sve_len; /* SVE vector length in bytes */
/* Flag indicating that exceptions from secure mode are routed to EL3. */
bool secure_routed_to_el3;
bool vfp_enabled; /* FP enabled via FPSCR.EN */
diff --git a/target/arm/helper.c b/target/arm/helper.c
index db67e8ac72..d46d3622fc 100644
--- a/target/arm/helper.c
+++ b/target/arm/helper.c
@@ -11823,14 +11823,37 @@ void cpu_get_tb_cpu_state(CPUARMState *env, target_ulong *pc,
target_ulong *cs_base, uint32_t *pflags)
{
ARMMMUIdx mmu_idx = core_to_arm_mmu_idx(env, cpu_mmu_index(env, false));
+ int fp_el = fp_exception_el(env);
uint32_t flags;
if (is_a64(env)) {
+ int sve_el = sve_exception_el(env);
+ uint32_t zcr_len;
+
*pc = env->pc;
flags = ARM_TBFLAG_AARCH64_STATE_MASK;
/* Get control bits for tagged addresses */
flags |= (arm_regime_tbi0(env, mmu_idx) << ARM_TBFLAG_TBI0_SHIFT);
flags |= (arm_regime_tbi1(env, mmu_idx) << ARM_TBFLAG_TBI1_SHIFT);
+ flags |= sve_el << ARM_TBFLAG_SVEEXC_EL_SHIFT;
+
+ /* If SVE is disabled, but FP is enabled,
+ then the effective len is 0. */
+ if (sve_el != 0 && fp_el == 0) {
+ zcr_len = 0;
+ } else {
+ int current_el = arm_current_el(env);
+
+ zcr_len = env->vfp.zcr_el[current_el <= 1 ? 1 : current_el];
+ zcr_len &= 0xf;
+ if (current_el < 2 && arm_feature(env, ARM_FEATURE_EL2)) {
+ zcr_len = MIN(zcr_len, 0xf & (uint32_t)env->vfp.zcr_el[2]);
+ }
+ if (current_el < 3 && arm_feature(env, ARM_FEATURE_EL3)) {
+ zcr_len = MIN(zcr_len, 0xf & (uint32_t)env->vfp.zcr_el[3]);
+ }
+ }
+ flags |= zcr_len << ARM_TBFLAG_ZCR_LEN_SHIFT;
} else {
*pc = env->regs[15];
flags = (env->thumb << ARM_TBFLAG_THUMB_SHIFT)
@@ -11873,7 +11896,7 @@ void cpu_get_tb_cpu_state(CPUARMState *env, target_ulong *pc,
if (arm_cpu_data_is_big_endian(env)) {
flags |= ARM_TBFLAG_BE_DATA_MASK;
}
- flags |= fp_exception_el(env) << ARM_TBFLAG_FPEXC_EL_SHIFT;
+ flags |= fp_el << ARM_TBFLAG_FPEXC_EL_SHIFT;
if (arm_v7m_is_handler_mode(env)) {
flags |= ARM_TBFLAG_HANDLER_MASK;
diff --git a/target/arm/translate-a64.c b/target/arm/translate-a64.c
index 10eef870fe..4c1eca7062 100644
--- a/target/arm/translate-a64.c
+++ b/target/arm/translate-a64.c
@@ -11263,6 +11263,8 @@ static int aarch64_tr_init_disas_context(DisasContextBase *dcbase,
dc->user = (dc->current_el == 0);
#endif
dc->fp_excp_el = ARM_TBFLAG_FPEXC_EL(dc->base.tb->flags);
+ dc->sve_excp_el = ARM_TBFLAG_SVEEXC_EL(dc->base.tb->flags);
+ dc->sve_len = (ARM_TBFLAG_ZCR_LEN(dc->base.tb->flags) + 1) * 16;
dc->vec_len = 0;
dc->vec_stride = 0;
dc->cp_regs = arm_cpu->cp_regs;
--
2.14.3
^ permalink raw reply related [flat|nested] 16+ messages in thread
* Re: [Qemu-devel] [PATCH v3 2/5] target/arm: Add predicate registers for SVE
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 2/5] target/arm: Add predicate " Richard Henderson
@ 2018-01-23 11:46 ` Alex Bennée
2018-01-29 17:30 ` Peter Maydell
1 sibling, 0 replies; 16+ messages in thread
From: Alex Bennée @ 2018-01-23 11:46 UTC (permalink / raw)
To: Richard Henderson; +Cc: qemu-devel, peter.maydell
Richard Henderson <richard.henderson@linaro.org> writes:
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
> ---
> target/arm/cpu.h | 12 ++++++++++++
> 1 file changed, 12 insertions(+)
>
> diff --git a/target/arm/cpu.h b/target/arm/cpu.h
> index 1854fe51a8..3f4f6b6144 100644
> --- a/target/arm/cpu.h
> +++ b/target/arm/cpu.h
> @@ -188,6 +188,13 @@ typedef struct ARMVectorReg {
> uint64_t d[2 * ARM_MAX_VQ] QEMU_ALIGNED(16);
> } ARMVectorReg;
>
> +/* In AArch32 mode, predicate registers do not exist at all. */
> +#ifdef TARGET_AARCH64
> +typedef struct ARMPredicateReg {
> + uint64_t p[2 * ARM_MAX_VQ / 8] QEMU_ALIGNED(16);
> +} ARMPredicateReg;
> +#endif
> +
>
> typedef struct CPUARMState {
> /* Regs for current mode. */
> @@ -515,6 +522,11 @@ typedef struct CPUARMState {
> struct {
> ARMVectorReg zregs[32];
>
> +#ifdef TARGET_AARCH64
> + /* Store FFR as pregs[16] to make it easier to treat as any other. */
> + ARMPredicateReg pregs[17];
> +#endif
> +
> uint32_t xregs[16];
> /* We store these fpcsr fields separately for convenience. */
> int vec_len;
--
Alex Bennée
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [Qemu-devel] [PATCH v3 4/5] target/arm: Add ZCR_ELx
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 4/5] target/arm: Add ZCR_ELx Richard Henderson
@ 2018-01-23 16:23 ` Richard Henderson
2018-01-29 17:48 ` Peter Maydell
1 sibling, 0 replies; 16+ messages in thread
From: Richard Henderson @ 2018-01-23 16:23 UTC (permalink / raw)
To: qemu-devel; +Cc: peter.maydell, alex.bennee
On 01/22/2018 07:53 PM, Richard Henderson wrote:
> +static const ARMCPRegInfo zcr_el1_reginfo = {
> + .name = "ZCR_EL1", .state = ARM_CP_STATE_AA64,
> + .opc0 = 3, .opc1 = 0, .crn = 1, .crm = 2, .opc2 = 0,
> + .access = PL1_RW, .accessfn = zcr_access, .type = ARM_CP_64BIT,
> + .fieldoffset = offsetof(CPUARMState, vfp.zcr_el[1]),
> + .writefn = zcr_write, .raw_writefn = raw_write
> +};
Ho hum. Got far enough in the rest of my rebasing to see that .type must be
dropped -- there's an assert saying STATE_AA64 implies 64BIT and shouldn't be
repeated.
r~
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [Qemu-devel] [PATCH v3 3/5] target/arm: Add SVE to migration state
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 3/5] target/arm: Add SVE to migration state Richard Henderson
@ 2018-01-26 15:05 ` Alex Bennée
2018-01-29 17:32 ` Peter Maydell
1 sibling, 0 replies; 16+ messages in thread
From: Alex Bennée @ 2018-01-26 15:05 UTC (permalink / raw)
To: Richard Henderson; +Cc: qemu-devel, peter.maydell
Richard Henderson <richard.henderson@linaro.org> writes:
> Save the high parts of the Zregs and all of the Pregs.
> The ZCR_ELx registers are migrated via the CP mechanism.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
> ---
> target/arm/machine.c | 53 ++++++++++++++++++++++++++++++++++++++++++++++++++++
> 1 file changed, 53 insertions(+)
>
> diff --git a/target/arm/machine.c b/target/arm/machine.c
> index cb0e1c92bb..2c8b43062f 100644
> --- a/target/arm/machine.c
> +++ b/target/arm/machine.c
> @@ -122,6 +122,56 @@ static const VMStateDescription vmstate_iwmmxt = {
> }
> };
>
> +#ifdef TARGET_AARCH64
> +/* The expression ARM_MAX_VQ - 2 is 0 for pure AArch32 build,
> + * and ARMPredicateReg is actively empty. This triggers errors
> + * in the expansion of the VMSTATE macros.
> + */
> +
> +static bool sve_needed(void *opaque)
> +{
> + ARMCPU *cpu = opaque;
> + CPUARMState *env = &cpu->env;
> +
> + return arm_feature(env, ARM_FEATURE_SVE);
> +}
> +
> +/* The first two words of each Zreg is stored in VFP state. */
> +static const VMStateDescription vmstate_zreg_hi_reg = {
> + .name = "cpu/sve/zreg_hi",
> + .version_id = 1,
> + .minimum_version_id = 1,
> + .fields = (VMStateField[]) {
> + VMSTATE_UINT64_SUB_ARRAY(d, ARMVectorReg, 2, ARM_MAX_VQ - 2),
> + VMSTATE_END_OF_LIST()
> + }
> +};
> +
> +static const VMStateDescription vmstate_preg_reg = {
> + .name = "cpu/sve/preg",
> + .version_id = 1,
> + .minimum_version_id = 1,
> + .fields = (VMStateField[]) {
> + VMSTATE_UINT64_ARRAY(p, ARMPredicateReg, 2 * ARM_MAX_VQ / 8),
> + VMSTATE_END_OF_LIST()
> + }
> +};
> +
> +static const VMStateDescription vmstate_sve = {
> + .name = "cpu/sve",
> + .version_id = 1,
> + .minimum_version_id = 1,
> + .needed = sve_needed,
> + .fields = (VMStateField[]) {
> + VMSTATE_STRUCT_ARRAY(env.vfp.zregs, ARMCPU, 32, 0,
> + vmstate_zreg_hi_reg, ARMVectorReg),
> + VMSTATE_STRUCT_ARRAY(env.vfp.pregs, ARMCPU, 17, 0,
> + vmstate_preg_reg, ARMPredicateReg),
> + VMSTATE_END_OF_LIST()
> + }
> +};
> +#endif /* AARCH64 */
> +
> static bool m_needed(void *opaque)
> {
> ARMCPU *cpu = opaque;
> @@ -586,6 +636,9 @@ const VMStateDescription vmstate_arm_cpu = {
> &vmstate_pmsav7,
> &vmstate_pmsav8,
> &vmstate_m_security,
> +#ifdef TARGET_AARCH64
> + &vmstate_sve,
> +#endif
> NULL
> }
> };
--
Alex Bennée
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [Qemu-devel] [PATCH v3 1/5] target/arm: Expand vector registers for SVE
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 1/5] target/arm: Expand vector registers " Richard Henderson
@ 2018-01-29 17:30 ` Peter Maydell
0 siblings, 0 replies; 16+ messages in thread
From: Peter Maydell @ 2018-01-29 17:30 UTC (permalink / raw)
To: Richard Henderson; +Cc: QEMU Developers, Alex Bennée
On 23 January 2018 at 03:53, Richard Henderson
<richard.henderson@linaro.org> wrote:
> Change vfp.regs as a uint64_t to vfp.zregs as an ARMVectorReg.
> The previous patches have made the change in representation
> relatively painless.
>
> Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
> target/arm/cpu.h | 59 +++++++++++++++++++++++++++++++---------------
> target/arm/machine.c | 35 ++++++++++++++++++++++++++-
> target/arm/translate-a64.c | 8 +++----
> target/arm/translate.c | 7 +++---
> 4 files changed, 81 insertions(+), 28 deletions(-)
>
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
thanks
-- PMM
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [Qemu-devel] [PATCH v3 2/5] target/arm: Add predicate registers for SVE
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 2/5] target/arm: Add predicate " Richard Henderson
2018-01-23 11:46 ` Alex Bennée
@ 2018-01-29 17:30 ` Peter Maydell
1 sibling, 0 replies; 16+ messages in thread
From: Peter Maydell @ 2018-01-29 17:30 UTC (permalink / raw)
To: Richard Henderson; +Cc: QEMU Developers, Alex Bennée
On 23 January 2018 at 03:53, Richard Henderson
<richard.henderson@linaro.org> wrote:
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
> target/arm/cpu.h | 12 ++++++++++++
> 1 file changed, 12 insertions(+)
>
> diff --git a/target/arm/cpu.h b/target/arm/cpu.h
> index 1854fe51a8..3f4f6b6144 100644
> --- a/target/arm/cpu.h
> +++ b/target/arm/cpu.h
> @@ -188,6 +188,13 @@ typedef struct ARMVectorReg {
> uint64_t d[2 * ARM_MAX_VQ] QEMU_ALIGNED(16);
> } ARMVectorReg;
>
> +/* In AArch32 mode, predicate registers do not exist at all. */
> +#ifdef TARGET_AARCH64
> +typedef struct ARMPredicateReg {
> + uint64_t p[2 * ARM_MAX_VQ / 8] QEMU_ALIGNED(16);
> +} ARMPredicateReg;
> +#endif
> +
>
> typedef struct CPUARMState {
> /* Regs for current mode. */
> @@ -515,6 +522,11 @@ typedef struct CPUARMState {
> struct {
> ARMVectorReg zregs[32];
>
> +#ifdef TARGET_AARCH64
> + /* Store FFR as pregs[16] to make it easier to treat as any other. */
> + ARMPredicateReg pregs[17];
> +#endif
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
thanks
-- PMM
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [Qemu-devel] [PATCH v3 3/5] target/arm: Add SVE to migration state
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 3/5] target/arm: Add SVE to migration state Richard Henderson
2018-01-26 15:05 ` Alex Bennée
@ 2018-01-29 17:32 ` Peter Maydell
1 sibling, 0 replies; 16+ messages in thread
From: Peter Maydell @ 2018-01-29 17:32 UTC (permalink / raw)
To: Richard Henderson; +Cc: QEMU Developers, Alex Bennée
On 23 January 2018 at 03:53, Richard Henderson
<richard.henderson@linaro.org> wrote:
> Save the high parts of the Zregs and all of the Pregs.
> The ZCR_ELx registers are migrated via the CP mechanism.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
> target/arm/machine.c | 53 ++++++++++++++++++++++++++++++++++++++++++++++++++++
> 1 file changed, 53 insertions(+)
>
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
thanks
-- PMM
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [Qemu-devel] [PATCH v3 4/5] target/arm: Add ZCR_ELx
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 4/5] target/arm: Add ZCR_ELx Richard Henderson
2018-01-23 16:23 ` Richard Henderson
@ 2018-01-29 17:48 ` Peter Maydell
1 sibling, 0 replies; 16+ messages in thread
From: Peter Maydell @ 2018-01-29 17:48 UTC (permalink / raw)
To: Richard Henderson; +Cc: QEMU Developers, Alex Bennée
On 23 January 2018 at 03:53, Richard Henderson
<richard.henderson@linaro.org> wrote:
> Define ZCR_EL[1-3].
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> ---
> target/arm/cpu.h | 5 ++
> target/arm/helper.c | 131 ++++++++++++++++++++++++++++++++++++++++++++++++++++
> 2 files changed, 136 insertions(+)
>
Apart from the issue you've noticed about not wanting to specify
.type:
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
thanks
-- PMM
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [Qemu-devel] [PATCH v3 5/5] target/arm: Add SVE state to TB->FLAGS
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 5/5] target/arm: Add SVE state to TB->FLAGS Richard Henderson
@ 2018-01-29 18:01 ` Peter Maydell
2018-01-29 18:16 ` Richard Henderson
0 siblings, 1 reply; 16+ messages in thread
From: Peter Maydell @ 2018-01-29 18:01 UTC (permalink / raw)
To: Richard Henderson; +Cc: QEMU Developers, Alex Bennée
On 23 January 2018 at 03:53, Richard Henderson
<richard.henderson@linaro.org> wrote:
> Add both SVE exception state and vector length.
>
> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
> diff --git a/target/arm/translate-a64.c b/target/arm/translate-a64.c
> index 10eef870fe..4c1eca7062 100644
> --- a/target/arm/translate-a64.c
> +++ b/target/arm/translate-a64.c
> @@ -11263,6 +11263,8 @@ static int aarch64_tr_init_disas_context(DisasContextBase *dcbase,
> dc->user = (dc->current_el == 0);
> #endif
> dc->fp_excp_el = ARM_TBFLAG_FPEXC_EL(dc->base.tb->flags);
> + dc->sve_excp_el = ARM_TBFLAG_SVEEXC_EL(dc->base.tb->flags);
> + dc->sve_len = (ARM_TBFLAG_ZCR_LEN(dc->base.tb->flags) + 1) * 16;
You've carefully arranged that the sve_excp checks are a superset
of the fp_excp checks, which means that we get the correct
exception prioritization by always doing the sve_excp check first
and then the fp_excp check second, without having to look at
whether fp_excp_el or sve_excp_el is larger to see which should
take precedence. We could
assert(dc->sve_excp_el <= dc->fp_excp_el);
and perhaps have a comment noting why this is useful...
Otherwise
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
thanks
-- PMM
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [Qemu-devel] [PATCH v3 5/5] target/arm: Add SVE state to TB->FLAGS
2018-01-29 18:01 ` Peter Maydell
@ 2018-01-29 18:16 ` Richard Henderson
0 siblings, 0 replies; 16+ messages in thread
From: Richard Henderson @ 2018-01-29 18:16 UTC (permalink / raw)
To: Peter Maydell; +Cc: QEMU Developers, Alex Bennée
On 01/29/2018 10:01 AM, Peter Maydell wrote:
> On 23 January 2018 at 03:53, Richard Henderson
> <richard.henderson@linaro.org> wrote:
>> Add both SVE exception state and vector length.
>>
>> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
>
>> diff --git a/target/arm/translate-a64.c b/target/arm/translate-a64.c
>> index 10eef870fe..4c1eca7062 100644
>> --- a/target/arm/translate-a64.c
>> +++ b/target/arm/translate-a64.c
>> @@ -11263,6 +11263,8 @@ static int aarch64_tr_init_disas_context(DisasContextBase *dcbase,
>> dc->user = (dc->current_el == 0);
>> #endif
>> dc->fp_excp_el = ARM_TBFLAG_FPEXC_EL(dc->base.tb->flags);
>> + dc->sve_excp_el = ARM_TBFLAG_SVEEXC_EL(dc->base.tb->flags);
>> + dc->sve_len = (ARM_TBFLAG_ZCR_LEN(dc->base.tb->flags) + 1) * 16;
>
> You've carefully arranged that the sve_excp checks are a superset
> of the fp_excp checks, which means that we get the correct
> exception prioritization by always doing the sve_excp check first
> and then the fp_excp check second, without having to look at
> whether fp_excp_el or sve_excp_el is larger to see which should
> take precedence. We could
> assert(dc->sve_excp_el <= dc->fp_excp_el);
> and perhaps have a comment noting why this is useful...
Sort of, I suppose. Modulo the fact that "enabled" is zero,
so sve disabled & fp enabled means sve_el > fp_el.
But you're right that to some extent I'm doing too much work
replicating the fp exception check.
r~
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE
2018-01-23 3:53 [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE Richard Henderson
` (4 preceding siblings ...)
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 5/5] target/arm: Add SVE state to TB->FLAGS Richard Henderson
@ 2018-02-08 14:34 ` Peter Maydell
5 siblings, 0 replies; 16+ messages in thread
From: Peter Maydell @ 2018-02-08 14:34 UTC (permalink / raw)
To: Richard Henderson; +Cc: QEMU Developers, Alex Bennée
On 23 January 2018 at 03:53, Richard Henderson
<richard.henderson@linaro.org> wrote:
> Based on PMM's target-arm.next branch, which now has most of v2.
>
> While looking again at ZCR_ELx, I think that there's an existing
> bug in the FPCR/FPSR system registers, wherein we do not have an
> access function for when the FPU is disabled.
Applied to target-arm.next, thanks.
-- PMM
^ permalink raw reply [flat|nested] 16+ messages in thread
end of thread, other threads:[~2018-02-08 14:34 UTC | newest]
Thread overview: 16+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2018-01-23 3:53 [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE Richard Henderson
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 1/5] target/arm: Expand vector registers " Richard Henderson
2018-01-29 17:30 ` Peter Maydell
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 2/5] target/arm: Add predicate " Richard Henderson
2018-01-23 11:46 ` Alex Bennée
2018-01-29 17:30 ` Peter Maydell
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 3/5] target/arm: Add SVE to migration state Richard Henderson
2018-01-26 15:05 ` Alex Bennée
2018-01-29 17:32 ` Peter Maydell
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 4/5] target/arm: Add ZCR_ELx Richard Henderson
2018-01-23 16:23 ` Richard Henderson
2018-01-29 17:48 ` Peter Maydell
2018-01-23 3:53 ` [Qemu-devel] [PATCH v3 5/5] target/arm: Add SVE state to TB->FLAGS Richard Henderson
2018-01-29 18:01 ` Peter Maydell
2018-01-29 18:16 ` Richard Henderson
2018-02-08 14:34 ` [Qemu-devel] [PATCH v3 0/5] target/arm: Preparatory work for SVE Peter Maydell
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).