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

[Xen-devel] [PATCH] arm/monitor vm-events: Implement guest-request support


  • To: xen-devel@xxxxxxxxxxxxx
  • From: Corneliu ZUZU <czuzu@xxxxxxxxxxxxxxx>
  • Date: Thu, 18 Feb 2016 21:35:16 +0200
  • Cc: Tamas K Lengyel <tamas@xxxxxxxxxxxxx>, Keir Fraser <keir@xxxxxxx>, Ian Campbell <ian.campbell@xxxxxxxxxx>, Razvan Cojocaru <rcojocaru@xxxxxxxxxxxxxxx>, Andrew Cooper <andrew.cooper3@xxxxxxxxxx>, Stefano Stabellini <stefano.stabellini@xxxxxxxxxx>, Jan Beulich <jbeulich@xxxxxxxx>
  • Comment: DomainKeys? See http://domainkeys.sourceforge.net/
  • Delivery-date: Thu, 18 Feb 2016 19:35:53 +0000
  • Domainkey-signature: a=rsa-sha1; q=dns; c=nofws; s=default; d=bitdefender.com; b=3NlHlEqQ8CHq755cRJ33IU37lZB5IixMW0nRWbKEHmRwieXMfktHgfmspgGB4q3plu7m/q2QI/uGEaVwnJbPw7L3Lbo+qkAPVsmQSrYQw48xiq5mYBMIab6g00/RLQwLNraLPZ/ZXyOhIaYFD4tqeExe6lqDwkLTA4jW6ifoE5Ck4/vwZYXaKK/3zLOSnxhWmDJURL3VMEiCzyyx1xgSoaA0eyPZV4GgKiAFiOlwpxw2uBPO6j+rykce4AL5F/JyoYPt53z6N1QsEKDF82k3MLNIQf+VNNN0kuoRi2qGEjFttzeHNlGeQJ0yVsSQMs7+xQoaOadu4WMHhovecr9+Ig==; h=Received:Received:Received:Received:Received:From:To:Cc:Subject:Date:Message-Id:X-Mailer:X-BitDefender-Scanner:X-BitDefender-Spam:X-BitDefender-SpamStamp:X-BitDefender-CF-Stamp;
  • List-id: Xen developer discussion <xen-devel.lists.xen.org>

This patch adds ARM support for guest-request monitor vm-events.

Summary of changes:
== Moved to common-side:
  * XEN_DOMCTL_MONITOR_EVENT_GUEST_REQUEST handling (moved from X86
      arch_monitor_domctl_event to common monitor_domctl)
  * hvm_event_guest_request, hvm_event_traps (also added target vcpu as param)
  * guest-request bits from X86 'struct arch_domain' (to common 'struct domain')
== ARM implementations:
  * do_hvm_op now handling of HVMOP_guest_request_vm_event => calls
      hvm_event_guest_request (as on X86)
  * arch_monitor_get_capabilities: updated to reflect support for
      XEN_DOMCTL_MONITOR_EVENT_GUEST_REQUEST
  * vm_event_init_domain (does nothing), vm_event_cleanup_domain
== Misc:
  * hvm_event_fill_regs renamed to arch_hvm_event_fill_regs, no longer
      X86-specific. ARM-side implementation of this function currently does
      nothing, that will be added in a separate patch.

Signed-off-by: Corneliu ZUZU <czuzu@xxxxxxxxxxxxxxx>
---
 MAINTAINERS                     |   1 +
 xen/arch/arm/hvm.c              |   8 +++
 xen/arch/x86/hvm/event.c        | 116 ++++++----------------------------------
 xen/arch/x86/hvm/hvm.c          |   1 +
 xen/arch/x86/monitor.c          |  14 -----
 xen/arch/x86/vm_event.c         |   1 +
 xen/common/Makefile             |   2 +-
 xen/common/hvm/Makefile         |   3 +-
 xen/common/hvm/event.c          |  96 +++++++++++++++++++++++++++++++++
 xen/common/monitor.c            |  31 +++++++++--
 xen/include/asm-arm/hvm/event.h |  41 ++++++++++++++
 xen/include/asm-arm/monitor.h   |   7 ++-
 xen/include/asm-arm/vm_event.h  |   4 +-
 xen/include/asm-x86/domain.h    |  18 +++----
 xen/include/asm-x86/hvm/event.h |  43 ++++++++++++++-
 xen/include/xen/hvm/event.h     |  41 ++++++++++++++
 xen/include/xen/sched.h         |   6 +++
 17 files changed, 299 insertions(+), 134 deletions(-)
 create mode 100644 xen/common/hvm/event.c
 create mode 100644 xen/include/asm-arm/hvm/event.h
 create mode 100644 xen/include/xen/hvm/event.h

diff --git a/MAINTAINERS b/MAINTAINERS
index cd4da04..768ad32 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -356,6 +356,7 @@ M:  Tamas K Lengyel <tamas@xxxxxxxxxxxxx>
 S:     Supported
 F:     xen/common/vm_event.c
 F:     xen/common/mem_access.c
+F:     xen/common/hvm/event.c
 F:     xen/common/monitor.c
 F:     xen/arch/x86/hvm/event.c
 F:     xen/arch/x86/monitor.c
diff --git a/xen/arch/arm/hvm.c b/xen/arch/arm/hvm.c
index 056db1a..767edd1 100644
--- a/xen/arch/arm/hvm.c
+++ b/xen/arch/arm/hvm.c
@@ -22,6 +22,7 @@
 #include <xen/errno.h>
 #include <xen/guest_access.h>
 #include <xen/sched.h>
+#include <xen/hvm/event.h>
 
 #include <xsm/xsm.h>
 
@@ -72,6 +73,13 @@ long do_hvm_op(unsigned long op, 
XEN_GUEST_HANDLE_PARAM(void) arg)
         break;
     }
 
+    case HVMOP_guest_request_vm_event:
+        if ( guest_handle_is_null(arg) )
+            hvm_event_guest_request();
+        else
+            rc = -EINVAL;
+        break;
+
     default:
     {
         gdprintk(XENLOG_DEBUG, "HVMOP op=%lu: not implemented\n", op);
diff --git a/xen/arch/x86/hvm/event.c b/xen/arch/x86/hvm/event.c
index cb9c152..bbb0dc8 100644
--- a/xen/arch/x86/hvm/event.c
+++ b/xen/arch/x86/hvm/event.c
@@ -6,6 +6,7 @@
  * Copyright (c) 2004, Intel Corporation.
  * Copyright (c) 2005, International Business Machines Corporation.
  * Copyright (c) 2008, Citrix Systems, Inc.
+ * Copyright (c) 2016, Bitdefender S.R.L.
  *
  * This program is free software; you can redistribute it and/or modify it
  * under the terms and conditions of the GNU General Public License,
@@ -20,103 +21,32 @@
  * this program; If not, see <http://www.gnu.org/licenses/>.
  */
 
-#include <xen/vm_event.h>
-#include <xen/paging.h>
+#include <xen/hvm/event.h>
 #include <asm/hvm/event.h>
 #include <asm/monitor.h>
-#include <asm/altp2m.h>
 #include <public/vm_event.h>
 
-static void hvm_event_fill_regs(vm_event_request_t *req)
-{
-    const struct cpu_user_regs *regs = guest_cpu_user_regs();
-    const struct vcpu *curr = current;
-
-    req->data.regs.x86.rax = regs->eax;
-    req->data.regs.x86.rcx = regs->ecx;
-    req->data.regs.x86.rdx = regs->edx;
-    req->data.regs.x86.rbx = regs->ebx;
-    req->data.regs.x86.rsp = regs->esp;
-    req->data.regs.x86.rbp = regs->ebp;
-    req->data.regs.x86.rsi = regs->esi;
-    req->data.regs.x86.rdi = regs->edi;
-
-    req->data.regs.x86.r8  = regs->r8;
-    req->data.regs.x86.r9  = regs->r9;
-    req->data.regs.x86.r10 = regs->r10;
-    req->data.regs.x86.r11 = regs->r11;
-    req->data.regs.x86.r12 = regs->r12;
-    req->data.regs.x86.r13 = regs->r13;
-    req->data.regs.x86.r14 = regs->r14;
-    req->data.regs.x86.r15 = regs->r15;
-
-    req->data.regs.x86.rflags = regs->eflags;
-    req->data.regs.x86.rip    = regs->eip;
-
-    req->data.regs.x86.msr_efer = curr->arch.hvm_vcpu.guest_efer;
-    req->data.regs.x86.cr0 = curr->arch.hvm_vcpu.guest_cr[0];
-    req->data.regs.x86.cr3 = curr->arch.hvm_vcpu.guest_cr[3];
-    req->data.regs.x86.cr4 = curr->arch.hvm_vcpu.guest_cr[4];
-}
-
-static int hvm_event_traps(uint8_t sync, vm_event_request_t *req)
-{
-    int rc;
-    struct vcpu *curr = current;
-    struct domain *currd = curr->domain;
-
-    rc = vm_event_claim_slot(currd, &currd->vm_event->monitor);
-    switch ( rc )
-    {
-    case 0:
-        break;
-    case -ENOSYS:
-        /*
-         * If there was no ring to handle the event, then
-         * simply continue executing normally.
-         */
-        return 1;
-    default:
-        return rc;
-    };
-
-    if ( sync )
-    {
-        req->flags |= VM_EVENT_FLAG_VCPU_PAUSED;
-        vm_event_vcpu_pause(curr);
-    }
-
-    if ( altp2m_active(currd) )
-    {
-        req->flags |= VM_EVENT_FLAG_ALTERNATE_P2M;
-        req->altp2m_idx = vcpu_altp2m(curr).p2midx;
-    }
-
-    hvm_event_fill_regs(req);
-    vm_event_put_request(currd, &currd->vm_event->monitor, req);
-
-    return 1;
-}
-
 bool_t hvm_event_cr(unsigned int index, unsigned long value, unsigned long old)
 {
-    struct arch_domain *currad = &current->domain->arch;
+    struct vcpu *curr = current;
+    struct arch_domain *ad = &curr->domain->arch;
     unsigned int ctrlreg_bitmask = monitor_ctrlreg_bitmask(index);
 
-    if ( (currad->monitor.write_ctrlreg_enabled & ctrlreg_bitmask) &&
-         (!(currad->monitor.write_ctrlreg_onchangeonly & ctrlreg_bitmask) ||
+    if ( (ad->monitor.write_ctrlreg_enabled & ctrlreg_bitmask) &&
+         (!(ad->monitor.write_ctrlreg_onchangeonly & ctrlreg_bitmask) ||
           value != old) )
     {
+        bool_t sync = !!(ad->monitor.write_ctrlreg_sync & ctrlreg_bitmask);
+
         vm_event_request_t req = {
             .reason = VM_EVENT_REASON_WRITE_CTRLREG,
-            .vcpu_id = current->vcpu_id,
+            .vcpu_id = curr->vcpu_id,
             .u.write_ctrlreg.index = index,
             .u.write_ctrlreg.new_value = value,
             .u.write_ctrlreg.old_value = old
         };
 
-        hvm_event_traps(currad->monitor.write_ctrlreg_sync & ctrlreg_bitmask,
-                        &req);
+        hvm_event_traps(curr, sync, &req);
         return 1;
     }
 
@@ -126,30 +56,18 @@ bool_t hvm_event_cr(unsigned int index, unsigned long 
value, unsigned long old)
 void hvm_event_msr(unsigned int msr, uint64_t value)
 {
     struct vcpu *curr = current;
-    vm_event_request_t req = {
-        .reason = VM_EVENT_REASON_MOV_TO_MSR,
-        .vcpu_id = curr->vcpu_id,
-        .u.mov_to_msr.msr = msr,
-        .u.mov_to_msr.value = value,
-    };
-
-    if ( curr->domain->arch.monitor.mov_to_msr_enabled )
-        hvm_event_traps(1, &req);
-}
-
-void hvm_event_guest_request(void)
-{
-    struct vcpu *curr = current;
-    struct arch_domain *currad = &curr->domain->arch;
+    struct arch_domain *ad = &curr->domain->arch;
 
-    if ( currad->monitor.guest_request_enabled )
+    if ( ad->monitor.mov_to_msr_enabled )
     {
         vm_event_request_t req = {
-            .reason = VM_EVENT_REASON_GUEST_REQUEST,
+            .reason = VM_EVENT_REASON_MOV_TO_MSR,
             .vcpu_id = curr->vcpu_id,
+            .u.mov_to_msr.msr = msr,
+            .u.mov_to_msr.value = value,
         };
 
-        hvm_event_traps(currad->monitor.guest_request_sync, &req);
+        hvm_event_traps(curr, 1, &req);
     }
 }
 
@@ -197,7 +115,7 @@ int hvm_event_breakpoint(unsigned long rip,
 
     req.vcpu_id = curr->vcpu_id;
 
-    return hvm_event_traps(1, &req);
+    return hvm_event_traps(curr, 1, &req);
 }
 
 /*
diff --git a/xen/arch/x86/hvm/hvm.c b/xen/arch/x86/hvm/hvm.c
index a29c421..11c2ef6 100644
--- a/xen/arch/x86/hvm/hvm.c
+++ b/xen/arch/x86/hvm/hvm.c
@@ -32,6 +32,7 @@
 #include <xen/guest_access.h>
 #include <xen/event.h>
 #include <xen/paging.h>
+#include <xen/hvm/event.h>
 #include <xen/cpu.h>
 #include <xen/wait.h>
 #include <xen/mem_access.h>
diff --git a/xen/arch/x86/monitor.c b/xen/arch/x86/monitor.c
index b4bd008..7768cbb 100644
--- a/xen/arch/x86/monitor.c
+++ b/xen/arch/x86/monitor.c
@@ -124,20 +124,6 @@ int arch_monitor_domctl_event(struct domain *d,
         break;
     }
 
-    case XEN_DOMCTL_MONITOR_EVENT_GUEST_REQUEST:
-    {
-        bool_t old_status = ad->monitor.guest_request_enabled;
-
-        if ( unlikely(old_status == requested_status) )
-            return -EEXIST;
-
-        domain_pause(d);
-        ad->monitor.guest_request_sync = mop->u.guest_request.sync;
-        ad->monitor.guest_request_enabled = requested_status;
-        domain_unpause(d);
-        break;
-    }
-
     default:
         /*
          * Should not be reached unless arch_monitor_get_capabilities() is not
diff --git a/xen/arch/x86/vm_event.c b/xen/arch/x86/vm_event.c
index 08d678a..f97dec3 100644
--- a/xen/arch/x86/vm_event.c
+++ b/xen/arch/x86/vm_event.c
@@ -57,6 +57,7 @@ void vm_event_cleanup_domain(struct domain *d)
 
     d->arch.mem_access_emulate_each_rep = 0;
     memset(&d->arch.monitor, 0, sizeof(d->arch.monitor));
+    memset(&d->monitor, 0, sizeof(d->monitor));
 }
 
 void vm_event_toggle_singlestep(struct domain *d, struct vcpu *v)
diff --git a/xen/common/Makefile b/xen/common/Makefile
index 0d76efe..703faa5 100644
--- a/xen/common/Makefile
+++ b/xen/common/Makefile
@@ -67,7 +67,7 @@ obj-$(xenoprof)    += xenoprof.o
 
 obj-$(CONFIG_COMPAT) += $(addprefix compat/,domain.o kernel.o memory.o 
multicall.o tmem_xen.o xlat.o)
 
-subdir-$(CONFIG_X86) += hvm
+subdir-y += hvm
 
 subdir-$(coverage) += gcov
 
diff --git a/xen/common/hvm/Makefile b/xen/common/hvm/Makefile
index a464a57..11e109d 100644
--- a/xen/common/hvm/Makefile
+++ b/xen/common/hvm/Makefile
@@ -1 +1,2 @@
-obj-y += save.o
+obj-$(CONFIG_X86) += save.o
+obj-y += event.o
diff --git a/xen/common/hvm/event.c b/xen/common/hvm/event.c
new file mode 100644
index 0000000..28ceadc
--- /dev/null
+++ b/xen/common/hvm/event.c
@@ -0,0 +1,96 @@
+/*
+ * xen/common/hvm/event.c
+ *
+ * Common hardware virtual machine event abstractions.
+ *
+ * Copyright (c) 2004, Intel Corporation.
+ * Copyright (c) 2005, International Business Machines Corporation.
+ * Copyright (c) 2008, Citrix Systems, Inc.
+ * Copyright (c) 2016, Bitdefender S.R.L.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program; If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <xen/hvm/event.h>
+#include <xen/vm_event.h>
+#include <asm/hvm/event.h>
+#if CONFIG_X86
+#include <asm/altp2m.h>
+#endif
+
+int hvm_event_traps(struct vcpu *v, uint8_t sync, vm_event_request_t *req)
+{
+    int rc;
+    struct domain *d = v->domain;
+
+    rc = vm_event_claim_slot(d, &d->vm_event->monitor);
+    switch ( rc )
+    {
+    case 0:
+        break;
+    case -ENOSYS:
+        /*
+         * If there was no ring to handle the event, then
+         * simply continue executing normally.
+         */
+        return 1;
+    default:
+        return rc;
+    };
+
+    if ( sync )
+    {
+        req->flags |= VM_EVENT_FLAG_VCPU_PAUSED;
+        vm_event_vcpu_pause(v);
+    }
+
+#if CONFIG_X86
+    if ( altp2m_active(d) )
+    {
+        req->flags |= VM_EVENT_FLAG_ALTERNATE_P2M;
+        req->altp2m_idx = vcpu_altp2m(v).p2midx;
+    }
+#endif
+
+    arch_hvm_event_fill_regs(req);
+
+    vm_event_put_request(d, &d->vm_event->monitor, req);
+
+    return 1;
+}
+
+void hvm_event_guest_request(void)
+{
+    struct vcpu *curr = current;
+    struct domain *d = curr->domain;
+
+    if ( d->monitor.guest_request_enabled )
+    {
+        vm_event_request_t req = {
+            .reason = VM_EVENT_REASON_GUEST_REQUEST,
+            .vcpu_id = curr->vcpu_id,
+        };
+
+        hvm_event_traps(curr, d->monitor.guest_request_sync, &req);
+    }
+}
+
+/*
+ * Local variables:
+ * mode: C
+ * c-file-style: "BSD"
+ * c-basic-offset: 4
+ * tab-width: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
diff --git a/xen/common/monitor.c b/xen/common/monitor.c
index 2a99a04..7c3d1c8 100644
--- a/xen/common/monitor.c
+++ b/xen/common/monitor.c
@@ -28,6 +28,7 @@
 int monitor_domctl(struct domain *d, struct xen_domctl_monitor_op *mop)
 {
     int rc;
+    bool_t requested_status = 0;
 
     if ( unlikely(current->domain == d) ) /* no domain_pause() */
         return -EPERM;
@@ -39,15 +40,16 @@ int monitor_domctl(struct domain *d, struct 
xen_domctl_monitor_op *mop)
     switch ( mop->op )
     {
     case XEN_DOMCTL_MONITOR_OP_ENABLE:
+        requested_status = 1;
+        /* fallthrough */
     case XEN_DOMCTL_MONITOR_OP_DISABLE:
-        /* Check if event type is available. */
         /* sanity check: avoid left-shift undefined behavior */
         if ( unlikely(mop->event > 31) )
             return -EINVAL;
+        /* Check if event type is available. */
         if ( unlikely(!(arch_monitor_get_capabilities(d) & (1U << 
mop->event))) )
             return -EOPNOTSUPP;
-        /* Arch-side handles enable/disable ops. */
-        return arch_monitor_domctl_event(d, mop);
+        break;
 
     case XEN_DOMCTL_MONITOR_OP_GET_CAPABILITIES:
         mop->event = arch_monitor_get_capabilities(d);
@@ -57,6 +59,29 @@ int monitor_domctl(struct domain *d, struct 
xen_domctl_monitor_op *mop)
         /* The monitor op is probably handled on the arch-side. */
         return arch_monitor_domctl_op(d, mop);
     }
+
+    switch ( mop->event )
+    {
+    case XEN_DOMCTL_MONITOR_EVENT_GUEST_REQUEST:
+    {
+        bool_t old_status = d->monitor.guest_request_enabled;
+
+        if ( unlikely(old_status == requested_status) )
+            return -EEXIST;
+
+        domain_pause(d);
+        d->monitor.guest_request_sync = mop->u.guest_request.sync;
+        d->monitor.guest_request_enabled = requested_status;
+        domain_unpause(d);
+        break;
+    }
+
+    default:
+        /* Give arch-side the chance to handle this event */
+        return arch_monitor_domctl_event(d, mop);
+    }
+
+    return 0;
 }
 
 /*
diff --git a/xen/include/asm-arm/hvm/event.h b/xen/include/asm-arm/hvm/event.h
new file mode 100644
index 0000000..cd93581
--- /dev/null
+++ b/xen/include/asm-arm/hvm/event.h
@@ -0,0 +1,41 @@
+/*
+ * include/asm-arm/hvm/event.h
+ *
+ * Arch-specific hardware virtual machine event abstractions.
+ *
+ * Copyright (c) 2016, Bitdefender S.R.L.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program; If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef __ASM_ARM_HVM_EVENT_H__
+#define __ASM_ARM_HVM_EVENT_H__
+
+#include <public/vm_event.h>
+
+static inline void arch_hvm_event_fill_regs(vm_event_request_t *req)
+{
+    /* Not supported on ARM. */
+}
+
+#endif /* __ASM_ARM_HVM_EVENT_H__ */
+
+/*
+ * Local variables:
+ * mode: C
+ * c-file-style: "BSD"
+ * c-basic-offset: 4
+ * tab-width: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
diff --git a/xen/include/asm-arm/monitor.h b/xen/include/asm-arm/monitor.h
index 82a4a66..db1e357 100644
--- a/xen/include/asm-arm/monitor.h
+++ b/xen/include/asm-arm/monitor.h
@@ -27,8 +27,11 @@
 
 static inline uint32_t arch_monitor_get_capabilities(struct domain *d)
 {
-    /* No monitor vm-events implemented on ARM. */
-    return 0;
+    uint32_t capabilities = 0;
+
+    capabilities = (1U << XEN_DOMCTL_MONITOR_EVENT_GUEST_REQUEST);
+
+    return capabilities;
 }
 
 static inline
diff --git a/xen/include/asm-arm/vm_event.h b/xen/include/asm-arm/vm_event.h
index 4d0fbf7..017fb6f 100644
--- a/xen/include/asm-arm/vm_event.h
+++ b/xen/include/asm-arm/vm_event.h
@@ -25,14 +25,14 @@
 static inline
 int vm_event_init_domain(struct domain *d)
 {
-    /* Not supported on ARM. */
+    /* Nothing to do. */
     return 0;
 }
 
 static inline
 void vm_event_cleanup_domain(struct domain *d)
 {
-    /* Not supported on ARM. */
+    memset(&d->monitor, 0, sizeof(d->monitor));
 }
 
 static inline
diff --git a/xen/include/asm-x86/domain.h b/xen/include/asm-x86/domain.h
index 4fad638..1de7a9e 100644
--- a/xen/include/asm-x86/domain.h
+++ b/xen/include/asm-x86/domain.h
@@ -376,17 +376,15 @@ struct arch_domain
     unsigned long *pirq_eoi_map;
     unsigned long pirq_eoi_map_mfn;
 
-    /* Monitor options */
+    /* Arch-specific monitor options */
     struct {
-        unsigned int write_ctrlreg_enabled       : 4;
-        unsigned int write_ctrlreg_sync          : 4;
-        unsigned int write_ctrlreg_onchangeonly  : 4;
-        unsigned int mov_to_msr_enabled          : 1;
-        unsigned int mov_to_msr_extended         : 1;
-        unsigned int singlestep_enabled          : 1;
-        unsigned int software_breakpoint_enabled : 1;
-        unsigned int guest_request_enabled       : 1;
-        unsigned int guest_request_sync          : 1;
+        uint16_t write_ctrlreg_enabled       : 4;
+        uint16_t write_ctrlreg_sync          : 4;
+        uint16_t write_ctrlreg_onchangeonly  : 4;
+        uint16_t mov_to_msr_enabled          : 1;
+        uint16_t mov_to_msr_extended         : 1;
+        uint16_t singlestep_enabled          : 1;
+        uint16_t software_breakpoint_enabled : 1;
     } monitor;
 
     /* Mem_access emulation control */
diff --git a/xen/include/asm-x86/hvm/event.h b/xen/include/asm-x86/hvm/event.h
index 7a83b45..6f70e83 100644
--- a/xen/include/asm-x86/hvm/event.h
+++ b/xen/include/asm-x86/hvm/event.h
@@ -1,5 +1,9 @@
 /*
- * event.h: Hardware virtual machine assist events.
+ * include/asm-x86/hvm/event.h
+ *
+ * Arch-specific hardware virtual machine event abstractions.
+ *
+ * Copyright (c) 2016, Bitdefender S.R.L.
  *
  * This program is free software; you can redistribute it and/or modify it
  * under the terms and conditions of the GNU General Public License,
@@ -17,6 +21,42 @@
 #ifndef __ASM_X86_HVM_EVENT_H__
 #define __ASM_X86_HVM_EVENT_H__
 
+#include <xen/sched.h>
+#include <xen/paging.h>
+#include <public/vm_event.h>
+
+static inline void arch_hvm_event_fill_regs(vm_event_request_t *req)
+{
+    const struct cpu_user_regs *regs = guest_cpu_user_regs();
+    const struct vcpu *curr = current;
+
+    req->data.regs.x86.rax = regs->eax;
+    req->data.regs.x86.rcx = regs->ecx;
+    req->data.regs.x86.rdx = regs->edx;
+    req->data.regs.x86.rbx = regs->ebx;
+    req->data.regs.x86.rsp = regs->esp;
+    req->data.regs.x86.rbp = regs->ebp;
+    req->data.regs.x86.rsi = regs->esi;
+    req->data.regs.x86.rdi = regs->edi;
+
+    req->data.regs.x86.r8  = regs->r8;
+    req->data.regs.x86.r9  = regs->r9;
+    req->data.regs.x86.r10 = regs->r10;
+    req->data.regs.x86.r11 = regs->r11;
+    req->data.regs.x86.r12 = regs->r12;
+    req->data.regs.x86.r13 = regs->r13;
+    req->data.regs.x86.r14 = regs->r14;
+    req->data.regs.x86.r15 = regs->r15;
+
+    req->data.regs.x86.rflags = regs->eflags;
+    req->data.regs.x86.rip    = regs->eip;
+
+    req->data.regs.x86.msr_efer = curr->arch.hvm_vcpu.guest_efer;
+    req->data.regs.x86.cr0 = curr->arch.hvm_vcpu.guest_cr[0];
+    req->data.regs.x86.cr3 = curr->arch.hvm_vcpu.guest_cr[3];
+    req->data.regs.x86.cr4 = curr->arch.hvm_vcpu.guest_cr[4];
+}
+
 enum hvm_event_breakpoint_type
 {
     HVM_EVENT_SOFTWARE_BREAKPOINT,
@@ -35,7 +75,6 @@ bool_t hvm_event_cr(unsigned int index, unsigned long value,
 void hvm_event_msr(unsigned int msr, uint64_t value);
 int hvm_event_breakpoint(unsigned long rip,
                          enum hvm_event_breakpoint_type type);
-void hvm_event_guest_request(void);
 
 #endif /* __ASM_X86_HVM_EVENT_H__ */
 
diff --git a/xen/include/xen/hvm/event.h b/xen/include/xen/hvm/event.h
new file mode 100644
index 0000000..941d611
--- /dev/null
+++ b/xen/include/xen/hvm/event.h
@@ -0,0 +1,41 @@
+/*
+ * include/xen/hvm/event.h
+ *
+ * Common hardware virtual machine event abstractions.
+ *
+ * Copyright (c) 2016, Bitdefender S.R.L.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program; If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef __XEN_HVM_EVENT_H__
+#define __XEN_HVM_EVENT_H__
+
+#include <xen/sched.h>
+#include <public/vm_event.h>
+
+void hvm_event_guest_request(void);
+
+int hvm_event_traps(struct vcpu *v, uint8_t sync, vm_event_request_t *req);
+
+#endif /* __XEN_HVM_EVENT_H__ */
+
+/*
+ * Local variables:
+ * mode: C
+ * c-file-style: "BSD"
+ * c-basic-offset: 4
+ * tab-width: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
diff --git a/xen/include/xen/sched.h b/xen/include/xen/sched.h
index b47a3fe..c2efb49 100644
--- a/xen/include/xen/sched.h
+++ b/xen/include/xen/sched.h
@@ -464,6 +464,12 @@ struct domain
     /* vNUMA topology accesses are protected by rwlock. */
     rwlock_t vnuma_rwlock;
     struct vnuma_info *vnuma;
+
+    /* Common monitor options */
+    struct {
+        uint8_t guest_request_enabled       : 1;
+        uint8_t guest_request_sync          : 1;
+    } monitor;
 };
 
 /* Protect updates/reads (resp.) of domain_list and domain_hash. */
-- 
2.5.0


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


 


Rackspace

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