]> xenbits.xensource.com Git - people/vhanquez/xen.git/commitdiff
kunmap_atomic() must zap the PTE to avoid dangling references
authorkaf24@firebug.cl.cam.ac.uk <kaf24@firebug.cl.cam.ac.uk>
Wed, 28 Jun 2006 17:40:23 +0000 (18:40 +0100)
committerkaf24@firebug.cl.cam.ac.uk <kaf24@firebug.cl.cam.ac.uk>
Wed, 28 Jun 2006 17:40:23 +0000 (18:40 +0100)
when attempting to free memory back to Xen. We can implement
something more efficient in future.

Also add debug print message if guest tries to free 'in use'
memory. We'll make it a real guest-visible error in future.

Signed-off-by: Keir Fraser <keir@xensource.com>
xen-unstable changeset:   10529:4260eb8c08740de0000081c61a6237ffcb95b2d5
xen-unstable date:        Wed Jun 28 18:17:41 2006 +0100

linux-2.6-xen-sparse/arch/i386/mm/highmem-xen.c
xen/common/memory.c

index 2a9ce1c4f8339a6e47de6b68a9509cdc99f1f359..566219167d56a5505c0934906c3bdcfb0ef7d52c 100644 (file)
@@ -79,6 +79,16 @@ void kunmap_atomic(void *kvaddr, enum km_type type)
         */
        pte_clear(&init_mm, vaddr, kmap_pte-idx);
        __flush_tlb_one(vaddr);
+#elif defined(CONFIG_XEN)
+       /*
+        * We must ensure there are no dangling pagetable references when
+        * returning memory to Xen (decrease_reservation).
+        * XXX TODO: We could make this faster by only zapping when
+        * kmap_flush_unused is called but that is trickier and more invasive.
+        */
+       unsigned long vaddr = (unsigned long) kvaddr & PAGE_MASK;
+       enum fixed_addresses idx = type + KM_TYPE_NR*smp_processor_id();
+       pte_clear(&init_mm, vaddr, kmap_pte-idx);
 #endif
 
        dec_preempt_count();
index 64137ce33526545c23ccf7d2817a7525749921d0..5a4a4042580dc8d4b315ebd82d4e1cb6a8fe4eed 100644 (file)
@@ -167,6 +167,15 @@ guest_remove_page(
     if ( test_and_clear_bit(_PGC_allocated, &page->count_info) )
         put_page(page);
 
+    if ( unlikely((page->count_info & PGC_count_mask) != 1) )
+    {
+        /* We'll make this a guest-visible error in future, so take heed! */
+        DPRINTK("Dom%d freeing in-use page %lx (pseudophys %lx):"
+                " count=%x type=%lx\n",
+                d->domain_id, mfn, get_gpfn_from_mfn(mfn),
+                page->count_info, page->u.inuse.type_info);
+    }
+
     guest_physmap_remove_page(d, gmfn, mfn);
 
     put_page(page);