diff mbox

[Xen-devel,RFC,8/9] xen: arm: support for up to 48-bit physical addressing on arm64

Message ID 8541fa3183c9eae4ad5163b1d1da5f5563a3e5b2.1406728037.git.ian.campbell@citrix.com
State New
Headers show

Commit Message

Ian Campbell July 30, 2014, 1:47 p.m. UTC
This only affects Xen's own stage one paging.

- Use symbolic names for TCR bits for clarity.
- Update PADDR_BITS
- Base field of LPAE PT structs is now 36 bits (and therefore
  unsigned long long for arm32 compatibility)
- TCR_EL2.PS is set from ID_AA64MMFR0_EL1.PASize.
- Provide decode of ID_AA64MMFR0_EL1 in CPU info

Parts of this are derived from "xen/arm: Add 4-level page table for
stage 2 translation" by Vijaya Kumar K.

Signed-off-by: Ian Campbell <ian.campbell@citrix.com>
---
 xen/arch/arm/arm32/head.S       |    2 +-
 xen/arch/arm/arm64/head.S       |   10 ++++++---
 xen/include/asm-arm/page.h      |   16 ++++++++------
 xen/include/asm-arm/processor.h |   45 ++++++++++++++++++++++++++++++++++++++-
 4 files changed, 62 insertions(+), 11 deletions(-)
diff mbox

Patch

diff --git a/xen/arch/arm/arm32/head.S b/xen/arch/arm/arm32/head.S
index ec57974..8fbaf25 100644
--- a/xen/arch/arm/arm32/head.S
+++ b/xen/arch/arm/arm32/head.S
@@ -227,7 +227,7 @@  cpu_init_done:
          * PT walks use Inner-Shareable accesses,
          * PT walks are write-back, write-allocate in both cache levels,
          * Full 32-bit address space goes through this table. */
-        ldr   r0, =0x80003500
+        ldr   r0, =(TCR_RES1|TCR_SH0_IS|TCR_ORGN0_WBWA|TCR_IRGN0_WBWA|TCR_T0SZ(0))
         mcr   CP32(r0, HTCR)
 
         /* Set up the HSCTLR:
diff --git a/xen/arch/arm/arm64/head.S b/xen/arch/arm/arm64/head.S
index dcb7071..28e3e77 100644
--- a/xen/arch/arm/arm64/head.S
+++ b/xen/arch/arm/arm64/head.S
@@ -224,13 +224,17 @@  skip_bss:
         ldr   x0, =MAIRVAL
         msr   mair_el2, x0
 
-        /* Set up the HTCR:
-         * PASize -- 40 bits / 1TB
+        /* Set up TCR_EL2:
+         * PS -- Based on ID_AA64MMFR0_EL1.PARange
          * Top byte is used
          * PT walks use Inner-Shareable accesses,
          * PT walks are write-back, write-allocate in both cache levels,
          * Full 64-bit address space goes through this table. */
-        ldr   x0, =0x80823500
+        ldr   x0, =(TCR_RES1|TCR_SH0_IS|TCR_ORGN0_WBWA|TCR_IRGN0_WBWA|TCR_T0SZ(0))
+        /* ID_AA64MMFR0_EL1[3:0] (PARange) corresponds to TCR_EL2[18:16] (PS) */
+        mrs   x1, ID_AA64MMFR0_EL1
+        bfi   x0, x1, #16, #3
+
         msr   tcr_el2, x0
 
         /* Set up the SCTLR_EL2:
diff --git a/xen/include/asm-arm/page.h b/xen/include/asm-arm/page.h
index c1c8680..43a1ee9 100644
--- a/xen/include/asm-arm/page.h
+++ b/xen/include/asm-arm/page.h
@@ -6,7 +6,11 @@ 
 #include <public/xen.h>
 #include <asm/processor.h>
 
+#ifdef CONFIG_ARM_64
+#define PADDR_BITS              48
+#else
 #define PADDR_BITS              40
+#endif
 #define PADDR_MASK              ((1ULL << PADDR_BITS)-1)
 
 #define VADDR_BITS              32
@@ -114,8 +118,8 @@  typedef struct __packed {
     unsigned long ng:1;         /* Not-Global */
 
     /* The base address must be appropriately aligned for Block entries */
-    unsigned long base:28;      /* Base address of block or next table */
-    unsigned long sbz:12;       /* Must be zero */
+    unsigned long long base:36; /* Base address of block or next table */
+    unsigned long sbz:4;        /* Must be zero */
 
     /* These seven bits are only used in Block entries and are ignored
      * in Table entries. */
@@ -149,8 +153,8 @@  typedef struct __packed {
     unsigned long sbz4:1;
 
     /* The base address must be appropriately aligned for Block entries */
-    unsigned long base:28;      /* Base address of block or next table */
-    unsigned long sbz3:12;
+    unsigned long long base:36; /* Base address of block or next table */
+    unsigned long sbz3:4;
 
     /* These seven bits are only used in Block entries and are ignored
      * in Table entries. */
@@ -174,9 +178,9 @@  typedef struct __packed {
     unsigned long pad2:10;
 
     /* The base address must be appropriately aligned for Block entries */
-    unsigned long base:28;      /* Base address of block or next table */
+    unsigned long long base:36; /* Base address of block or next table */
 
-    unsigned long pad1:24;
+    unsigned long pad1:16;
 } lpae_walk_t;
 
 typedef union {
diff --git a/xen/include/asm-arm/processor.h b/xen/include/asm-arm/processor.h
index 9d230f3..979a41d 100644
--- a/xen/include/asm-arm/processor.h
+++ b/xen/include/asm-arm/processor.h
@@ -84,6 +84,38 @@ 
 #define HCR_SWIO        (_AC(1,UL)<<1) /* Set/Way Invalidation Override */
 #define HCR_VM          (_AC(1,UL)<<0) /* Virtual MMU Enable */
 
+/* TCR: Stage 1 Translation Control */
+
+#define TCR_T0SZ(x)     ((x)<<0)
+
+#define TCR_IRGN0_NC    (_AC(0x0,UL)<<8)
+#define TCR_IRGN0_WBWA  (_AC(0x1,UL)<<8)
+#define TCR_IRGN0_WT    (_AC(0x2,UL)<<8)
+#define TCR_IRGN0_WB    (_AC(0x3,UL)<<8)
+
+#define TCR_ORGN0_NC    (_AC(0x0,UL)<<10)
+#define TCR_ORGN0_WBWA  (_AC(0x1,UL)<<10)
+#define TCR_ORGN0_WT    (_AC(0x2,UL)<<10)
+#define TCR_ORGN0_WB    (_AC(0x3,UL)<<10)
+
+#define TCR_SH0_NS      (_AC(0x0,UL)<<12)
+#define TCR_SH0_OS      (_AC(0x2,UL)<<12)
+#define TCR_SH0_IS      (_AC(0x3,UL)<<12)
+
+#define TCR_TG0_4K      (_AC(0x0,UL)<<14)
+#define TCR_TG0_64K     (_AC(0x1,UL)<<14)
+#define TCR_TG0_16K     (_AC(0x2,UL)<<14)
+
+#define TCR_PS(x)       ((x)<<16)
+
+#define TCR_TBI         (_AC(0x1,UL)<<20)
+
+#ifdef CONFIG_ARM_64
+#define TCR_RES1        (_AC(1,UL)<<31|_AC(1,UL)<<23)
+#else
+#define TCR_RES1        (_AC(1,UL)<<31)
+#endif
+
 /* HCPTR Hyp. Coprocessor Trap Register */
 #define HCPTR_TTA       ((_AC(1,U)<<20))        /* Trap trace registers */
 #define HCPTR_CP(x)     ((_AC(1,U)<<(x)))       /* Trap Coprocessor x */
@@ -188,8 +220,19 @@  struct cpuinfo_arm {
         uint64_t bits[2];
     } aux64;
 
-    struct {
+    union {
         uint64_t bits[2];
+        struct {
+            unsigned long pa_range:4;
+            unsigned long asid_bits:4;
+            unsigned long bigend:4;
+            unsigned long secure_ns:4;
+            unsigned long bigend_el0:4;
+            unsigned long tgranule_16K:4;
+            unsigned long tgranule_64K:4;
+            unsigned long tgranule_4K:4;
+            unsigned long __res0:32;
+       };
     } mm64;
 
     struct {