|
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [PATCH v1 4/8] xen/domain: introduce domid_alloc()
Move domain ID allocation to a dedicated function domid_alloc() and
use it during domain creation.
Update domid_top within domid_alloc() to reflect the highest known
domain ID.
Initialize domid_top using the result of get_initial_domain_id().
Allocation algorithm:
- If an explicit domain ID is provided, verify its availability and
use it if free;
- Otherwise, perform an exhaustive search for the first available ID
within the [0..DOMID_FIRST_RESERVED) range, excluding hardware_domid.
The change is a prerequisite for enabling console input rotation
across domains on x86 (currently, limited to dom0, PV shim and Xen).
Signed-off-by: Denis Mukhin <dmukhin@xxxxxxxx>
---
xen/arch/arm/dom0less-build.c | 15 ++++----
xen/arch/arm/domain_build.c | 19 +++++++---
xen/common/domctl.c | 71 ++++++++++++++++++++++-------------
xen/common/kernel.c | 8 ++++
xen/include/xen/domain.h | 3 ++
5 files changed, 76 insertions(+), 40 deletions(-)
diff --git a/xen/arch/arm/dom0less-build.c b/xen/arch/arm/dom0less-build.c
index d7d7665c0a..4b9e22039e 100644
--- a/xen/arch/arm/dom0less-build.c
+++ b/xen/arch/arm/dom0less-build.c
@@ -975,14 +975,18 @@ void __init create_domUs(void)
.grant_opts = XEN_DOMCTL_GRANT_version(opt_gnttab_max_version),
};
unsigned int flags = 0U;
+ domid_t domid;
uint32_t val;
int rc;
if ( !dt_device_is_compatible(node, "xen,domain") )
continue;
- if ( (domid_top + 1) >= DOMID_FIRST_RESERVED )
- panic("No more domain IDs available\n");
+ rc = domid_alloc(DOMID_AUTO);
+ if ( rc < 0 )
+ panic("cannot allocate domain ID for domain %s (rc = %d)\n",
+ dt_node_name(node), rc);
+ domid = rc;
if ( dt_find_property(node, "xen,static-mem", NULL) )
{
@@ -1107,12 +1111,7 @@ void __init create_domUs(void)
if ( !llc_coloring_enabled && llc_colors_str )
panic("'llc-colors' found, but LLC coloring is disabled\n");
- /*
- * The variable max_init_domid is initialized with zero, so here it's
- * very important to use the pre-increment operator to call
- * domain_create() with a domid > 0. (domid == 0 is reserved for Dom0)
- */
- d = domain_create(++domid_top, &d_cfg, flags);
+ d = domain_create(domid, &d_cfg, flags);
if ( IS_ERR(d) )
panic("Error creating domain %s (rc = %ld)\n",
dt_node_name(node), PTR_ERR(d));
diff --git a/xen/arch/arm/domain_build.c b/xen/arch/arm/domain_build.c
index 2b5b433183..2d8c2931d6 100644
--- a/xen/arch/arm/domain_build.c
+++ b/xen/arch/arm/domain_build.c
@@ -2367,8 +2367,15 @@ void __init create_dom0(void)
.grant_opts = XEN_DOMCTL_GRANT_version(opt_gnttab_max_version),
};
unsigned int flags = CDF_privileged;
+ domid_t domid;
int rc;
+ rc = domid_alloc(get_initial_domain_id());
+ if ( rc < 0 )
+ panic("Cannot use domain ID %d (rc = %d)\n",
+ get_initial_domain_id(), rc);
+ domid = rc;
+
/* The vGIC for DOM0 is exactly emulating the hardware GIC */
dom0_cfg.arch.gic_version = XEN_DOMCTL_CONFIG_GIC_NATIVE;
dom0_cfg.arch.nr_spis = VGIC_DEF_NR_SPIS;
@@ -2391,19 +2398,21 @@ void __init create_dom0(void)
if ( !llc_coloring_enabled )
flags |= CDF_directmap;
- dom0 = domain_create(0, &dom0_cfg, flags);
+ dom0 = domain_create(domid, &dom0_cfg, flags);
if ( IS_ERR(dom0) )
- panic("Error creating domain 0 (rc = %ld)\n", PTR_ERR(dom0));
+ panic("Error creating domain %d (rc = %ld)\n", domid, PTR_ERR(dom0));
if ( llc_coloring_enabled && (rc = dom0_set_llc_colors(dom0)) )
- panic("Error initializing LLC coloring for domain 0 (rc = %d)\n", rc);
+ panic("Error initializing LLC coloring for domain %d (rc = %d)\n",
+ domid, rc);
if ( alloc_dom0_vcpu0(dom0) == NULL )
- panic("Error creating domain 0 vcpu0\n");
+ panic("Error creating domain %d vcpu0\n", domid);
rc = construct_dom0(dom0);
if ( rc )
- panic("Could not set up DOM0 guest OS (rc = %d)\n", rc);
+ panic("Could not set up guest OS for domain %d (rc = %d)\n",
+ domid, rc);
}
/*
diff --git a/xen/common/domctl.c b/xen/common/domctl.c
index bfe2e1f9f0..9964aa000a 100644
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -63,6 +63,46 @@ static inline int is_free_domid(domid_t dom)
return 0;
}
+/*
+ * Allocate new domain ID based on the hint.
+ *
+ * If hint is outside of valid [0..DOMID_FIRST_RESERVED] range of IDs,
+ * perform an exhaustive search of the first free domain ID excluding
+ * hardware_domid.
+ */
+int domid_alloc(int hint)
+{
+ domid_t domid;
+
+ if ( hint >= 0 && hint < DOMID_FIRST_RESERVED )
+ {
+ if ( !is_free_domid(hint) )
+ return -EEXIST;
+
+ domid = hint;
+ }
+ else
+ {
+ for ( domid = domid_top + 1; domid != domid_top; domid++ )
+ {
+ if ( domid == DOMID_FIRST_RESERVED )
+ domid = 0;
+ if ( domid == hardware_domid )
+ continue;
+ if ( is_free_domid(domid) )
+ break;
+ }
+
+ if ( domid == domid_top )
+ return -ENOMEM;
+ }
+
+ if ( domid_top < domid )
+ domid_top = domid;
+
+ return domid;
+}
+
void getdomaininfo(struct domain *d, struct xen_domctl_getdomaininfo *info)
{
struct vcpu *v;
@@ -421,34 +461,11 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xen_domctl_t)
u_domctl)
case XEN_DOMCTL_createdomain:
{
- domid_t dom;
- static domid_t rover = 0;
+ ret = domid_alloc(op->domain);
+ if ( ret < 0 )
+ break;
- dom = op->domain;
- if ( (dom > 0) && (dom < DOMID_FIRST_RESERVED) )
- {
- ret = -EEXIST;
- if ( !is_free_domid(dom) )
- break;
- }
- else
- {
- for ( dom = rover + 1; dom != rover; dom++ )
- {
- if ( dom == DOMID_FIRST_RESERVED )
- dom = 1;
- if ( is_free_domid(dom) )
- break;
- }
-
- ret = -ENOMEM;
- if ( dom == rover )
- break;
-
- rover = dom;
- }
-
- d = domain_create(dom, &op->u.createdomain, false);
+ d = domain_create(ret, &op->u.createdomain, false);
if ( IS_ERR(d) )
{
ret = PTR_ERR(d);
diff --git a/xen/common/kernel.c b/xen/common/kernel.c
index 8b63ca55f1..50c44b986e 100644
--- a/xen/common/kernel.c
+++ b/xen/common/kernel.c
@@ -568,6 +568,14 @@ static long xenver_varbuf_op(int cmd,
XEN_GUEST_HANDLE_PARAM(void) arg)
return sz;
}
+static int __init cf_check globals_init(void)
+{
+ domid_top = get_initial_domain_id();
+
+ return 0;
+}
+__initcall(globals_init);
+
long do_xen_version(int cmd, XEN_GUEST_HANDLE_PARAM(void) arg)
{
bool deny = xsm_xen_version(XSM_OTHER, cmd);
diff --git a/xen/include/xen/domain.h b/xen/include/xen/domain.h
index b7425827b8..c91b9704de 100644
--- a/xen/include/xen/domain.h
+++ b/xen/include/xen/domain.h
@@ -39,6 +39,9 @@ extern domid_t domid_top;
domid_t get_initial_domain_id(void);
+#define DOMID_AUTO (-1)
+int domid_alloc(int hint);
+
/* CDF_* constant. Internal flags for domain creation. */
/* Is this a privileged domain? */
#define CDF_privileged (1U << 0)
--
2.34.1
|
![]() |
Lists.xenproject.org is hosted with RackSpace, monitoring our |