NetBSD-Bugs archive

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

Re: port-xen/47057: Xen NetBSD DomU file system trash under Linux Dom0



On Sat, Oct 20, 2012 at 06:02:27PM +0200, Roger Pau Monné wrote:
> > Can you determine if it's cons or prod (or both) which is corrupted,
> > and in which way ? What are the values when it's corrupted ?
> > Are they always the same ?
> 
> This is a trim of what I think is relevant, the first lines correspond
> to the last known values of prod and cons before the corruption, and the
> rest is quite self explanatory:
> 
> xenbus_xs (process_msg:763) xb_read hdr 0.
> xb_read: cons: 3470 prod: 3473
> Finished read of 3 bytes (0 to go)
> xenbus_xs (process_msg:776) xb_read body 0.
> xenbus_xs (process_msg:811) process_msg: type 7 body OK.
> xenbus_xs (read_reply:134) read_reply: type 7 body OK.
> xenbus_xs (xs_talkv:224) read done.
> 
> [?]

is there anything happening here ?

> 
> xb_read: cons: 2403996137 prod: 3531897424

So both cons and prod would be corrupted. As the domU is supposed to update
rsp_cons only, I guess we're looking for something that is writing to
random memory.

Maybe the atached patch will help; anything trying to write to the page
outside of xb_read and xb_write should get a page fault.

-- 
Manuel Bouyer <bouyer%antioche.eu.org@localhost>
     NetBSD: 26 ans d'experience feront toujours la difference
--
Index: xenbus_comms.c
===================================================================
RCS file: /cvsroot/src/sys/arch/xen/xenbus/xenbus_comms.c,v
retrieving revision 1.14
diff -u -p -u -r1.14 xenbus_comms.c
--- xenbus_comms.c      20 Sep 2011 00:12:24 -0000      1.14
+++ xenbus_comms.c      20 Oct 2012 16:40:44 -0000
@@ -37,6 +37,7 @@ __KERNEL_RCSID(0, "$NetBSD: xenbus_comms
 #include <sys/param.h>
 #include <sys/proc.h>
 #include <sys/systm.h>
+#include <uvm/uvm_extern.h>
 
 #include <xen/xen.h>   /* for xendomain_is_dom0() */
 #include <xen/hypervisor.h>
@@ -142,6 +143,10 @@ xb_write(const void *data, unsigned len)
                        continue;
                if (avail > len)
                        avail = len;
+               pmap_kenter_ma((vaddr_t)intf,
+                   xen_start_info.store_mfn << PAGE_SHIFT,
+                   VM_PROT_READ | VM_PROT_WRITE, 0);
+               pmap_update(pmap_kernel());
 
                memcpy(dst, data, avail);
                data = (const char *)data + avail;
@@ -151,6 +156,10 @@ xb_write(const void *data, unsigned len)
                xen_rmb();
                intf->req_prod += avail;
                xen_rmb();
+               pmap_protect(pmap_kernel(), (vaddr_t)intf,
+                   (vaddr_t)intf + PAGE_SIZE,
+                   VM_PROT_READ);
+               pmap_update(pmap_kernel());
 
                hypervisor_notify_via_evtchn(xen_start_info.store_evtchn);
        }
@@ -198,9 +207,17 @@ xb_read(void *data, unsigned len)
                len -= avail;
 
                /* Other side must not see free space until we've copied out */
+               pmap_kenter_ma((vaddr_t)intf,
+                   xen_start_info.store_mfn << PAGE_SHIFT,
+                   VM_PROT_READ | VM_PROT_WRITE, 0);
+               pmap_update(pmap_kernel());
                xen_rmb();
                intf->rsp_cons += avail;
                xen_rmb();
+               pmap_protect(pmap_kernel(), (vaddr_t)intf,
+                   (vaddr_t)intf + PAGE_SIZE,
+                   VM_PROT_READ);
+               pmap_update(pmap_kernel());
 
                XENPRINTF(("Finished read of %i bytes (%i to go)\n",
                    avail, len));


Home | Main Index | Thread Index | Old Index