[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 |