[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Xen-changelog] Simple batched writable p.t. support for multi-processor guests.



ChangeSet 1.1385, 2005/04/26 10:31:16+01:00, kaf24@xxxxxxxxxxxxxxxxxxxx

        Simple batched writable p.t. support for multi-processor guests.
        Signed-off-by: Keir Fraser <keir@xxxxxxxxxxxxx>



 arch/x86/mm.c        |   38 +++++++++++++++++++++++++++-----------
 include/asm-x86/mm.h |    2 ++
 2 files changed, 29 insertions(+), 11 deletions(-)


diff -Nru a/xen/arch/x86/mm.c b/xen/arch/x86/mm.c
--- a/xen/arch/x86/mm.c 2005-04-26 06:03:15 -04:00
+++ b/xen/arch/x86/mm.c 2005-04-26 06:03:15 -04:00
@@ -2477,9 +2477,11 @@
     int            i;
     unsigned int   modified = 0;
 
-    // not supported in combination with various shadow modes!
-    ASSERT( !shadow_mode_enabled(d) );
-    
+    ASSERT(!shadow_mode_enabled(d));
+
+    if ( unlikely(d->arch.ptwr[which].ed != current) )
+        write_ptbase(d->arch.ptwr[which].ed);
+
     l1va = d->arch.ptwr[which].l1va;
     ptep = (unsigned long *)&linear_pg_table[l1_linear_offset(l1va)];
 
@@ -2513,7 +2515,7 @@
 
     /* Ensure that there are no stale writable mappings in any TLB. */
     /* NB. INVLPG is a serialising instruction: flushes pending updates. */
-    local_flush_tlb_one(l1va); /* XXX Multi-CPU guests? */
+    flush_tlb_one_mask(d->cpuset, l1va);
     PTWR_PRINTK("[%c] disconnected_l1va at %p now %lx\n",
                 PTWR_PRINT_WHICH, ptep, pte);
 
@@ -2579,6 +2581,9 @@
      */
 
     d->arch.ptwr[which].l1va = 0;
+
+    if ( unlikely(d->arch.ptwr[which].ed != current) )
+        write_ptbase(current);
 }
 
 static int ptwr_emulated_update(
@@ -2741,7 +2746,7 @@
     page = &frame_table[pfn];
 
     /* We are looking only for read-only mappings of p.t. pages. */
-    if ( ((l1e_get_flags(pte) & (_PAGE_RW | _PAGE_PRESENT)) != _PAGE_PRESENT) 
||
+    if ( ((l1e_get_flags(pte) & (_PAGE_RW|_PAGE_PRESENT)) != _PAGE_PRESENT) ||
          ((page->u.inuse.type_info & PGT_type_mask) != PGT_l1_page_table) ||
          (page_get_owner(page) != d) )
     {
@@ -2753,10 +2758,6 @@
     goto emulate;
 #endif
 
-    /* Writable pagetables are not yet SMP safe. Use emulator for now. */
-    if ( d->exec_domain[0]->ed_next_list != NULL )
-        goto emulate;
-
     /* Get the L2 index at which this L1 p.t. is always mapped. */
     l2_idx = page->u.inuse.type_info & PGT_va_mask;
     if ( unlikely(l2_idx >= PGT_va_unknown) )
@@ -2785,7 +2786,21 @@
               (l2_idx == d->arch.ptwr[PTWR_PT_ACTIVE].l2_idx)) )
             which = PTWR_PT_ACTIVE;
     }
-    
+
+    /*
+     * If this is a multi-processor guest then ensure that the page is hooked
+     * into at most one L2 table, which must be the one running on this VCPU.
+     */
+    if ( (d->exec_domain[0]->ed_next_list != NULL) &&
+         ((page->u.inuse.type_info & PGT_count_mask) != 
+          (!!(page->u.inuse.type_info & PGT_pinned) +
+           (which == PTWR_PT_ACTIVE))) )
+    {
+        /* Could be conflicting writable mappings from other VCPUs. */
+        cleanup_writable_pagetable(d);
+        goto emulate;
+    }
+
     PTWR_PRINTK("[%c] page_fault on l1 pt at va %lx, pt for %08x, "
                 "pfn %lx\n", PTWR_PRINT_WHICH,
                 addr, l2_idx << L2_PAGETABLE_SHIFT, pfn);
@@ -2810,12 +2825,13 @@
 
     d->arch.ptwr[which].l1va   = addr | 1;
     d->arch.ptwr[which].l2_idx = l2_idx;
+    d->arch.ptwr[which].ed     = current;
     
     /* For safety, disconnect the L1 p.t. page from current space. */
     if ( which == PTWR_PT_ACTIVE )
     {
         l2e_remove_flags(pl2e, _PAGE_PRESENT);
-        local_flush_tlb(); /* XXX Multi-CPU guests? */
+        flush_tlb_mask(d->cpuset);
     }
     
     /* Temporarily map the L1 page, and make a copy of it. */
diff -Nru a/xen/include/asm-x86/mm.h b/xen/include/asm-x86/mm.h
--- a/xen/include/asm-x86/mm.h  2005-04-26 06:03:15 -04:00
+++ b/xen/include/asm-x86/mm.h  2005-04-26 06:03:15 -04:00
@@ -301,6 +301,8 @@
     unsigned int l2_idx; /* NB. Only used for PTWR_PT_ACTIVE. */
     /* Info about last ptwr update batch. */
     unsigned int prev_nr_updates;
+    /* Exec domain which created writable mapping. */
+    struct exec_domain *ed;
 };
 
 #define PTWR_PT_ACTIVE 0

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.