From: Jan Beulich Date: Fri, 29 Apr 2016 16:30:22 +0000 (+0200) Subject: x86: fix domain cleanup X-Git-Tag: archive/raspbian/4.8.0-1+rpi1~1^2~1181 X-Git-Url: https://dgit.raspbian.org/?a=commitdiff_plain;h=a29e895b2bde17ab239da3bff76ec00c8d9b2e77;p=xen.git x86: fix domain cleanup Free d->arch.cpuids on both the creation error path and during destruction. Don't bypass iommu_domain_destroy(). Move psr_domain_init() up so that hvm_domain_initialise() again is the last thing which can fail, and hence doesn't require undoing later on. Move psr_domain_free() up on the creation error path, so that cleanup once again gets done in reverse order of setup. Signed-off-by: Jan Beulich Reviewed-by: Andrew Cooper Release-acked-by: Wei Liu --- diff --git a/xen/arch/x86/domain.c b/xen/arch/x86/domain.c index d13b272ce3..5af2cc5b7f 100644 --- a/xen/arch/x86/domain.c +++ b/xen/arch/x86/domain.c @@ -648,21 +648,18 @@ int arch_domain_create(struct domain *d, unsigned int domcr_flags, } spin_lock_init(&d->arch.e820_lock); + if ( (rc = psr_domain_init(d)) != 0 ) + goto fail; + if ( has_hvm_container_domain(d) ) { if ( (rc = hvm_domain_initialise(d)) != 0 ) - { - iommu_domain_destroy(d); goto fail; - } } else /* 64-bit PV guest by default. */ d->arch.is_32bit_pv = d->arch.has_32bit_shinfo = 0; - if ( (rc = psr_domain_init(d)) != 0 ) - goto fail; - /* initialize default tsc behavior in case tools don't */ tsc_set_info(d, TSC_MODE_DEFAULT, 0UL, 0, 0); spin_lock_init(&d->arch.vtsc_lock); @@ -680,8 +677,11 @@ int arch_domain_create(struct domain *d, unsigned int domcr_flags, fail: d->is_dying = DOMDYING_dead; + psr_domain_free(d); + iommu_domain_destroy(d); cleanup_domain_irq_mapping(d); free_xenheap_page(d->shared_info); + xfree(d->arch.cpuids); if ( paging_initialised ) paging_final_teardown(d); free_perdomain_mappings(d); @@ -690,7 +690,6 @@ int arch_domain_create(struct domain *d, unsigned int domcr_flags, xfree(d->arch.pv_domain.cpuidmasks); free_xenheap_page(d->arch.pv_domain.gdt_ldt_l1tab); } - psr_domain_free(d); return rc; } @@ -700,6 +699,7 @@ void arch_domain_destroy(struct domain *d) hvm_domain_destroy(d); xfree(d->arch.e820); + xfree(d->arch.cpuids); free_domain_pirqs(d); if ( !is_idle_domain(d) )