[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] Re: [Xen-devel] [PATCH v2 4/6] xen/arm: implement get/put_page_type
At 16:05 +0100 on 20 Jul (1342800356), Stefano Stabellini wrote: > Add a basic get_page_type and put_page_type implementation: the > implementation is similar to the x86 one, without all the code to handle > shadow pagetables and other unneeded features. OK, we definitely decided that ARM didn't need page typecounts. :) Is this needed for some common code? Tim. > Signed-off-by: Stefano Stabellini <stefano.stabellini@xxxxxxxxxxxxx> > --- > xen/arch/arm/dummy.S | 4 -- > xen/arch/arm/mm.c | 91 > ++++++++++++++++++++++++++++++++++++++++++++++ > xen/include/asm-arm/mm.h | 1 - > 3 files changed, 91 insertions(+), 5 deletions(-) > > diff --git a/xen/arch/arm/dummy.S b/xen/arch/arm/dummy.S > index baced25..2b96d22 100644 > --- a/xen/arch/arm/dummy.S > +++ b/xen/arch/arm/dummy.S > @@ -22,10 +22,6 @@ DUMMY(arch_get_info_guest); > DUMMY(arch_vcpu_reset); > NOP(update_vcpu_system_time); > > -/* Page Reference & Type Maintenance */ > -DUMMY(get_page_type); > -DUMMY(put_page_type); > - > /* Grant Tables */ > DUMMY(steal_page); > > diff --git a/xen/arch/arm/mm.c b/xen/arch/arm/mm.c > index 01a6781..7033023 100644 > --- a/xen/arch/arm/mm.c > +++ b/xen/arch/arm/mm.c > @@ -28,8 +28,10 @@ > #include <xen/guest_access.h> > #include <asm/page.h> > #include <asm/current.h> > +#include <asm/flushtlb.h> > #include <public/memory.h> > #include <xen/sched.h> > +#include <xen/perfc.h> > > struct domain *dom_xen, *dom_io; > > @@ -604,6 +606,95 @@ int get_page(struct page_info *page, struct domain > *domain) > return 0; > } > > +void put_page_type(struct page_info *page) > +{ > + unsigned long nx, x, y = page->u.inuse.type_info; > + > + for ( ; ; ) > + { > + x = y; > + nx = x - 1; > + > + ASSERT((x & PGT_count_mask) != 0); > + > + if ( unlikely((nx & PGT_count_mask) == 0) ) > + /* > + * Record TLB information for flush later > + */ > + page->tlbflush_timestamp = tlbflush_current_time(); > + > + if ( likely((y = cmpxchg(&page->u.inuse.type_info, x, nx)) == x) ) > + break; > + } > +} > + > +int get_page_type(struct page_info *page, unsigned long type) > +{ > + unsigned long nx, x, y = page->u.inuse.type_info; > + > + for ( ; ; ) > + { > + x = y; > + nx = x + 1; > + if ( unlikely((nx & PGT_count_mask) == 0) ) > + { > + printk("Type count overflow on pfn %lx", page_to_mfn(page)); > + return -EINVAL; > + } > + else if ( (x & PGT_count_mask) == 0 ) > + { > + struct domain *d = page_get_owner(page); > + > + if ( (x & PGT_type_mask) != type ) > + { > + /* > + * On type change we check to flush stale TLB entries. This > + * may be unnecessary (e.g., page was GDT/LDT) but those > + * circumstances should be very rare. > + */ > + cpumask_t mask; > + > + cpumask_copy(&mask, d->domain_dirty_cpumask); > + > + /* Don't flush if the timestamp is old enough */ > + tlbflush_filter(mask, page->tlbflush_timestamp); > + > + if ( unlikely(!cpumask_empty(&mask)) ) > + { > + perfc_incr(need_flush_tlb_flush); > + flush_tlb_mask(&mask); > + } > + > + /* We lose existing type and validity. */ > + nx &= ~(PGT_type_mask | PGT_validated); > + nx |= type; > + > + /* No special validation needed for writable pages. */ > + /* Page tables and GDT/LDT need to be scanned for validity. > */ > + if ( type == PGT_writable_page ) > + nx |= PGT_validated; > + } > + } > + else if ( unlikely(!(x & PGT_validated)) ) > + { > + /* Someone else is updating validation of this page. Wait... > */ > + while ( (y = page->u.inuse.type_info) == x ) > + { > + cpu_relax(); > + } > + continue; > + } > + > + if ( likely((y = cmpxchg(&page->u.inuse.type_info, x, nx)) == x) ) > + break; > + } > + > + if ( unlikely(!(nx & PGT_validated)) ) > + BUG(); > + > + return 1; > +} > + > void gnttab_clear_flag(unsigned long nr, uint16_t *addr) > { > /* > diff --git a/xen/include/asm-arm/mm.h b/xen/include/asm-arm/mm.h > index 53801b0..b37bd35 100644 > --- a/xen/include/asm-arm/mm.h > +++ b/xen/include/asm-arm/mm.h > @@ -71,7 +71,6 @@ struct page_info > > #define PGT_none PG_mask(0, 4) /* no special uses of this page */ > #define PGT_writable_page PG_mask(7, 4) /* has writable mappings? */ > -#define PGT_shared_page PG_mask(8, 4) /* CoW sharable page */ > #define PGT_type_mask PG_mask(15, 4) /* Bits 28-31 or 60-63. */ > > /* Owning guest has pinned this page to its current type? */ > -- > 1.7.2.5 > > > _______________________________________________ > Xen-devel mailing list > Xen-devel@xxxxxxxxxxxxx > http://lists.xen.org/xen-devel _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxx http://lists.xen.org/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |