diff mbox

[v6,24/37] target-arm: Implement AArch64 view of CONTEXTIDR

Message ID 1397146536-30116-25-git-send-email-peter.maydell@linaro.org
State Superseded
Headers show

Commit Message

Peter Maydell April 10, 2014, 4:15 p.m. UTC
Implement AArch64 view of the CONTEXTIDR register.
We tighten up the condition when we flush the TLB on a CONTEXTIDR
write to avoid needlessly flushing the TLB every time on a 64
bit system (and also on a 32 bit system using LPAE, as a bonus).

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
 target-arm/cpu.h    |  2 +-
 target-arm/helper.c | 33 ++++++++++++++++++---------------
 2 files changed, 19 insertions(+), 16 deletions(-)

Comments

Peter Crosthwaite April 14, 2014, 6:16 a.m. UTC | #1
On Fri, Apr 11, 2014 at 2:15 AM, Peter Maydell <peter.maydell@linaro.org> wrote:
> Implement AArch64 view of the CONTEXTIDR register.
> We tighten up the condition when we flush the TLB on a CONTEXTIDR
> write to avoid needlessly flushing the TLB every time on a 64
> bit system (and also on a 32 bit system using LPAE, as a bonus).
>
> Signed-off-by: Peter Maydell <peter.maydell@linaro.org>

Reviewed-by: Peter Crosthwaite <peter.crosthwaite@xilinx.com>

> ---
>  target-arm/cpu.h    |  2 +-
>  target-arm/helper.c | 33 ++++++++++++++++++---------------
>  2 files changed, 19 insertions(+), 16 deletions(-)
>
> diff --git a/target-arm/cpu.h b/target-arm/cpu.h
> index ec0306b..d0f42fd 100644
> --- a/target-arm/cpu.h
> +++ b/target-arm/cpu.h
> @@ -201,7 +201,7 @@ typedef struct CPUARMState {
>          uint64_t mair_el1;
>          uint64_t c12_vbar; /* vector base address register */
>          uint32_t c13_fcse; /* FCSE PID.  */
> -        uint32_t c13_context; /* Context ID.  */
> +        uint64_t contextidr_el1; /* Context ID.  */
>          uint64_t tpidr_el0; /* User RW Thread register.  */
>          uint64_t tpidrro_el0; /* User RO Thread register.  */
>          uint64_t tpidr_el1; /* Privileged Thread register.  */
> diff --git a/target-arm/helper.c b/target-arm/helper.c
> index 655c5ab..10300aa 100644
> --- a/target-arm/helper.c
> +++ b/target-arm/helper.c
> @@ -304,6 +304,17 @@ void init_cpreg_list(ARMCPU *cpu)
>      g_list_free(keys);
>  }
>
> +/* Return true if extended addresses are enabled.
> + * This is always the case if our translation regime is 64 bit,
> + * but depends on TTBCR.EAE for 32 bit.
> + */
> +static inline bool extended_addresses_enabled(CPUARMState *env)
> +{
> +    return arm_el_is_aa64(env, 1)
> +        || ((arm_feature(env, ARM_FEATURE_LPAE)
> +             && (env->cp15.c2_control & (1U << 31))));
> +}
> +
>  static void dacr_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
>  {
>      ARMCPU *cpu = arm_env_get_cpu(env);
> @@ -330,14 +341,15 @@ static void contextidr_write(CPUARMState *env, const ARMCPRegInfo *ri,
>  {
>      ARMCPU *cpu = arm_env_get_cpu(env);
>
> -    if (env->cp15.c13_context != value && !arm_feature(env, ARM_FEATURE_MPU)) {
> +    if (env->cp15.contextidr_el1 != value && !arm_feature(env, ARM_FEATURE_MPU)
> +        && !extended_addresses_enabled(env)) {
>          /* For VMSA (when not using the LPAE long descriptor page table
>           * format) this register includes the ASID, so do a TLB flush.
>           * For PMSA it is purely a process ID and no action is needed.
>           */
>          tlb_flush(CPU(cpu), 1);
>      }
> -    env->cp15.c13_context = value;
> +    env->cp15.contextidr_el1 = value;
>  }
>
>  static void tlbiall_write(CPUARMState *env, const ARMCPRegInfo *ri,
> @@ -391,8 +403,10 @@ static const ARMCPRegInfo cp_reginfo[] = {
>      { .name = "FCSEIDR", .cp = 15, .crn = 13, .crm = 0, .opc1 = 0, .opc2 = 0,
>        .access = PL1_RW, .fieldoffset = offsetof(CPUARMState, cp15.c13_fcse),
>        .resetvalue = 0, .writefn = fcse_write, .raw_writefn = raw_write, },
> -    { .name = "CONTEXTIDR", .cp = 15, .crn = 13, .crm = 0, .opc1 = 0, .opc2 = 1,
> -      .access = PL1_RW, .fieldoffset = offsetof(CPUARMState, cp15.c13_context),
> +    { .name = "CONTEXTIDR", .state = ARM_CP_STATE_BOTH,
> +      .opc0 = 3, .opc1 = 0, .crn = 13, .crm = 0, .opc2 = 1,
> +      .access = PL1_RW,
> +      .fieldoffset = offsetof(CPUARMState, cp15.contextidr_el1),
>        .resetvalue = 0, .writefn = contextidr_write, .raw_writefn = raw_write, },
>      /* ??? This covers not just the impdef TLB lockdown registers but also
>       * some v7VMSA registers relating to TEX remap, so it is overly broad.
> @@ -1155,17 +1169,6 @@ static void par_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
>  #ifndef CONFIG_USER_ONLY
>  /* get_phys_addr() isn't present for user-mode-only targets */
>
> -/* Return true if extended addresses are enabled.
> - * This is always the case if our translation regime is 64 bit,
> - * but depends on TTBCR.EAE for 32 bit.
> - */
> -static inline bool extended_addresses_enabled(CPUARMState *env)
> -{
> -    return arm_el_is_aa64(env, 1)
> -        || ((arm_feature(env, ARM_FEATURE_LPAE)
> -             && (env->cp15.c2_control & (1U << 31))));
> -}
> -
>  static CPAccessResult ats_access(CPUARMState *env, const ARMCPRegInfo *ri)
>  {
>      if (ri->opc2 & 4) {
> --
> 1.9.1
>
>
diff mbox

Patch

diff --git a/target-arm/cpu.h b/target-arm/cpu.h
index ec0306b..d0f42fd 100644
--- a/target-arm/cpu.h
+++ b/target-arm/cpu.h
@@ -201,7 +201,7 @@  typedef struct CPUARMState {
         uint64_t mair_el1;
         uint64_t c12_vbar; /* vector base address register */
         uint32_t c13_fcse; /* FCSE PID.  */
-        uint32_t c13_context; /* Context ID.  */
+        uint64_t contextidr_el1; /* Context ID.  */
         uint64_t tpidr_el0; /* User RW Thread register.  */
         uint64_t tpidrro_el0; /* User RO Thread register.  */
         uint64_t tpidr_el1; /* Privileged Thread register.  */
diff --git a/target-arm/helper.c b/target-arm/helper.c
index 655c5ab..10300aa 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -304,6 +304,17 @@  void init_cpreg_list(ARMCPU *cpu)
     g_list_free(keys);
 }
 
+/* Return true if extended addresses are enabled.
+ * This is always the case if our translation regime is 64 bit,
+ * but depends on TTBCR.EAE for 32 bit.
+ */
+static inline bool extended_addresses_enabled(CPUARMState *env)
+{
+    return arm_el_is_aa64(env, 1)
+        || ((arm_feature(env, ARM_FEATURE_LPAE)
+             && (env->cp15.c2_control & (1U << 31))));
+}
+
 static void dacr_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
 {
     ARMCPU *cpu = arm_env_get_cpu(env);
@@ -330,14 +341,15 @@  static void contextidr_write(CPUARMState *env, const ARMCPRegInfo *ri,
 {
     ARMCPU *cpu = arm_env_get_cpu(env);
 
-    if (env->cp15.c13_context != value && !arm_feature(env, ARM_FEATURE_MPU)) {
+    if (env->cp15.contextidr_el1 != value && !arm_feature(env, ARM_FEATURE_MPU)
+        && !extended_addresses_enabled(env)) {
         /* For VMSA (when not using the LPAE long descriptor page table
          * format) this register includes the ASID, so do a TLB flush.
          * For PMSA it is purely a process ID and no action is needed.
          */
         tlb_flush(CPU(cpu), 1);
     }
-    env->cp15.c13_context = value;
+    env->cp15.contextidr_el1 = value;
 }
 
 static void tlbiall_write(CPUARMState *env, const ARMCPRegInfo *ri,
@@ -391,8 +403,10 @@  static const ARMCPRegInfo cp_reginfo[] = {
     { .name = "FCSEIDR", .cp = 15, .crn = 13, .crm = 0, .opc1 = 0, .opc2 = 0,
       .access = PL1_RW, .fieldoffset = offsetof(CPUARMState, cp15.c13_fcse),
       .resetvalue = 0, .writefn = fcse_write, .raw_writefn = raw_write, },
-    { .name = "CONTEXTIDR", .cp = 15, .crn = 13, .crm = 0, .opc1 = 0, .opc2 = 1,
-      .access = PL1_RW, .fieldoffset = offsetof(CPUARMState, cp15.c13_context),
+    { .name = "CONTEXTIDR", .state = ARM_CP_STATE_BOTH,
+      .opc0 = 3, .opc1 = 0, .crn = 13, .crm = 0, .opc2 = 1,
+      .access = PL1_RW,
+      .fieldoffset = offsetof(CPUARMState, cp15.contextidr_el1),
       .resetvalue = 0, .writefn = contextidr_write, .raw_writefn = raw_write, },
     /* ??? This covers not just the impdef TLB lockdown registers but also
      * some v7VMSA registers relating to TEX remap, so it is overly broad.
@@ -1155,17 +1169,6 @@  static void par_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
 #ifndef CONFIG_USER_ONLY
 /* get_phys_addr() isn't present for user-mode-only targets */
 
-/* Return true if extended addresses are enabled.
- * This is always the case if our translation regime is 64 bit,
- * but depends on TTBCR.EAE for 32 bit.
- */
-static inline bool extended_addresses_enabled(CPUARMState *env)
-{
-    return arm_el_is_aa64(env, 1)
-        || ((arm_feature(env, ARM_FEATURE_LPAE)
-             && (env->cp15.c2_control & (1U << 31))));
-}
-
 static CPAccessResult ats_access(CPUARMState *env, const ARMCPRegInfo *ri)
 {
     if (ri->opc2 & 4) {