xen-devel.lists.xenproject.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 4/5] Xen/MCE: Abort live migration when vMCE occur
@ 2012-10-10 14:46 Liu, Jinsong
  2012-10-16 10:42 ` Liu, Jinsong
                   ` (2 more replies)
  0 siblings, 3 replies; 29+ messages in thread
From: Liu, Jinsong @ 2012-10-10 14:46 UTC (permalink / raw)
  To: Ian Campbell, xen-devel@lists.xensource.com
  Cc: Ian Jackson, Christoph Egger, Keir (Xen.org), Jan Beulich

[-- Attachment #1: Type: text/plain, Size: 7061 bytes --]

Xen/MCE: Abort live migration when vMCE occur

This patch monitor the critical area of live migration (from vMCE point of view,
the copypages stage of migration is the critical area while other areas are not).

If a vMCE occur at the critical area of live migration, there is risk that error
data may be copied to the target. Currently we don't have convenient way to handle
this case, so for the sake of safe, we abort it and try migration later (at that
time broken page would not be mapped and copied to the target).

Signed-off-by: Liu, Jinsong <jinsong.liu@intel.com>

diff -r e27a6d53ac15 tools/libxc/xc_domain.c
--- a/tools/libxc/xc_domain.c	Thu Oct 11 01:52:33 2012 +0800
+++ b/tools/libxc/xc_domain.c	Thu Oct 11 05:12:48 2012 +0800
@@ -283,6 +283,30 @@
     return ret;
 }
 
+/* Start vmce monitor */
+int xc_domain_vmce_monitor_start(xc_interface *xch,
+                                 uint32_t domid)
+{
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_start;
+    domctl.domain = (domid_t)domid;
+
+    return do_domctl(xch, &domctl);
+}
+
+/* End vmce monitor */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid)
+{
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_end;
+    domctl.domain = (domid_t)domid;
+
+    return do_domctl(xch, &domctl);
+}
+
 /* get info from hvm guest for save */
 int xc_domain_hvm_getcontext(xc_interface *xch,
                              uint32_t domid,
diff -r e27a6d53ac15 tools/libxc/xc_domain_save.c
--- a/tools/libxc/xc_domain_save.c	Thu Oct 11 01:52:33 2012 +0800
+++ b/tools/libxc/xc_domain_save.c	Thu Oct 11 05:12:48 2012 +0800
@@ -895,6 +895,8 @@
      */
     int compressing = 0;
 
+    int vmce_while_monitor = 0;
+
     int completed = 0;
 
     if ( hvm && !callbacks->switch_qemu_logdirty )
@@ -1109,6 +1111,12 @@
         goto out;
     }
 
+    if ( xc_domain_vmce_monitor_start(xch, dom) )
+    {
+        PERROR("Error when start vmce monitor\n");
+        goto out;
+    }
+
   copypages:
 #define wrexact(fd, buf, len) write_buffer(xch, last_iter, ob, (fd), (buf), (len))
 #define wruncached(fd, live, buf, len) write_uncached(xch, last_iter, ob, (fd), (buf), (len))
@@ -1571,6 +1579,18 @@
 
     DPRINTF("All memory is saved\n");
 
+    vmce_while_monitor = xc_domain_vmce_monitor_end(xch, dom);
+    if ( vmce_while_monitor < 0 )
+    {
+        PERROR("Error when end vmce monitor\n");
+        goto out;
+    }
+    else if ( vmce_while_monitor > 0 )
+    {
+        fprintf(stderr, "vMCE occurred, abort this time and try later.\n");
+        goto out;
+    }
+
     /* After last_iter, buffer the rest of pagebuf & tailbuf data into a
      * separate output buffer and flush it after the compressed page chunks.
      */
diff -r e27a6d53ac15 tools/libxc/xenctrl.h
--- a/tools/libxc/xenctrl.h	Thu Oct 11 01:52:33 2012 +0800
+++ b/tools/libxc/xenctrl.h	Thu Oct 11 05:12:48 2012 +0800
@@ -575,6 +575,26 @@
                           xc_domaininfo_t *info);
 
 /**
+ * This function start monitor vmce event.
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @return <0 on failure, 0 on success
+ */
+int xc_domain_vmce_monitor_start(xc_interface *xch,
+                                 uint32_t domid);
+
+/**
+ * This function end monitor vmce event
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @return < 0 on failure, >= 0 on success while
+ *   = 0 on no vmce occurred
+ *   > 0 on vmce occurred
+ */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid);
+
+/**
  * This function returns information about the context of a hvm domain
  * @parm xch a handle to an open hypervisor interface
  * @parm domid the domain to get information from
diff -r e27a6d53ac15 xen/arch/x86/cpu/mcheck/mce_intel.c
--- a/xen/arch/x86/cpu/mcheck/mce_intel.c	Thu Oct 11 01:52:33 2012 +0800
+++ b/xen/arch/x86/cpu/mcheck/mce_intel.c	Thu Oct 11 05:12:48 2012 +0800
@@ -359,6 +359,12 @@
                     goto vmce_failed;
                 }
 
+                if ( unlikely(d->arch.vmce_monitor) )
+                {
+                    /* vMCE occur when guest migration */
+                    d->arch.vmce_monitor = 1;
+                }
+
                 /* We will inject vMCE to DOMU*/
                 if ( inject_vmce(d, VMCE_INJECT_BROADCAST) < 0 )
                 {
diff -r e27a6d53ac15 xen/arch/x86/domctl.c
--- a/xen/arch/x86/domctl.c	Thu Oct 11 01:52:33 2012 +0800
+++ b/xen/arch/x86/domctl.c	Thu Oct 11 05:12:48 2012 +0800
@@ -1568,6 +1568,47 @@
     }
     break;
 
+    case XEN_DOMCTL_vmce_monitor_start:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL )
+        {
+            if ( d->arch.vmce_monitor )
+                ret = -EBUSY;
+            else
+                d->arch.vmce_monitor = -1;
+
+            rcu_unlock_domain(d);
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
+    case XEN_DOMCTL_vmce_monitor_end:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL)
+        {
+            if ( !d->arch.vmce_monitor )
+                ret = -EINVAL;
+            else
+            {
+                ret = d->arch.vmce_monitor > 0 ? 1 : 0;
+                d->arch.vmce_monitor = 0;
+            }
+
+            rcu_unlock_domain(d);
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
     default:
         ret = iommu_do_domctl(domctl, u_domctl);
         break;
diff -r e27a6d53ac15 xen/include/asm-x86/domain.h
--- a/xen/include/asm-x86/domain.h	Thu Oct 11 01:52:33 2012 +0800
+++ b/xen/include/asm-x86/domain.h	Thu Oct 11 05:12:48 2012 +0800
@@ -279,6 +279,11 @@
     bool_t has_32bit_shinfo;
     /* Domain cannot handle spurious page faults? */
     bool_t suppress_spurious_page_faults;
+    /* Monitoring guest memory copy of migration
+     * = 0 - not monitoring
+     * < 0 - monitoring
+     * > 0 - vMCE occurred while monitoring */
+    s8 vmce_monitor;
 
     /* Continuable domain_relinquish_resources(). */
     enum {
diff -r e27a6d53ac15 xen/include/public/domctl.h
--- a/xen/include/public/domctl.h	Thu Oct 11 01:52:33 2012 +0800
+++ b/xen/include/public/domctl.h	Thu Oct 11 05:12:48 2012 +0800
@@ -900,6 +900,8 @@
 #define XEN_DOMCTL_set_access_required           64
 #define XEN_DOMCTL_audit_p2m                     65
 #define XEN_DOMCTL_set_virq_handler              66
+#define XEN_DOMCTL_vmce_monitor_start            67
+#define XEN_DOMCTL_vmce_monitor_end              68
 #define XEN_DOMCTL_gdbsx_guestmemio            1000
 #define XEN_DOMCTL_gdbsx_pausevcpu             1001
 #define XEN_DOMCTL_gdbsx_unpausevcpu           1002

[-- Attachment #2: 4_vmce_when_migrate.patch --]
[-- Type: application/octet-stream, Size: 6849 bytes --]

Xen/MCE: Abort live migration when vMCE occur

This patch monitor the critical area of live migration (from vMCE point of view,
the copypages stage of migration is the critical area while other areas are not).

If a vMCE occur at the critical area of live migration, there is risk that error
data may be copied to the target. Currently we don't have convenient way to handle
this case, so for the sake of safe, we abort it and try migration later (at that
time broken page would not be mapped and copied to the target).

Signed-off-by: Liu, Jinsong <jinsong.liu@intel.com>

diff -r e27a6d53ac15 tools/libxc/xc_domain.c
--- a/tools/libxc/xc_domain.c	Thu Oct 11 01:52:33 2012 +0800
+++ b/tools/libxc/xc_domain.c	Thu Oct 11 05:12:48 2012 +0800
@@ -283,6 +283,30 @@
     return ret;
 }
 
+/* Start vmce monitor */
+int xc_domain_vmce_monitor_start(xc_interface *xch,
+                                 uint32_t domid)
+{
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_start;
+    domctl.domain = (domid_t)domid;
+
+    return do_domctl(xch, &domctl);
+}
+
+/* End vmce monitor */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid)
+{
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_end;
+    domctl.domain = (domid_t)domid;
+
+    return do_domctl(xch, &domctl);
+}
+
 /* get info from hvm guest for save */
 int xc_domain_hvm_getcontext(xc_interface *xch,
                              uint32_t domid,
diff -r e27a6d53ac15 tools/libxc/xc_domain_save.c
--- a/tools/libxc/xc_domain_save.c	Thu Oct 11 01:52:33 2012 +0800
+++ b/tools/libxc/xc_domain_save.c	Thu Oct 11 05:12:48 2012 +0800
@@ -895,6 +895,8 @@
      */
     int compressing = 0;
 
+    int vmce_while_monitor = 0;
+
     int completed = 0;
 
     if ( hvm && !callbacks->switch_qemu_logdirty )
@@ -1109,6 +1111,12 @@
         goto out;
     }
 
+    if ( xc_domain_vmce_monitor_start(xch, dom) )
+    {
+        PERROR("Error when start vmce monitor\n");
+        goto out;
+    }
+
   copypages:
 #define wrexact(fd, buf, len) write_buffer(xch, last_iter, ob, (fd), (buf), (len))
 #define wruncached(fd, live, buf, len) write_uncached(xch, last_iter, ob, (fd), (buf), (len))
@@ -1571,6 +1579,18 @@
 
     DPRINTF("All memory is saved\n");
 
+    vmce_while_monitor = xc_domain_vmce_monitor_end(xch, dom);
+    if ( vmce_while_monitor < 0 )
+    {
+        PERROR("Error when end vmce monitor\n");
+        goto out;
+    }
+    else if ( vmce_while_monitor > 0 )
+    {
+        fprintf(stderr, "vMCE occurred, abort this time and try later.\n");
+        goto out;
+    }
+
     /* After last_iter, buffer the rest of pagebuf & tailbuf data into a
      * separate output buffer and flush it after the compressed page chunks.
      */
diff -r e27a6d53ac15 tools/libxc/xenctrl.h
--- a/tools/libxc/xenctrl.h	Thu Oct 11 01:52:33 2012 +0800
+++ b/tools/libxc/xenctrl.h	Thu Oct 11 05:12:48 2012 +0800
@@ -575,6 +575,26 @@
                           xc_domaininfo_t *info);
 
 /**
+ * This function start monitor vmce event.
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @return <0 on failure, 0 on success
+ */
+int xc_domain_vmce_monitor_start(xc_interface *xch,
+                                 uint32_t domid);
+
+/**
+ * This function end monitor vmce event
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @return < 0 on failure, >= 0 on success while
+ *   = 0 on no vmce occurred
+ *   > 0 on vmce occurred
+ */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid);
+
+/**
  * This function returns information about the context of a hvm domain
  * @parm xch a handle to an open hypervisor interface
  * @parm domid the domain to get information from
diff -r e27a6d53ac15 xen/arch/x86/cpu/mcheck/mce_intel.c
--- a/xen/arch/x86/cpu/mcheck/mce_intel.c	Thu Oct 11 01:52:33 2012 +0800
+++ b/xen/arch/x86/cpu/mcheck/mce_intel.c	Thu Oct 11 05:12:48 2012 +0800
@@ -359,6 +359,12 @@
                     goto vmce_failed;
                 }
 
+                if ( unlikely(d->arch.vmce_monitor) )
+                {
+                    /* vMCE occur when guest migration */
+                    d->arch.vmce_monitor = 1;
+                }
+
                 /* We will inject vMCE to DOMU*/
                 if ( inject_vmce(d, VMCE_INJECT_BROADCAST) < 0 )
                 {
diff -r e27a6d53ac15 xen/arch/x86/domctl.c
--- a/xen/arch/x86/domctl.c	Thu Oct 11 01:52:33 2012 +0800
+++ b/xen/arch/x86/domctl.c	Thu Oct 11 05:12:48 2012 +0800
@@ -1568,6 +1568,47 @@
     }
     break;
 
+    case XEN_DOMCTL_vmce_monitor_start:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL )
+        {
+            if ( d->arch.vmce_monitor )
+                ret = -EBUSY;
+            else
+                d->arch.vmce_monitor = -1;
+
+            rcu_unlock_domain(d);
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
+    case XEN_DOMCTL_vmce_monitor_end:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL)
+        {
+            if ( !d->arch.vmce_monitor )
+                ret = -EINVAL;
+            else
+            {
+                ret = d->arch.vmce_monitor > 0 ? 1 : 0;
+                d->arch.vmce_monitor = 0;
+            }
+
+            rcu_unlock_domain(d);
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
     default:
         ret = iommu_do_domctl(domctl, u_domctl);
         break;
diff -r e27a6d53ac15 xen/include/asm-x86/domain.h
--- a/xen/include/asm-x86/domain.h	Thu Oct 11 01:52:33 2012 +0800
+++ b/xen/include/asm-x86/domain.h	Thu Oct 11 05:12:48 2012 +0800
@@ -279,6 +279,11 @@
     bool_t has_32bit_shinfo;
     /* Domain cannot handle spurious page faults? */
     bool_t suppress_spurious_page_faults;
+    /* Monitoring guest memory copy of migration
+     * = 0 - not monitoring
+     * < 0 - monitoring
+     * > 0 - vMCE occurred while monitoring */
+    s8 vmce_monitor;
 
     /* Continuable domain_relinquish_resources(). */
     enum {
diff -r e27a6d53ac15 xen/include/public/domctl.h
--- a/xen/include/public/domctl.h	Thu Oct 11 01:52:33 2012 +0800
+++ b/xen/include/public/domctl.h	Thu Oct 11 05:12:48 2012 +0800
@@ -900,6 +900,8 @@
 #define XEN_DOMCTL_set_access_required           64
 #define XEN_DOMCTL_audit_p2m                     65
 #define XEN_DOMCTL_set_virq_handler              66
+#define XEN_DOMCTL_vmce_monitor_start            67
+#define XEN_DOMCTL_vmce_monitor_end              68
 #define XEN_DOMCTL_gdbsx_guestmemio            1000
 #define XEN_DOMCTL_gdbsx_pausevcpu             1001
 #define XEN_DOMCTL_gdbsx_unpausevcpu           1002

[-- Attachment #3: Type: text/plain, Size: 126 bytes --]

_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
http://lists.xen.org/xen-devel

^ permalink raw reply	[flat|nested] 29+ messages in thread
* [PATCH 4/5] Xen/MCE: Abort live migration when vMCE occur
@ 2012-09-19  8:14 Liu, Jinsong
  0 siblings, 0 replies; 29+ messages in thread
From: Liu, Jinsong @ 2012-09-19  8:14 UTC (permalink / raw)
  To: Jan Beulich, xen-devel@lists.xensource.com
  Cc: Christoph Egger, keir@xen.org, Ian.Campbell@citrix.com

[-- Attachment #1: Type: text/plain, Size: 7958 bytes --]

Xen/MCE: Abort live migration when vMCE occur

This patch monitor the critical area of live migration (from vMCE point of view,
the copypages stage of migration is the critical area while other areas are not).

If a vMCE occur at the critical area of live migration, abort and try migration later.

Signed-off-by: Liu, Jinsong <jinsong.liu@intel.com>

diff -r e71c4bdcc05a tools/libxc/xc_domain.c
--- a/tools/libxc/xc_domain.c	Wed Sep 19 23:27:40 2012 +0800
+++ b/tools/libxc/xc_domain.c	Thu Sep 20 00:00:17 2012 +0800
@@ -283,6 +283,37 @@
     return ret;
 }
 
+/* Start vmce monitor */
+int xc_domain_vmce_monitor_start(xc_interface *xch,
+                                 uint32_t domid)
+{
+    int ret;
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_start;
+    domctl.domain = (domid_t)domid;
+    ret = do_domctl(xch, &domctl);
+
+    return ret ? -1 : 0;
+}
+
+/* End vmce monitor */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid,
+                               signed char *vmce_while_monitor)
+{
+    int ret;
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_end;
+    domctl.domain = (domid_t)domid;
+    ret = do_domctl(xch, &domctl);
+    if ( !ret )
+        *vmce_while_monitor = domctl.u.vmce_monitor.vmce_while_monitor;
+
+    return ret ? -1 : 0;
+}
+
 /* get info from hvm guest for save */
 int xc_domain_hvm_getcontext(xc_interface *xch,
                              uint32_t domid,
diff -r e71c4bdcc05a tools/libxc/xc_domain_save.c
--- a/tools/libxc/xc_domain_save.c	Wed Sep 19 23:27:40 2012 +0800
+++ b/tools/libxc/xc_domain_save.c	Thu Sep 20 00:00:17 2012 +0800
@@ -895,6 +895,8 @@
      */
     int compressing = 0;
 
+    signed char vmce_while_monitor = 0;
+
     int completed = 0;
 
     if ( hvm && !callbacks->switch_qemu_logdirty )
@@ -1109,6 +1111,12 @@
         goto out;
     }
 
+    if ( xc_domain_vmce_monitor_start(xch, dom) )
+    {
+        PERROR("Error when start vmce monitor\n");
+        goto out;
+    }
+
   copypages:
 #define wrexact(fd, buf, len) write_buffer(xch, last_iter, ob, (fd), (buf), (len))
 #define wruncached(fd, live, buf, len) write_uncached(xch, last_iter, ob, (fd), (buf), (len))
@@ -1571,6 +1579,17 @@
 
     DPRINTF("All memory is saved\n");
 
+    if ( xc_domain_vmce_monitor_end(xch, dom, &vmce_while_monitor) )
+    {
+        PERROR("Error when end vmce monitor\n");
+        goto out;
+    }
+    else if ( vmce_while_monitor == -1 )
+    {
+        fprintf(stderr, "vMCE occurred, abort this time and try later.\n");
+        goto out;
+    }
+
     /* After last_iter, buffer the rest of pagebuf & tailbuf data into a
      * separate output buffer and flush it after the compressed page chunks.
      */
diff -r e71c4bdcc05a tools/libxc/xenctrl.h
--- a/tools/libxc/xenctrl.h	Wed Sep 19 23:27:40 2012 +0800
+++ b/tools/libxc/xenctrl.h	Thu Sep 20 00:00:17 2012 +0800
@@ -575,6 +575,26 @@
                           xc_domaininfo_t *info);
 
 /**
+ * This function start monitor vmce event.
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @return 0 on success, -1 on failure
+ */
+int xc_domain_vmce_monitor_start(xc_interface *xch,
+                                 uint32_t domid);
+
+/**
+ * This function end monitor vmce event
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @parm vmce_while_migrate a pointer return whether vMCE occur when migrate 
+ * @return 0 on success, -1 on failure
+ */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid,
+                               signed char *vmce_while_monitor);
+
+/**
  * This function returns information about the context of a hvm domain
  * @parm xch a handle to an open hypervisor interface
  * @parm domid the domain to get information from
diff -r e71c4bdcc05a xen/arch/x86/cpu/mcheck/mce_intel.c
--- a/xen/arch/x86/cpu/mcheck/mce_intel.c	Wed Sep 19 23:27:40 2012 +0800
+++ b/xen/arch/x86/cpu/mcheck/mce_intel.c	Thu Sep 20 00:00:17 2012 +0800
@@ -358,6 +358,12 @@
                     goto vmce_failed;
                 }
 
+                if ( unlikely(d->arch.vmce_monitor) )
+                {
+                    /* vMCE occur when guest migration */
+                    d->arch.vmce_monitor = -1;
+                }
+
                 /* We will inject vMCE to DOMU*/
                 if ( inject_vmce(d) < 0 )
                 {
diff -r e71c4bdcc05a xen/arch/x86/domctl.c
--- a/xen/arch/x86/domctl.c	Wed Sep 19 23:27:40 2012 +0800
+++ b/xen/arch/x86/domctl.c	Thu Sep 20 00:00:17 2012 +0800
@@ -1514,6 +1514,40 @@
     }
     break;
 
+    case XEN_DOMCTL_vmce_monitor_start:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL )
+        {
+            d->arch.vmce_monitor = 1;
+            rcu_unlock_domain(d);
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
+    case XEN_DOMCTL_vmce_monitor_end:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL)
+        {
+            domctl->u.vmce_monitor.vmce_while_monitor =
+                                      d->arch.vmce_monitor;
+            d->arch.vmce_monitor = 0;
+            rcu_unlock_domain(d);
+            if ( copy_to_guest(u_domctl, domctl, 1) )
+                ret = -EFAULT;
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
     default:
         ret = iommu_do_domctl(domctl, u_domctl);
         break;
diff -r e71c4bdcc05a xen/include/asm-x86/domain.h
--- a/xen/include/asm-x86/domain.h	Wed Sep 19 23:27:40 2012 +0800
+++ b/xen/include/asm-x86/domain.h	Thu Sep 20 00:00:17 2012 +0800
@@ -279,6 +279,11 @@
     bool_t has_32bit_shinfo;
     /* Domain cannot handle spurious page faults? */
     bool_t suppress_spurious_page_faults;
+    /* Monitoring guest memory copy of migration
+     * = 0 - not monitoring
+     * > 0 - monitoring
+     * < 0 - vMCE occurred while monitoring */
+    s8 vmce_monitor;
 
     /* Continuable domain_relinquish_resources(). */
     enum {
diff -r e71c4bdcc05a xen/include/public/domctl.h
--- a/xen/include/public/domctl.h	Wed Sep 19 23:27:40 2012 +0800
+++ b/xen/include/public/domctl.h	Thu Sep 20 00:00:17 2012 +0800
@@ -828,6 +828,12 @@
 typedef struct xen_domctl_set_access_required xen_domctl_set_access_required_t;
 DEFINE_XEN_GUEST_HANDLE(xen_domctl_set_access_required_t);
 
+struct xen_domctl_vmce_monitor {
+    signed char vmce_while_monitor;
+};
+typedef struct xen_domctl_vmce_monitor xen_domctl_vmce_monitor_t;
+DEFINE_XEN_GUEST_HANDLE(xen_domctl_vmce_monitor_t);
+
 struct xen_domctl {
     uint32_t cmd;
 #define XEN_DOMCTL_createdomain                   1
@@ -893,6 +899,8 @@
 #define XEN_DOMCTL_set_access_required           64
 #define XEN_DOMCTL_audit_p2m                     65
 #define XEN_DOMCTL_set_virq_handler              66
+#define XEN_DOMCTL_vmce_monitor_start            67
+#define XEN_DOMCTL_vmce_monitor_end              68
 #define XEN_DOMCTL_gdbsx_guestmemio            1000
 #define XEN_DOMCTL_gdbsx_pausevcpu             1001
 #define XEN_DOMCTL_gdbsx_unpausevcpu           1002
@@ -947,6 +955,7 @@
         struct xen_domctl_set_access_required access_required;
         struct xen_domctl_audit_p2m         audit_p2m;
         struct xen_domctl_set_virq_handler  set_virq_handler;
+        struct xen_domctl_vmce_monitor      vmce_monitor;
         struct xen_domctl_gdbsx_memio       gdbsx_guest_memio;
         struct xen_domctl_gdbsx_pauseunp_vcpu gdbsx_pauseunp_vcpu;
         struct xen_domctl_gdbsx_domstatus   gdbsx_domstatus;

[-- Attachment #2: 4_vmce_when_migrate.patch --]
[-- Type: application/octet-stream, Size: 7729 bytes --]

Xen/MCE: Abort live migration when vMCE occur

This patch monitor the critical area of live migration (from vMCE point of view,
the copypages stage of migration is the critical area while other areas are not).

If a vMCE occur at the critical area of live migration, abort and try migration later.

Signed-off-by: Liu, Jinsong <jinsong.liu@intel.com>

diff -r e71c4bdcc05a tools/libxc/xc_domain.c
--- a/tools/libxc/xc_domain.c	Wed Sep 19 23:27:40 2012 +0800
+++ b/tools/libxc/xc_domain.c	Thu Sep 20 00:00:17 2012 +0800
@@ -283,6 +283,37 @@
     return ret;
 }
 
+/* Start vmce monitor */
+int xc_domain_vmce_monitor_start(xc_interface *xch,
+                                 uint32_t domid)
+{
+    int ret;
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_start;
+    domctl.domain = (domid_t)domid;
+    ret = do_domctl(xch, &domctl);
+
+    return ret ? -1 : 0;
+}
+
+/* End vmce monitor */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid,
+                               signed char *vmce_while_monitor)
+{
+    int ret;
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_end;
+    domctl.domain = (domid_t)domid;
+    ret = do_domctl(xch, &domctl);
+    if ( !ret )
+        *vmce_while_monitor = domctl.u.vmce_monitor.vmce_while_monitor;
+
+    return ret ? -1 : 0;
+}
+
 /* get info from hvm guest for save */
 int xc_domain_hvm_getcontext(xc_interface *xch,
                              uint32_t domid,
diff -r e71c4bdcc05a tools/libxc/xc_domain_save.c
--- a/tools/libxc/xc_domain_save.c	Wed Sep 19 23:27:40 2012 +0800
+++ b/tools/libxc/xc_domain_save.c	Thu Sep 20 00:00:17 2012 +0800
@@ -895,6 +895,8 @@
      */
     int compressing = 0;
 
+    signed char vmce_while_monitor = 0;
+
     int completed = 0;
 
     if ( hvm && !callbacks->switch_qemu_logdirty )
@@ -1109,6 +1111,12 @@
         goto out;
     }
 
+    if ( xc_domain_vmce_monitor_start(xch, dom) )
+    {
+        PERROR("Error when start vmce monitor\n");
+        goto out;
+    }
+
   copypages:
 #define wrexact(fd, buf, len) write_buffer(xch, last_iter, ob, (fd), (buf), (len))
 #define wruncached(fd, live, buf, len) write_uncached(xch, last_iter, ob, (fd), (buf), (len))
@@ -1571,6 +1579,17 @@
 
     DPRINTF("All memory is saved\n");
 
+    if ( xc_domain_vmce_monitor_end(xch, dom, &vmce_while_monitor) )
+    {
+        PERROR("Error when end vmce monitor\n");
+        goto out;
+    }
+    else if ( vmce_while_monitor == -1 )
+    {
+        fprintf(stderr, "vMCE occurred, abort this time and try later.\n");
+        goto out;
+    }
+
     /* After last_iter, buffer the rest of pagebuf & tailbuf data into a
      * separate output buffer and flush it after the compressed page chunks.
      */
diff -r e71c4bdcc05a tools/libxc/xenctrl.h
--- a/tools/libxc/xenctrl.h	Wed Sep 19 23:27:40 2012 +0800
+++ b/tools/libxc/xenctrl.h	Thu Sep 20 00:00:17 2012 +0800
@@ -575,6 +575,26 @@
                           xc_domaininfo_t *info);
 
 /**
+ * This function start monitor vmce event.
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @return 0 on success, -1 on failure
+ */
+int xc_domain_vmce_monitor_start(xc_interface *xch,
+                                 uint32_t domid);
+
+/**
+ * This function end monitor vmce event
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @parm vmce_while_migrate a pointer return whether vMCE occur when migrate 
+ * @return 0 on success, -1 on failure
+ */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid,
+                               signed char *vmce_while_monitor);
+
+/**
  * This function returns information about the context of a hvm domain
  * @parm xch a handle to an open hypervisor interface
  * @parm domid the domain to get information from
diff -r e71c4bdcc05a xen/arch/x86/cpu/mcheck/mce_intel.c
--- a/xen/arch/x86/cpu/mcheck/mce_intel.c	Wed Sep 19 23:27:40 2012 +0800
+++ b/xen/arch/x86/cpu/mcheck/mce_intel.c	Thu Sep 20 00:00:17 2012 +0800
@@ -358,6 +358,12 @@
                     goto vmce_failed;
                 }
 
+                if ( unlikely(d->arch.vmce_monitor) )
+                {
+                    /* vMCE occur when guest migration */
+                    d->arch.vmce_monitor = -1;
+                }
+
                 /* We will inject vMCE to DOMU*/
                 if ( inject_vmce(d) < 0 )
                 {
diff -r e71c4bdcc05a xen/arch/x86/domctl.c
--- a/xen/arch/x86/domctl.c	Wed Sep 19 23:27:40 2012 +0800
+++ b/xen/arch/x86/domctl.c	Thu Sep 20 00:00:17 2012 +0800
@@ -1514,6 +1514,40 @@
     }
     break;
 
+    case XEN_DOMCTL_vmce_monitor_start:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL )
+        {
+            d->arch.vmce_monitor = 1;
+            rcu_unlock_domain(d);
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
+    case XEN_DOMCTL_vmce_monitor_end:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL)
+        {
+            domctl->u.vmce_monitor.vmce_while_monitor =
+                                      d->arch.vmce_monitor;
+            d->arch.vmce_monitor = 0;
+            rcu_unlock_domain(d);
+            if ( copy_to_guest(u_domctl, domctl, 1) )
+                ret = -EFAULT;
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
     default:
         ret = iommu_do_domctl(domctl, u_domctl);
         break;
diff -r e71c4bdcc05a xen/include/asm-x86/domain.h
--- a/xen/include/asm-x86/domain.h	Wed Sep 19 23:27:40 2012 +0800
+++ b/xen/include/asm-x86/domain.h	Thu Sep 20 00:00:17 2012 +0800
@@ -279,6 +279,11 @@
     bool_t has_32bit_shinfo;
     /* Domain cannot handle spurious page faults? */
     bool_t suppress_spurious_page_faults;
+    /* Monitoring guest memory copy of migration
+     * = 0 - not monitoring
+     * > 0 - monitoring
+     * < 0 - vMCE occurred while monitoring */
+    s8 vmce_monitor;
 
     /* Continuable domain_relinquish_resources(). */
     enum {
diff -r e71c4bdcc05a xen/include/public/domctl.h
--- a/xen/include/public/domctl.h	Wed Sep 19 23:27:40 2012 +0800
+++ b/xen/include/public/domctl.h	Thu Sep 20 00:00:17 2012 +0800
@@ -828,6 +828,12 @@
 typedef struct xen_domctl_set_access_required xen_domctl_set_access_required_t;
 DEFINE_XEN_GUEST_HANDLE(xen_domctl_set_access_required_t);
 
+struct xen_domctl_vmce_monitor {
+    signed char vmce_while_monitor;
+};
+typedef struct xen_domctl_vmce_monitor xen_domctl_vmce_monitor_t;
+DEFINE_XEN_GUEST_HANDLE(xen_domctl_vmce_monitor_t);
+
 struct xen_domctl {
     uint32_t cmd;
 #define XEN_DOMCTL_createdomain                   1
@@ -893,6 +899,8 @@
 #define XEN_DOMCTL_set_access_required           64
 #define XEN_DOMCTL_audit_p2m                     65
 #define XEN_DOMCTL_set_virq_handler              66
+#define XEN_DOMCTL_vmce_monitor_start            67
+#define XEN_DOMCTL_vmce_monitor_end              68
 #define XEN_DOMCTL_gdbsx_guestmemio            1000
 #define XEN_DOMCTL_gdbsx_pausevcpu             1001
 #define XEN_DOMCTL_gdbsx_unpausevcpu           1002
@@ -947,6 +955,7 @@
         struct xen_domctl_set_access_required access_required;
         struct xen_domctl_audit_p2m         audit_p2m;
         struct xen_domctl_set_virq_handler  set_virq_handler;
+        struct xen_domctl_vmce_monitor      vmce_monitor;
         struct xen_domctl_gdbsx_memio       gdbsx_guest_memio;
         struct xen_domctl_gdbsx_pauseunp_vcpu gdbsx_pauseunp_vcpu;
         struct xen_domctl_gdbsx_domstatus   gdbsx_domstatus;

[-- Attachment #3: Type: text/plain, Size: 126 bytes --]

_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
http://lists.xen.org/xen-devel

^ permalink raw reply	[flat|nested] 29+ messages in thread
* [PATCH 4/5] Xen/MCE: Abort live migration when vMCE occur
@ 2012-09-18 13:16 Liu, Jinsong
  2012-09-18 15:29 ` Christoph Egger
  2012-10-10  9:10 ` Ian Campbell
  0 siblings, 2 replies; 29+ messages in thread
From: Liu, Jinsong @ 2012-09-18 13:16 UTC (permalink / raw)
  To: Jan Beulich, xen-devel@lists.xensource.com
  Cc: keir@xen.org, Ian.Campbell@citrix.com

[-- Attachment #1: Type: text/plain, Size: 7958 bytes --]

Xen/MCE: Abort live migration when vMCE occur

This patch monitor the critical area of live migration (from vMCE point of view,
the copypages stage of migration is the critical area while other areas are not).

If a vMCE occur at the critical area of live migration, abort and try migration later.

Signed-off-by: Liu, Jinsong <jinsong.liu@intel.com>

diff -r f843ac6f93c9 tools/libxc/xc_domain.c
--- a/tools/libxc/xc_domain.c	Wed Sep 19 01:21:18 2012 +0800
+++ b/tools/libxc/xc_domain.c	Wed Sep 19 03:31:30 2012 +0800
@@ -283,6 +283,37 @@
     return ret;
 }
 
+/* Start vmce monitor */
+int xc_domain_vmce_monitor_strat(xc_interface *xch,
+                                 uint32_t domid)
+{
+    int ret;
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_start;
+    domctl.domain = (domid_t)domid;
+    ret = do_domctl(xch, &domctl);
+
+    return ret ? -1 : 0;
+}
+
+/* End vmce monitor */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid,
+                               signed char *vmce_while_monitor)
+{
+    int ret;
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_end;
+    domctl.domain = (domid_t)domid;
+    ret = do_domctl(xch, &domctl);
+    if ( !ret )
+        *vmce_while_monitor = domctl.u.vmce_monitor.vmce_while_monitor;
+
+    return ret ? -1 : 0;
+}
+
 /* get info from hvm guest for save */
 int xc_domain_hvm_getcontext(xc_interface *xch,
                              uint32_t domid,
diff -r f843ac6f93c9 tools/libxc/xc_domain_save.c
--- a/tools/libxc/xc_domain_save.c	Wed Sep 19 01:21:18 2012 +0800
+++ b/tools/libxc/xc_domain_save.c	Wed Sep 19 03:31:30 2012 +0800
@@ -895,6 +895,8 @@
      */
     int compressing = 0;
 
+    signed char vmce_while_monitor = 0;
+
     int completed = 0;
 
     if ( hvm && !callbacks->switch_qemu_logdirty )
@@ -1109,6 +1111,12 @@
         goto out;
     }
 
+    if ( xc_domain_vmce_monitor_strat(xch, dom) )
+    {
+        PERROR("Error when start vmce monitor\n");
+        goto out;
+    }
+
   copypages:
 #define wrexact(fd, buf, len) write_buffer(xch, last_iter, ob, (fd), (buf), (len))
 #define wruncached(fd, live, buf, len) write_uncached(xch, last_iter, ob, (fd), (buf), (len))
@@ -1571,6 +1579,17 @@
 
     DPRINTF("All memory is saved\n");
 
+    if ( xc_domain_vmce_monitor_end(xch, dom, &vmce_while_monitor) )
+    {
+        PERROR("Error when end vmce monitor\n");
+        goto out;
+    }
+    else if ( vmce_while_monitor == -1 )
+    {
+        fprintf(stderr, "vMCE occurred, abort this time and try later.\n");
+        goto out;
+    }
+
     /* After last_iter, buffer the rest of pagebuf & tailbuf data into a
      * separate output buffer and flush it after the compressed page chunks.
      */
diff -r f843ac6f93c9 tools/libxc/xenctrl.h
--- a/tools/libxc/xenctrl.h	Wed Sep 19 01:21:18 2012 +0800
+++ b/tools/libxc/xenctrl.h	Wed Sep 19 03:31:30 2012 +0800
@@ -571,6 +571,26 @@
                           xc_domaininfo_t *info);
 
 /**
+ * This function start monitor vmce event.
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @return 0 on success, -1 on failure
+ */
+int xc_domain_vmce_monitor_strat(xc_interface *xch,
+                                 uint32_t domid);
+
+/**
+ * This function end monitor vmce event
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @parm vmce_while_migrate a pointer return whether vMCE occur when migrate 
+ * @return 0 on success, -1 on failure
+ */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid,
+                               signed char *vmce_while_monitor);
+
+/**
  * This function returns information about the context of a hvm domain
  * @parm xch a handle to an open hypervisor interface
  * @parm domid the domain to get information from
diff -r f843ac6f93c9 xen/arch/x86/cpu/mcheck/mce_intel.c
--- a/xen/arch/x86/cpu/mcheck/mce_intel.c	Wed Sep 19 01:21:18 2012 +0800
+++ b/xen/arch/x86/cpu/mcheck/mce_intel.c	Wed Sep 19 03:31:30 2012 +0800
@@ -596,6 +596,12 @@
                     goto vmce_failed;
                 }
 
+                if ( unlikely(d->arch.vmce_monitor) )
+                {
+                    /* vMCE occur when guest migration */
+                    d->arch.vmce_monitor = -1;
+                }
+
                 /* We will inject vMCE to DOMU*/
                 if ( inject_vmce(d) < 0 )
                 {
diff -r f843ac6f93c9 xen/arch/x86/domctl.c
--- a/xen/arch/x86/domctl.c	Wed Sep 19 01:21:18 2012 +0800
+++ b/xen/arch/x86/domctl.c	Wed Sep 19 03:31:30 2012 +0800
@@ -1514,6 +1514,40 @@
     }
     break;
 
+    case XEN_DOMCTL_vmce_monitor_start:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL )
+        {
+            d->arch.vmce_monitor = 1;
+            rcu_unlock_domain(d);
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
+    case XEN_DOMCTL_vmce_monitor_end:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL)
+        {
+            domctl->u.vmce_monitor.vmce_while_monitor =
+                                      d->arch.vmce_monitor;
+            d->arch.vmce_monitor = 0;
+            rcu_unlock_domain(d);
+            if ( copy_to_guest(u_domctl, domctl, 1) )
+                ret = -EFAULT;
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
     default:
         ret = iommu_do_domctl(domctl, u_domctl);
         break;
diff -r f843ac6f93c9 xen/include/asm-x86/domain.h
--- a/xen/include/asm-x86/domain.h	Wed Sep 19 01:21:18 2012 +0800
+++ b/xen/include/asm-x86/domain.h	Wed Sep 19 03:31:30 2012 +0800
@@ -279,6 +279,11 @@
     bool_t has_32bit_shinfo;
     /* Domain cannot handle spurious page faults? */
     bool_t suppress_spurious_page_faults;
+    /* Monitoring guest memory copy of migration
+     * = 0 - not monitoring
+     * > 0 - monitoring
+     * < 0 - vMCE occurred while monitoring */
+    s8 vmce_monitor;
 
     /* Continuable domain_relinquish_resources(). */
     enum {
diff -r f843ac6f93c9 xen/include/public/domctl.h
--- a/xen/include/public/domctl.h	Wed Sep 19 01:21:18 2012 +0800
+++ b/xen/include/public/domctl.h	Wed Sep 19 03:31:30 2012 +0800
@@ -828,6 +828,12 @@
 typedef struct xen_domctl_set_access_required xen_domctl_set_access_required_t;
 DEFINE_XEN_GUEST_HANDLE(xen_domctl_set_access_required_t);
 
+struct xen_domctl_vmce_monitor {
+    signed char vmce_while_monitor;
+};
+typedef struct xen_domctl_vmce_monitor xen_domctl_vmce_monitor_t;
+DEFINE_XEN_GUEST_HANDLE(xen_domctl_vmce_monitor_t);
+
 struct xen_domctl {
     uint32_t cmd;
 #define XEN_DOMCTL_createdomain                   1
@@ -893,6 +899,8 @@
 #define XEN_DOMCTL_set_access_required           64
 #define XEN_DOMCTL_audit_p2m                     65
 #define XEN_DOMCTL_set_virq_handler              66
+#define XEN_DOMCTL_vmce_monitor_start            67
+#define XEN_DOMCTL_vmce_monitor_end              68
 #define XEN_DOMCTL_gdbsx_guestmemio            1000
 #define XEN_DOMCTL_gdbsx_pausevcpu             1001
 #define XEN_DOMCTL_gdbsx_unpausevcpu           1002
@@ -947,6 +955,7 @@
         struct xen_domctl_set_access_required access_required;
         struct xen_domctl_audit_p2m         audit_p2m;
         struct xen_domctl_set_virq_handler  set_virq_handler;
+        struct xen_domctl_vmce_monitor      vmce_monitor;
         struct xen_domctl_gdbsx_memio       gdbsx_guest_memio;
         struct xen_domctl_gdbsx_pauseunp_vcpu gdbsx_pauseunp_vcpu;
         struct xen_domctl_gdbsx_domstatus   gdbsx_domstatus;

[-- Attachment #2: 4_vmce_when_migrate.patch --]
[-- Type: application/octet-stream, Size: 7729 bytes --]

Xen/MCE: Abort live migration when vMCE occur

This patch monitor the critical area of live migration (from vMCE point of view,
the copypages stage of migration is the critical area while other areas are not).

If a vMCE occur at the critical area of live migration, abort and try migration later.

Signed-off-by: Liu, Jinsong <jinsong.liu@intel.com>

diff -r f843ac6f93c9 tools/libxc/xc_domain.c
--- a/tools/libxc/xc_domain.c	Wed Sep 19 01:21:18 2012 +0800
+++ b/tools/libxc/xc_domain.c	Wed Sep 19 03:31:30 2012 +0800
@@ -283,6 +283,37 @@
     return ret;
 }
 
+/* Start vmce monitor */
+int xc_domain_vmce_monitor_strat(xc_interface *xch,
+                                 uint32_t domid)
+{
+    int ret;
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_start;
+    domctl.domain = (domid_t)domid;
+    ret = do_domctl(xch, &domctl);
+
+    return ret ? -1 : 0;
+}
+
+/* End vmce monitor */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid,
+                               signed char *vmce_while_monitor)
+{
+    int ret;
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_vmce_monitor_end;
+    domctl.domain = (domid_t)domid;
+    ret = do_domctl(xch, &domctl);
+    if ( !ret )
+        *vmce_while_monitor = domctl.u.vmce_monitor.vmce_while_monitor;
+
+    return ret ? -1 : 0;
+}
+
 /* get info from hvm guest for save */
 int xc_domain_hvm_getcontext(xc_interface *xch,
                              uint32_t domid,
diff -r f843ac6f93c9 tools/libxc/xc_domain_save.c
--- a/tools/libxc/xc_domain_save.c	Wed Sep 19 01:21:18 2012 +0800
+++ b/tools/libxc/xc_domain_save.c	Wed Sep 19 03:31:30 2012 +0800
@@ -895,6 +895,8 @@
      */
     int compressing = 0;
 
+    signed char vmce_while_monitor = 0;
+
     int completed = 0;
 
     if ( hvm && !callbacks->switch_qemu_logdirty )
@@ -1109,6 +1111,12 @@
         goto out;
     }
 
+    if ( xc_domain_vmce_monitor_strat(xch, dom) )
+    {
+        PERROR("Error when start vmce monitor\n");
+        goto out;
+    }
+
   copypages:
 #define wrexact(fd, buf, len) write_buffer(xch, last_iter, ob, (fd), (buf), (len))
 #define wruncached(fd, live, buf, len) write_uncached(xch, last_iter, ob, (fd), (buf), (len))
@@ -1571,6 +1579,17 @@
 
     DPRINTF("All memory is saved\n");
 
+    if ( xc_domain_vmce_monitor_end(xch, dom, &vmce_while_monitor) )
+    {
+        PERROR("Error when end vmce monitor\n");
+        goto out;
+    }
+    else if ( vmce_while_monitor == -1 )
+    {
+        fprintf(stderr, "vMCE occurred, abort this time and try later.\n");
+        goto out;
+    }
+
     /* After last_iter, buffer the rest of pagebuf & tailbuf data into a
      * separate output buffer and flush it after the compressed page chunks.
      */
diff -r f843ac6f93c9 tools/libxc/xenctrl.h
--- a/tools/libxc/xenctrl.h	Wed Sep 19 01:21:18 2012 +0800
+++ b/tools/libxc/xenctrl.h	Wed Sep 19 03:31:30 2012 +0800
@@ -571,6 +571,26 @@
                           xc_domaininfo_t *info);
 
 /**
+ * This function start monitor vmce event.
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @return 0 on success, -1 on failure
+ */
+int xc_domain_vmce_monitor_strat(xc_interface *xch,
+                                 uint32_t domid);
+
+/**
+ * This function end monitor vmce event
+ * @parm xch a handle to an open hypervisor interface
+ * @parm domid the domain id monitored
+ * @parm vmce_while_migrate a pointer return whether vMCE occur when migrate 
+ * @return 0 on success, -1 on failure
+ */
+int xc_domain_vmce_monitor_end(xc_interface *xch,
+                               uint32_t domid,
+                               signed char *vmce_while_monitor);
+
+/**
  * This function returns information about the context of a hvm domain
  * @parm xch a handle to an open hypervisor interface
  * @parm domid the domain to get information from
diff -r f843ac6f93c9 xen/arch/x86/cpu/mcheck/mce_intel.c
--- a/xen/arch/x86/cpu/mcheck/mce_intel.c	Wed Sep 19 01:21:18 2012 +0800
+++ b/xen/arch/x86/cpu/mcheck/mce_intel.c	Wed Sep 19 03:31:30 2012 +0800
@@ -596,6 +596,12 @@
                     goto vmce_failed;
                 }
 
+                if ( unlikely(d->arch.vmce_monitor) )
+                {
+                    /* vMCE occur when guest migration */
+                    d->arch.vmce_monitor = -1;
+                }
+
                 /* We will inject vMCE to DOMU*/
                 if ( inject_vmce(d) < 0 )
                 {
diff -r f843ac6f93c9 xen/arch/x86/domctl.c
--- a/xen/arch/x86/domctl.c	Wed Sep 19 01:21:18 2012 +0800
+++ b/xen/arch/x86/domctl.c	Wed Sep 19 03:31:30 2012 +0800
@@ -1514,6 +1514,40 @@
     }
     break;
 
+    case XEN_DOMCTL_vmce_monitor_start:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL )
+        {
+            d->arch.vmce_monitor = 1;
+            rcu_unlock_domain(d);
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
+    case XEN_DOMCTL_vmce_monitor_end:
+    {
+        struct domain *d;
+
+        d = rcu_lock_domain_by_id(domctl->domain);
+        if ( d != NULL)
+        {
+            domctl->u.vmce_monitor.vmce_while_monitor =
+                                      d->arch.vmce_monitor;
+            d->arch.vmce_monitor = 0;
+            rcu_unlock_domain(d);
+            if ( copy_to_guest(u_domctl, domctl, 1) )
+                ret = -EFAULT;
+        }
+        else
+            ret = -ESRCH;
+    }
+    break;
+
     default:
         ret = iommu_do_domctl(domctl, u_domctl);
         break;
diff -r f843ac6f93c9 xen/include/asm-x86/domain.h
--- a/xen/include/asm-x86/domain.h	Wed Sep 19 01:21:18 2012 +0800
+++ b/xen/include/asm-x86/domain.h	Wed Sep 19 03:31:30 2012 +0800
@@ -279,6 +279,11 @@
     bool_t has_32bit_shinfo;
     /* Domain cannot handle spurious page faults? */
     bool_t suppress_spurious_page_faults;
+    /* Monitoring guest memory copy of migration
+     * = 0 - not monitoring
+     * > 0 - monitoring
+     * < 0 - vMCE occurred while monitoring */
+    s8 vmce_monitor;
 
     /* Continuable domain_relinquish_resources(). */
     enum {
diff -r f843ac6f93c9 xen/include/public/domctl.h
--- a/xen/include/public/domctl.h	Wed Sep 19 01:21:18 2012 +0800
+++ b/xen/include/public/domctl.h	Wed Sep 19 03:31:30 2012 +0800
@@ -828,6 +828,12 @@
 typedef struct xen_domctl_set_access_required xen_domctl_set_access_required_t;
 DEFINE_XEN_GUEST_HANDLE(xen_domctl_set_access_required_t);
 
+struct xen_domctl_vmce_monitor {
+    signed char vmce_while_monitor;
+};
+typedef struct xen_domctl_vmce_monitor xen_domctl_vmce_monitor_t;
+DEFINE_XEN_GUEST_HANDLE(xen_domctl_vmce_monitor_t);
+
 struct xen_domctl {
     uint32_t cmd;
 #define XEN_DOMCTL_createdomain                   1
@@ -893,6 +899,8 @@
 #define XEN_DOMCTL_set_access_required           64
 #define XEN_DOMCTL_audit_p2m                     65
 #define XEN_DOMCTL_set_virq_handler              66
+#define XEN_DOMCTL_vmce_monitor_start            67
+#define XEN_DOMCTL_vmce_monitor_end              68
 #define XEN_DOMCTL_gdbsx_guestmemio            1000
 #define XEN_DOMCTL_gdbsx_pausevcpu             1001
 #define XEN_DOMCTL_gdbsx_unpausevcpu           1002
@@ -947,6 +955,7 @@
         struct xen_domctl_set_access_required access_required;
         struct xen_domctl_audit_p2m         audit_p2m;
         struct xen_domctl_set_virq_handler  set_virq_handler;
+        struct xen_domctl_vmce_monitor      vmce_monitor;
         struct xen_domctl_gdbsx_memio       gdbsx_guest_memio;
         struct xen_domctl_gdbsx_pauseunp_vcpu gdbsx_pauseunp_vcpu;
         struct xen_domctl_gdbsx_domstatus   gdbsx_domstatus;

[-- Attachment #3: Type: text/plain, Size: 126 bytes --]

_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xen.org
http://lists.xen.org/xen-devel

^ permalink raw reply	[flat|nested] 29+ messages in thread

end of thread, other threads:[~2012-10-31 10:58 UTC | newest]

Thread overview: 29+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2012-10-10 14:46 [PATCH 4/5] Xen/MCE: Abort live migration when vMCE occur Liu, Jinsong
2012-10-16 10:42 ` Liu, Jinsong
2012-10-19 14:52 ` Ian Jackson
2012-10-19 20:13   ` Liu, Jinsong
2012-10-22 11:32     ` Liu, Jinsong
2012-10-25 11:21       ` Ian Jackson
2012-10-25 12:32         ` Jan Beulich
2012-10-25 12:38           ` Ian Jackson
2012-10-25 12:44           ` Liu, Jinsong
2012-10-25 12:51             ` Ian Jackson
2012-10-19 16:51 ` George Dunlap
2012-10-19 20:32   ` Liu, Jinsong
2012-10-22 11:32     ` George Dunlap
2012-10-24 14:30       ` Liu, Jinsong
2012-10-29 15:21       ` [Patch 4/5] X86/vMCE: handle broken page occurred before migration Liu, Jinsong
2012-10-29 16:35         ` Jan Beulich
2012-10-29 17:19           ` Liu, Jinsong
2012-10-30  9:02         ` Jan Beulich
2012-10-31 10:55           ` Liu, Jinsong
2012-10-30  9:25         ` George Dunlap
2012-10-30  9:27         ` George Dunlap
2012-10-31 10:58           ` Liu, Jinsong
2012-10-29 15:22       ` [PATCH 5/5] Xen/MCE: handle broken page occurs during migration Liu, Jinsong
  -- strict thread matches above, loose matches on Subject: below --
2012-09-19  8:14 [PATCH 4/5] Xen/MCE: Abort live migration when vMCE occur Liu, Jinsong
2012-09-18 13:16 Liu, Jinsong
2012-09-18 15:29 ` Christoph Egger
2012-09-19  7:52   ` Liu, Jinsong
2012-10-10  9:10 ` Ian Campbell
2012-10-10 14:14   ` Liu, Jinsong

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).