summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to '0069-xen-arm-p2m-Populate-pages-for-GICv2-mapping-in-p2m_.patch')
-rw-r--r--0069-xen-arm-p2m-Populate-pages-for-GICv2-mapping-in-p2m_.patch169
1 files changed, 0 insertions, 169 deletions
diff --git a/0069-xen-arm-p2m-Populate-pages-for-GICv2-mapping-in-p2m_.patch b/0069-xen-arm-p2m-Populate-pages-for-GICv2-mapping-in-p2m_.patch
deleted file mode 100644
index 67cdb7a..0000000
--- a/0069-xen-arm-p2m-Populate-pages-for-GICv2-mapping-in-p2m_.patch
+++ /dev/null
@@ -1,169 +0,0 @@
-From f8915cd5dbe0f51e9bb31a54fe40600b839dd707 Mon Sep 17 00:00:00 2001
-From: Henry Wang <Henry.Wang@arm.com>
-Date: Tue, 25 Oct 2022 09:21:12 +0000
-Subject: [PATCH 069/126] xen/arm: p2m: Populate pages for GICv2 mapping in
- p2m_init()
-
-Hardware using GICv2 needs to create a P2M mapping of 8KB GICv2 area
-when the domain is created. Considering the worst case of page tables
-which requires 6 P2M pages as the two pages will be consecutive but not
-necessarily in the same L3 page table and keep a buffer, populate 16
-pages as the default value to the P2M pages pool in p2m_init() at the
-domain creation stage to satisfy the GICv2 requirement. For GICv3, the
-above-mentioned P2M mapping is not necessary, but since the allocated
-16 pages here would not be lost, hence populate these pages
-unconditionally.
-
-With the default 16 P2M pages populated, there would be a case that
-failures would happen in the domain creation with P2M pages already in
-use. To properly free the P2M for this case, firstly support the
-optionally preemption of p2m_teardown(), then call p2m_teardown() and
-p2m_set_allocation(d, 0, NULL) non-preemptively in p2m_final_teardown().
-As non-preemptive p2m_teardown() should only return 0, use a
-BUG_ON to confirm that.
-
-Since p2m_final_teardown() is called either after
-domain_relinquish_resources() where relinquish_p2m_mapping() has been
-called, or from failure path of domain_create()/arch_domain_create()
-where mappings that require p2m_put_l3_page() should never be created,
-relinquish_p2m_mapping() is not added in p2m_final_teardown(), add
-in-code comments to refer this.
-
-Fixes: cbea5a1149ca ("xen/arm: Allocate and free P2M pages from the P2M pool")
-Suggested-by: Julien Grall <jgrall@amazon.com>
-Signed-off-by: Henry Wang <Henry.Wang@arm.com>
-Reviewed-by: Julien Grall <jgrall@amazon.com>
-Reviewed-by: Bertrand Marquis <bertrand.marquis@arm.com>
-(cherry picked from commit: c7cff1188802646eaa38e918e5738da0e84949be)
----
- xen/arch/arm/domain.c | 2 +-
- xen/arch/arm/p2m.c | 34 ++++++++++++++++++++++++++++++++--
- xen/include/asm-arm/p2m.h | 14 ++++++++++----
- 3 files changed, 43 insertions(+), 7 deletions(-)
-
-diff --git a/xen/arch/arm/domain.c b/xen/arch/arm/domain.c
-index a5ffd952ecd0..b11359b8cca3 100644
---- a/xen/arch/arm/domain.c
-+++ b/xen/arch/arm/domain.c
-@@ -1041,7 +1041,7 @@ int domain_relinquish_resources(struct domain *d)
- return ret;
-
- PROGRESS(p2m):
-- ret = p2m_teardown(d);
-+ ret = p2m_teardown(d, true);
- if ( ret )
- return ret;
-
-diff --git a/xen/arch/arm/p2m.c b/xen/arch/arm/p2m.c
-index 25eb1d84cbc1..f6012f2a538f 100644
---- a/xen/arch/arm/p2m.c
-+++ b/xen/arch/arm/p2m.c
-@@ -1664,7 +1664,7 @@ static void p2m_free_vmid(struct domain *d)
- spin_unlock(&vmid_alloc_lock);
- }
-
--int p2m_teardown(struct domain *d)
-+int p2m_teardown(struct domain *d, bool allow_preemption)
- {
- struct p2m_domain *p2m = p2m_get_hostp2m(d);
- unsigned long count = 0;
-@@ -1672,6 +1672,9 @@ int p2m_teardown(struct domain *d)
- unsigned int i;
- int rc = 0;
-
-+ if ( page_list_empty(&p2m->pages) )
-+ return 0;
-+
- p2m_write_lock(p2m);
-
- /*
-@@ -1695,7 +1698,7 @@ int p2m_teardown(struct domain *d)
- p2m_free_page(p2m->domain, pg);
- count++;
- /* Arbitrarily preempt every 512 iterations */
-- if ( !(count % 512) && hypercall_preempt_check() )
-+ if ( allow_preemption && !(count % 512) && hypercall_preempt_check() )
- {
- rc = -ERESTART;
- break;
-@@ -1715,7 +1718,20 @@ void p2m_final_teardown(struct domain *d)
- if ( !p2m->domain )
- return;
-
-+ /*
-+ * No need to call relinquish_p2m_mapping() here because
-+ * p2m_final_teardown() is called either after domain_relinquish_resources()
-+ * where relinquish_p2m_mapping() has been called, or from failure path of
-+ * domain_create()/arch_domain_create() where mappings that require
-+ * p2m_put_l3_page() should never be created. For the latter case, also see
-+ * comment on top of the p2m_set_entry() for more info.
-+ */
-+
-+ BUG_ON(p2m_teardown(d, false));
- ASSERT(page_list_empty(&p2m->pages));
-+
-+ while ( p2m_teardown_allocation(d) == -ERESTART )
-+ continue; /* No preemption support here */
- ASSERT(page_list_empty(&d->arch.paging.p2m_freelist));
-
- if ( p2m->root )
-@@ -1782,6 +1798,20 @@ int p2m_init(struct domain *d)
- if ( rc )
- return rc;
-
-+ /*
-+ * Hardware using GICv2 needs to create a P2M mapping of 8KB GICv2 area
-+ * when the domain is created. Considering the worst case for page
-+ * tables and keep a buffer, populate 16 pages to the P2M pages pool here.
-+ * For GICv3, the above-mentioned P2M mapping is not necessary, but since
-+ * the allocated 16 pages here would not be lost, hence populate these
-+ * pages unconditionally.
-+ */
-+ spin_lock(&d->arch.paging.lock);
-+ rc = p2m_set_allocation(d, 16, NULL);
-+ spin_unlock(&d->arch.paging.lock);
-+ if ( rc )
-+ return rc;
-+
- return 0;
- }
-
-diff --git a/xen/include/asm-arm/p2m.h b/xen/include/asm-arm/p2m.h
-index 18675b234570..ea7ca41d82b2 100644
---- a/xen/include/asm-arm/p2m.h
-+++ b/xen/include/asm-arm/p2m.h
-@@ -194,14 +194,18 @@ int p2m_init(struct domain *d);
-
- /*
- * The P2M resources are freed in two parts:
-- * - p2m_teardown() will be called when relinquish the resources. It
-- * will free large resources (e.g. intermediate page-tables) that
-- * requires preemption.
-+ * - p2m_teardown() will be called preemptively when relinquish the
-+ * resources, in which case it will free large resources (e.g. intermediate
-+ * page-tables) that requires preemption.
- * - p2m_final_teardown() will be called when domain struct is been
- * freed. This *cannot* be preempted and therefore one small
- * resources should be freed here.
-+ * Note that p2m_final_teardown() will also call p2m_teardown(), to properly
-+ * free the P2M when failures happen in the domain creation with P2M pages
-+ * already in use. In this case p2m_teardown() is called non-preemptively and
-+ * p2m_teardown() will always return 0.
- */
--int p2m_teardown(struct domain *d);
-+int p2m_teardown(struct domain *d, bool allow_preemption);
- void p2m_final_teardown(struct domain *d);
-
- /*
-@@ -266,6 +270,8 @@ mfn_t p2m_get_entry(struct p2m_domain *p2m, gfn_t gfn,
- /*
- * Direct set a p2m entry: only for use by the P2M code.
- * The P2M write lock should be taken.
-+ * TODO: Add a check in __p2m_set_entry() to avoid creating a mapping in
-+ * arch_domain_create() that requires p2m_put_l3_page() to be called.
- */
- int p2m_set_entry(struct p2m_domain *p2m,
- gfn_t sgfn,
---
-2.37.4
-