Adds support in the identity mapping feature that allows KVM to setup
identity mapping for the Hyp mode with the AP[1] bit set as required by
the specification and also supports freeing created sub pmd's after
finished use.
---
 arch/arm/include/asm/pgtable-3level-hwdef.h |    1 +
 arch/arm/include/asm/pgtable.h              |    5 +++
 arch/arm/mm/idmap.c                         |   47 ++++++++++++++++++++++++++-
 3 files changed, 52 insertions(+), 1 deletions(-)

diff --git a/arch/arm/include/asm/pgtable-3level-hwdef.h 
b/arch/arm/include/asm/pgtable-3level-hwdef.h
index 6c0fb9b..9142208 100644
--- a/arch/arm/include/asm/pgtable-3level-hwdef.h
+++ b/arch/arm/include/asm/pgtable-3level-hwdef.h
@@ -48,6 +48,7 @@
 #endif
 #define PMD_SECT_AP_WRITE      (_AT(pmdval_t, 0))
 #define PMD_SECT_AP_READ       (_AT(pmdval_t, 0))
+#define PMD_SECT_AP1           (_AT(pmdval_t, 1) << 6)
 #define PMD_SECT_TEX(x)                (_AT(pmdval_t, 0))
 
 /*
diff --git a/arch/arm/include/asm/pgtable.h b/arch/arm/include/asm/pgtable.h
index 110f6f4..56081c0 100644
--- a/arch/arm/include/asm/pgtable.h
+++ b/arch/arm/include/asm/pgtable.h
@@ -403,6 +403,11 @@ static inline pte_t pte_modify(pte_t pte, pgprot_t newprot)
 void identity_mapping_add(pgd_t *, unsigned long, unsigned long);
 void identity_mapping_del(pgd_t *, unsigned long, unsigned long);
 
+#ifdef CONFIG_KVM
+void hyp_identity_mapping_add(pgd_t *, unsigned long, unsigned long);
+void hyp_identity_mapping_del(pgd_t *pgd, unsigned long addr, unsigned long 
end);
+#endif
+
 #endif /* !__ASSEMBLY__ */
 
 #endif /* CONFIG_MMU */
diff --git a/arch/arm/mm/idmap.c b/arch/arm/mm/idmap.c
index 834b803..66125d5 100644
--- a/arch/arm/mm/idmap.c
+++ b/arch/arm/mm/idmap.c
@@ -33,11 +33,16 @@ static void idmap_add_pmd(pgd_t *pgd, unsigned long addr, 
unsigned long end,
        flush_pmd_entry(pmd);
 }
 
-void identity_mapping_add(pgd_t *pgd, unsigned long addr, unsigned long end)
+static void __identity_mapping_add(pgd_t *pgd, unsigned long addr,
+                                  unsigned long end, bool hyp_mapping)
 {
        unsigned long prot, next;
 
        prot = PMD_TYPE_SECT | PMD_SECT_AP_WRITE | PMD_SECT_AF;
+
+       if (hyp_mapping)
+               prot |= PMD_SECT_AP1;
+
        if (cpu_architecture() <= CPU_ARCH_ARMv5TEJ && !cpu_is_xscale())
                prot |= PMD_BIT4;
 
@@ -47,6 +52,12 @@ void identity_mapping_add(pgd_t *pgd, unsigned long addr, 
unsigned long end)
        } while (addr = next, addr < end);
 }
 
+void identity_mapping_add(pgd_t *pgd, unsigned long addr, unsigned long end)
+{
+       __identity_mapping_add(pgd, addr, end, false);
+}
+
+
 #ifdef CONFIG_SMP
 static void idmap_del_pmd(pgd_t *pgd, unsigned long addr, unsigned long end)
 {
@@ -69,6 +80,40 @@ void identity_mapping_del(pgd_t *pgd, unsigned long addr, 
unsigned long end)
 }
 #endif
 
+#ifdef CONFIG_KVM
+void hyp_identity_mapping_add(pgd_t *pgd, unsigned long addr, unsigned long 
end)
+{
+       __identity_mapping_add(pgd, addr, end, true);
+}
+
+static void hyp_idmap_del_pmd(pgd_t *pgd, unsigned long addr)
+{
+       pmd_t *pmd;
+
+       pmd = pmd_offset(pgd, addr);
+       pmd_free(NULL, pmd);
+}
+
+/*
+ * This version actually frees the underlying pmds for all pgds in range and
+ * clear the pgds themselves afterwards.
+ */
+void hyp_identity_mapping_del(pgd_t *pgd, unsigned long addr, unsigned long 
end)
+{
+       unsigned long next;
+       pgd_t *next_pgd;
+
+       do {
+               next = pgd_addr_end(addr, end);
+               next_pgd = pgd + pgd_index(addr);
+               if (!pgd_none_or_clear_bad(next_pgd)) {
+                       hyp_idmap_del_pmd(next_pgd, addr);
+                       pgd_clear(next_pgd);
+               }
+       } while (addr = next, addr < end);
+}
+#endif
+
 /*
  * In order to soft-boot, we need to insert a 1:1 mapping in place of
  * the user-mode pages.  This will then ensure that we have predictable

--
To unsubscribe from this list: send the line "unsubscribe kvm" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to