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

Re: [Xen-devel] [PATCH v5] x86/hvm: Allow guest_request vm_events coming from userspace



On Tue, Aug 8, 2017 at 2:27 AM, Alexandru Isaila
<aisaila@xxxxxxxxxxxxxxx> wrote:
>
> In some introspection usecases, an in-guest agent needs to communicate
> with the external introspection agent.  An existing mechanism is
> HVMOP_guest_request_vm_event, but this is restricted to kernel usecases
> like all other hypercalls.
>
> Introduce a mechanism whereby the introspection agent can whitelist the
> use of HVMOP_guest_request_vm_event directly from userspace.
>
> Signed-off-by: Alexandru Isaila <aisaila@xxxxxxxxxxxxxxx>
>
> ---
> Changes since V4:
>         - Changed function mane from xc_allow_guest_userspace_event
>           to xc_monitor_guest_userspace_event
>         - Fixed guest_request_enabled check
>         - Delete the guest_request_sync
>         - Changed guest_request_userspace_event to
>           guest_request_userspace_enabled
>         - Moved guest_request_userspace_enabled flag from sched.h to
>           domain.h
> ---
>  tools/libxc/include/xenctrl.h |  1 +
>  tools/libxc/xc_monitor.c      | 14 ++++++++++++++
>  xen/arch/x86/hvm/hypercall.c  |  5 +++++
>  xen/common/monitor.c          | 13 +++++++++++++
>  xen/include/asm-x86/domain.h  | 19 ++++++++++---------
>  xen/include/public/domctl.h   | 21 +++++++++++----------
>  6 files changed, 54 insertions(+), 19 deletions(-)
>
> diff --git a/tools/libxc/include/xenctrl.h b/tools/libxc/include/xenctrl.h
> index bde8313..c72e12d 100644
> --- a/tools/libxc/include/xenctrl.h
> +++ b/tools/libxc/include/xenctrl.h
> @@ -2022,6 +2022,7 @@ int xc_monitor_descriptor_access(xc_interface *xch, 
> domid_t domain_id,
>                                   bool enable);
>  int xc_monitor_guest_request(xc_interface *xch, domid_t domain_id,
>                               bool enable, bool sync);
> +int xc_monitor_guest_userspace_event(xc_interface *xch, domid_t domain_id, 
> bool enable);
>  int xc_monitor_debug_exceptions(xc_interface *xch, domid_t domain_id,
>                                  bool enable, bool sync);
>  int xc_monitor_cpuid(xc_interface *xch, domid_t domain_id, bool enable);
> diff --git a/tools/libxc/xc_monitor.c b/tools/libxc/xc_monitor.c
> index b44ce93..bd8cbcf 100644
> --- a/tools/libxc/xc_monitor.c
> +++ b/tools/libxc/xc_monitor.c
> @@ -161,6 +161,20 @@ int xc_monitor_guest_request(xc_interface *xch, domid_t 
> domain_id, bool enable,
>      return do_domctl(xch, &domctl);
>  }
>
> +int xc_monitor_guest_userspace_event(xc_interface *xch, domid_t domain_id, 
> bool enable)
> +{
> +    DECLARE_DOMCTL;
> +
> +    domctl.cmd = XEN_DOMCTL_monitor_op;
> +    domctl.domain = domain_id;
> +    domctl.u.monitor_op.op = enable ? XEN_DOMCTL_MONITOR_OP_ENABLE
> +                                    : XEN_DOMCTL_MONITOR_OP_DISABLE;
> +    domctl.u.monitor_op.event = 
> XEN_DOMCTL_MONITOR_EVENT_GUEST_USERSPACE_EVENT;
> +
> +    return do_domctl(xch, &domctl);
> +}
> +
> +
>  int xc_monitor_emulate_each_rep(xc_interface *xch, domid_t domain_id,
>                                  bool enable)
>  {
> diff --git a/xen/arch/x86/hvm/hypercall.c b/xen/arch/x86/hvm/hypercall.c
> index e7238ce..5742dd1 100644
> --- a/xen/arch/x86/hvm/hypercall.c
> +++ b/xen/arch/x86/hvm/hypercall.c
> @@ -155,6 +155,11 @@ int hvm_hypercall(struct cpu_user_regs *regs)
>          /* Fallthrough to permission check. */
>      case 4:
>      case 2:
> +        if ( currd->arch.monitor.guest_request_userspace_enabled &&
> +            eax == __HYPERVISOR_hvm_op &&
> +            (mode == 8 ? regs->rdi : regs->ebx) == 
> HVMOP_guest_request_vm_event )
> +            break;
> +

So the CPL check happens after the monitor check, which means this
will trigger regardless if the hypercall is coming from userspace or
kernelspace. Since the monitor option specifically says userspace,
this should probably get moved into the block where CPL was checked.

>          if ( unlikely(hvm_get_cpl(curr)) )
>          {
>      default:
> diff --git a/xen/common/monitor.c b/xen/common/monitor.c
> index 451f42f..080a405 100644
> --- a/xen/common/monitor.c
> +++ b/xen/common/monitor.c
> @@ -79,6 +79,19 @@ int monitor_domctl(struct domain *d, struct 
> xen_domctl_monitor_op *mop)
>          break;
>      }
>
> +    case XEN_DOMCTL_MONITOR_EVENT_GUEST_USERSPACE_EVENT:
> +    {
> +        bool old_status = d->arch.monitor.guest_request_userspace_enabled;
> +
> +        if ( unlikely(old_status == requested_status) )
> +            return -EEXIST;
> +
> +        domain_pause(d);
> +        d->arch.monitor.guest_request_userspace_enabled = requested_status;
> +        domain_unpause(d);
> +        break;
> +    }
> +
>      default:
>          /* Give arch-side the chance to handle this event */
>          return arch_monitor_domctl_event(d, mop);
> diff --git a/xen/include/asm-x86/domain.h b/xen/include/asm-x86/domain.h
> index c10522b..de02507 100644
> --- a/xen/include/asm-x86/domain.h
> +++ b/xen/include/asm-x86/domain.h
> @@ -396,15 +396,16 @@ struct arch_domain
>
>      /* 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 singlestep_enabled          : 1;
> -        unsigned int software_breakpoint_enabled : 1;
> -        unsigned int debug_exception_enabled     : 1;
> -        unsigned int debug_exception_sync        : 1;
> -        unsigned int cpuid_enabled               : 1;
> -        unsigned int descriptor_access_enabled   : 1;
> +        unsigned int write_ctrlreg_enabled                                 : 
> 4;
> +        unsigned int write_ctrlreg_sync                                    : 
> 4;
> +        unsigned int write_ctrlreg_onchangeonly                            : 
> 4;
> +        unsigned int singlestep_enabled                                    : 
> 1;
> +        unsigned int software_breakpoint_enabled                           : 
> 1;
> +        unsigned int debug_exception_enabled                               : 
> 1;
> +        unsigned int debug_exception_sync                                  : 
> 1;
> +        unsigned int cpuid_enabled                                         : 
> 1;
> +        unsigned int descriptor_access_enabled                             : 
> 1;
> +        unsigned int guest_request_userspace_enabled                       : 
> 1;
>          struct monitor_msr_bitmap *msr_bitmap;
>          uint64_t write_ctrlreg_mask[4];
>      } monitor;
> diff --git a/xen/include/public/domctl.h b/xen/include/public/domctl.h
> index ff39762..870495c 100644
> --- a/xen/include/public/domctl.h
> +++ b/xen/include/public/domctl.h
> @@ -1073,16 +1073,17 @@ DEFINE_XEN_GUEST_HANDLE(xen_domctl_psr_cmt_op_t);
>  #define XEN_DOMCTL_MONITOR_OP_GET_CAPABILITIES  2
>  #define XEN_DOMCTL_MONITOR_OP_EMULATE_EACH_REP  3
>
> -#define XEN_DOMCTL_MONITOR_EVENT_WRITE_CTRLREG         0
> -#define XEN_DOMCTL_MONITOR_EVENT_MOV_TO_MSR            1
> -#define XEN_DOMCTL_MONITOR_EVENT_SINGLESTEP            2
> -#define XEN_DOMCTL_MONITOR_EVENT_SOFTWARE_BREAKPOINT   3
> -#define XEN_DOMCTL_MONITOR_EVENT_GUEST_REQUEST         4
> -#define XEN_DOMCTL_MONITOR_EVENT_DEBUG_EXCEPTION       5
> -#define XEN_DOMCTL_MONITOR_EVENT_CPUID                 6
> -#define XEN_DOMCTL_MONITOR_EVENT_PRIVILEGED_CALL       7
> -#define XEN_DOMCTL_MONITOR_EVENT_INTERRUPT             8
> -#define XEN_DOMCTL_MONITOR_EVENT_DESC_ACCESS           9
> +#define XEN_DOMCTL_MONITOR_EVENT_WRITE_CTRLREG                               
>  0
> +#define XEN_DOMCTL_MONITOR_EVENT_MOV_TO_MSR                                  
>  1
> +#define XEN_DOMCTL_MONITOR_EVENT_SINGLESTEP                                  
>  2
> +#define XEN_DOMCTL_MONITOR_EVENT_SOFTWARE_BREAKPOINT                         
>  3
> +#define XEN_DOMCTL_MONITOR_EVENT_GUEST_REQUEST                               
>  4
> +#define XEN_DOMCTL_MONITOR_EVENT_DEBUG_EXCEPTION                             
>  5
> +#define XEN_DOMCTL_MONITOR_EVENT_CPUID                                       
>  6
> +#define XEN_DOMCTL_MONITOR_EVENT_PRIVILEGED_CALL                             
>  7
> +#define XEN_DOMCTL_MONITOR_EVENT_INTERRUPT                                   
>  8
> +#define XEN_DOMCTL_MONITOR_EVENT_DESC_ACCESS                                 
>  9
> +#define XEN_DOMCTL_MONITOR_EVENT_GUEST_USERSPACE_EVENT                       
> 10
>
>  struct xen_domctl_monitor_op {
>      uint32_t op; /* XEN_DOMCTL_MONITOR_OP_* */
> --
> 2.7.4

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

 


Rackspace

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