[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [xen master] Revert "IOMMU/x86: perform PV Dom0 mappings in batches"
commit 81a739a99300ea325caedf696741c9814c5318f6 Author: Jan Beulich <jbeulich@xxxxxxxx> AuthorDate: Fri Jun 10 10:22:00 2022 +0200 Commit: Jan Beulich <jbeulich@xxxxxxxx> CommitDate: Fri Jun 10 10:22:00 2022 +0200 Revert "IOMMU/x86: perform PV Dom0 mappings in batches" This reverts commit f3185c165d28901c3222becfc8be547263c53745. That change require preemption checking to first be in place in iommu_{,un}map(). --- xen/arch/x86/pv/dom0_build.c | 84 ++++--------------------------------- xen/drivers/passthrough/x86/iommu.c | 41 +++++------------- 2 files changed, 17 insertions(+), 108 deletions(-) diff --git a/xen/arch/x86/pv/dom0_build.c b/xen/arch/x86/pv/dom0_build.c index 04a4ea3c18..e501979a86 100644 --- a/xen/arch/x86/pv/dom0_build.c +++ b/xen/arch/x86/pv/dom0_build.c @@ -46,8 +46,7 @@ void __init dom0_update_physmap(bool compat, unsigned long pfn, static __init void mark_pv_pt_pages_rdonly(struct domain *d, l4_pgentry_t *l4start, unsigned long vpt_start, - unsigned long nr_pt_pages, - unsigned int *flush_flags) + unsigned long nr_pt_pages) { unsigned long count; struct page_info *page; @@ -72,14 +71,6 @@ static __init void mark_pv_pt_pages_rdonly(struct domain *d, ASSERT((page->u.inuse.type_info & PGT_type_mask) <= PGT_root_page_table); ASSERT(!(page->u.inuse.type_info & ~(PGT_type_mask | PGT_pae_xen_l2))); - /* - * Page table pages need to be removed from the IOMMU again in case - * iommu_memory_setup() ended up mapping them. - */ - if ( need_iommu_pt_sync(d) && - iommu_unmap(d, _dfn(mfn_x(page_to_mfn(page))), 1, flush_flags) ) - BUG(); - /* Read-only mapping + PGC_allocated + page-table page. */ page->count_info = PGC_allocated | 3; page->u.inuse.type_info |= PGT_validated | 1; @@ -116,43 +107,11 @@ static __init void mark_pv_pt_pages_rdonly(struct domain *d, unmap_domain_page(pl3e); } -static void __init iommu_memory_setup(struct domain *d, const char *what, - struct page_info *page, unsigned long nr, - unsigned int *flush_flags) -{ - int rc; - mfn_t mfn = page_to_mfn(page); - - if ( !need_iommu_pt_sync(d) ) - return; - - rc = iommu_map(d, _dfn(mfn_x(mfn)), mfn, nr, - IOMMUF_readable | IOMMUF_writable, flush_flags); - if ( rc ) - { - printk(XENLOG_ERR "pre-mapping %s MFN [%lx,%lx) into IOMMU failed: %d\n", - what, mfn_x(mfn), mfn_x(mfn) + nr, rc); - return; - } - - /* - * For successfully established IOMMU mappings the type of the page(s) - * needs to match (for _get_page_type() to unmap upon type change). Set - * the page(s) to writable with no type ref. - */ - for ( ; nr--; ++page ) - { - ASSERT(!page->u.inuse.type_info); - page->u.inuse.type_info = PGT_writable_page | PGT_validated; - } -} - static __init void setup_pv_physmap(struct domain *d, unsigned long pgtbl_pfn, unsigned long v_start, unsigned long v_end, unsigned long vphysmap_start, unsigned long vphysmap_end, - unsigned long nr_pages, - unsigned int *flush_flags) + unsigned long nr_pages) { struct page_info *page = NULL; l4_pgentry_t *pl4e, *l4start = map_domain_page(_mfn(pgtbl_pfn)); @@ -218,10 +177,6 @@ static __init void setup_pv_physmap(struct domain *d, unsigned long pgtbl_pfn, L3_PAGETABLE_SHIFT - PAGE_SHIFT, MEMF_no_scrub)) != NULL ) { - iommu_memory_setup(d, "P2M 1G", page, - SUPERPAGE_PAGES * SUPERPAGE_PAGES, - flush_flags); - *pl3e = l3e_from_page(page, L1_PROT|_PAGE_DIRTY|_PAGE_PSE); vphysmap_start += 1UL << L3_PAGETABLE_SHIFT; continue; @@ -248,9 +203,6 @@ static __init void setup_pv_physmap(struct domain *d, unsigned long pgtbl_pfn, L2_PAGETABLE_SHIFT - PAGE_SHIFT, MEMF_no_scrub)) != NULL ) { - iommu_memory_setup(d, "P2M 2M", page, SUPERPAGE_PAGES, - flush_flags); - *pl2e = l2e_from_page(page, L1_PROT|_PAGE_DIRTY|_PAGE_PSE); vphysmap_start += 1UL << L2_PAGETABLE_SHIFT; continue; @@ -359,7 +311,6 @@ int __init dom0_construct_pv(struct domain *d, unsigned long initrd_pfn = -1, initrd_mfn = 0; unsigned long count; struct page_info *page = NULL; - unsigned int flush_flags = 0; start_info_t *si; struct vcpu *v = d->vcpu[0]; void *image_base = bootstrap_map(image); @@ -622,9 +573,6 @@ int __init dom0_construct_pv(struct domain *d, BUG(); } initrd->mod_end = 0; - - iommu_memory_setup(d, "initrd", mfn_to_page(_mfn(initrd_mfn)), - PFN_UP(initrd_len), &flush_flags); } printk("PHYSICAL MEMORY ARRANGEMENT:\n" @@ -658,13 +606,6 @@ int __init dom0_construct_pv(struct domain *d, process_pending_softirqs(); - /* - * Map the full range here and then punch holes for page tables - * alongside marking them as such in mark_pv_pt_pages_rdonly(). - */ - iommu_memory_setup(d, "init-alloc", mfn_to_page(_mfn(alloc_spfn)), - alloc_epfn - alloc_spfn, &flush_flags); - mpt_alloc = (vpt_start - v_start) + pfn_to_paddr(alloc_spfn); if ( vinitrd_start ) mpt_alloc -= PAGE_ALIGN(initrd_len); @@ -749,8 +690,7 @@ int __init dom0_construct_pv(struct domain *d, l1tab++; page = mfn_to_page(_mfn(mfn)); - if ( (!page->u.inuse.type_info || - page->u.inuse.type_info == (PGT_writable_page | PGT_validated)) && + if ( !page->u.inuse.type_info && !get_page_and_type(page, d, PGT_writable_page) ) BUG(); } @@ -779,7 +719,7 @@ int __init dom0_construct_pv(struct domain *d, } /* Pages that are part of page tables must be read only. */ - mark_pv_pt_pages_rdonly(d, l4start, vpt_start, nr_pt_pages, &flush_flags); + mark_pv_pt_pages_rdonly(d, l4start, vpt_start, nr_pt_pages); /* Mask all upcalls... */ for ( i = 0; i < XEN_LEGACY_MAX_VCPUS; i++ ) @@ -854,7 +794,7 @@ int __init dom0_construct_pv(struct domain *d, { pfn = pagetable_get_pfn(v->arch.guest_table); setup_pv_physmap(d, pfn, v_start, v_end, vphysmap_start, vphysmap_end, - nr_pages, &flush_flags); + nr_pages); } /* Write the phys->machine and machine->phys table entries. */ @@ -885,9 +825,7 @@ int __init dom0_construct_pv(struct domain *d, if ( get_gpfn_from_mfn(mfn) >= count ) { BUG_ON(compat); - if ( (!page->u.inuse.type_info || - page->u.inuse.type_info == (PGT_writable_page | - PGT_validated)) && + if ( !page->u.inuse.type_info && !get_page_and_type(page, d, PGT_writable_page) ) BUG(); @@ -903,12 +841,8 @@ int __init dom0_construct_pv(struct domain *d, #endif while ( pfn < nr_pages ) { - count = domain_tot_pages(d); - if ( (page = alloc_chunk(d, nr_pages - count)) == NULL ) + if ( (page = alloc_chunk(d, nr_pages - domain_tot_pages(d))) == NULL ) panic("Not enough RAM for DOM0 reservation\n"); - - iommu_memory_setup(d, "chunk", page, domain_tot_pages(d) - count, - &flush_flags); while ( pfn < domain_tot_pages(d) ) { mfn = mfn_x(page_to_mfn(page)); @@ -923,10 +857,6 @@ int __init dom0_construct_pv(struct domain *d, } } - /* Use while() to avoid compiler warning. */ - while ( iommu_iotlb_flush_all(d, flush_flags) ) - break; - if ( initrd_len != 0 ) { si->mod_start = vinitrd_start ?: initrd_pfn; diff --git a/xen/drivers/passthrough/x86/iommu.c b/xen/drivers/passthrough/x86/iommu.c index 11a4f244e4..0ba95473c9 100644 --- a/xen/drivers/passthrough/x86/iommu.c +++ b/xen/drivers/passthrough/x86/iommu.c @@ -348,8 +348,8 @@ static unsigned int __hwdom_init hwdom_iommu_map(const struct domain *d, void __hwdom_init arch_iommu_hwdom_init(struct domain *d) { - unsigned long i, top, max_pfn, start, count; - unsigned int flush_flags = 0, start_perms = 0; + unsigned long i, top, max_pfn; + unsigned int flush_flags = 0; BUG_ON(!is_hardware_domain(d)); @@ -380,9 +380,9 @@ void __hwdom_init arch_iommu_hwdom_init(struct domain *d) * First Mb will get mapped in one go by pvh_populate_p2m(). Avoid * setting up potentially conflicting mappings here. */ - start = paging_mode_translate(d) ? PFN_DOWN(MB(1)) : 0; + i = paging_mode_translate(d) ? PFN_DOWN(MB(1)) : 0; - for ( i = start, count = 0; i < top; ) + for ( ; i < top; i++ ) { unsigned long pfn = pdx_to_pfn(i); unsigned int perms = hwdom_iommu_map(d, pfn, max_pfn); @@ -391,41 +391,20 @@ void __hwdom_init arch_iommu_hwdom_init(struct domain *d) if ( !perms ) rc = 0; else if ( paging_mode_translate(d) ) - { rc = p2m_add_identity_entry(d, pfn, perms & IOMMUF_writable ? p2m_access_rw : p2m_access_r, 0); - if ( rc ) - printk(XENLOG_WARNING - "%pd: identity mapping of %lx failed: %d\n", - d, pfn, rc); - } - else if ( pfn != start + count || perms != start_perms ) - { - commit: - rc = iommu_map(d, _dfn(start), _mfn(start), count, start_perms, - &flush_flags); - if ( rc ) - printk(XENLOG_WARNING - "%pd: IOMMU identity mapping of [%lx,%lx) failed: %d\n", - d, pfn, pfn + count, rc); - SWAP(start, pfn); - start_perms = perms; - count = 1; - } else - { - ++count; - rc = 0; - } + rc = iommu_map(d, _dfn(pfn), _mfn(pfn), 1ul << PAGE_ORDER_4K, + perms, &flush_flags); + if ( rc ) + printk(XENLOG_WARNING "%pd: identity %smapping of %lx failed: %d\n", + d, !paging_mode_translate(d) ? "IOMMU " : "", pfn, rc); - if ( !(++i & 0xfffff) ) + if (!(i & 0xfffff)) process_pending_softirqs(); - - if ( i == top && count ) - goto commit; } /* Use if to avoid compiler warning */ -- generated by git-patchbot for /home/xen/git/xen.git#master
|
![]() |
Lists.xenproject.org is hosted with RackSpace, monitoring our |