[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-changelog] EVTCHNOP_alloc_unbound can allocate a port in an arbitrary
# HG changeset patch # User kaf24@xxxxxxxxxxxxxxxxxxxx # Node ID c3d9b7013b1442bcc8890da3b60e8e19688ac1a0 # Parent 6f71824a45c19e860a3655dd8e76a83e047c84d2 EVTCHNOP_alloc_unbound can allocate a port in an arbitrary domain (only if the caller is sufficiently privileged). Signed-off-by: Keir Fraser <keir@xxxxxxxxxxxxx> diff -r 6f71824a45c1 -r c3d9b7013b14 linux-2.6-xen-sparse/drivers/xen/blkfront/blkfront.c --- a/linux-2.6-xen-sparse/drivers/xen/blkfront/blkfront.c Wed Oct 5 17:06:42 2005 +++ b/linux-2.6-xen-sparse/drivers/xen/blkfront/blkfront.c Wed Oct 5 18:14:13 2005 @@ -485,7 +485,7 @@ static int setup_blkring(struct xenbus_device *dev, struct blkfront_info *info) { blkif_sring_t *sring; - evtchn_op_t op = { .cmd = EVTCHNOP_alloc_unbound }; + evtchn_op_t op; int err; info->ring_ref = GRANT_INVALID_REF; @@ -508,7 +508,9 @@ } info->ring_ref = err; - op.u.alloc_unbound.dom = info->backend_id; + op.cmd = EVTCHNOP_alloc_unbound; + op.u.alloc_unbound.dom = DOMID_SELF; + op.u.alloc_unbound.remote_dom = info->backend_id; err = HYPERVISOR_event_channel_op(&op); if (err) { gnttab_end_foreign_access(info->ring_ref, 0); @@ -518,7 +520,9 @@ xenbus_dev_error(dev, err, "allocating event channel"); return err; } + blkif_connect(info, op.u.alloc_unbound.port); + return 0; } diff -r 6f71824a45c1 -r c3d9b7013b14 linux-2.6-xen-sparse/drivers/xen/netfront/netfront.c --- a/linux-2.6-xen-sparse/drivers/xen/netfront/netfront.c Wed Oct 5 17:06:42 2005 +++ b/linux-2.6-xen-sparse/drivers/xen/netfront/netfront.c Wed Oct 5 18:14:13 2005 @@ -972,7 +972,7 @@ static int setup_device(struct xenbus_device *dev, struct netfront_info *info) { - evtchn_op_t op = { .cmd = EVTCHNOP_alloc_unbound }; + evtchn_op_t op; int err; info->tx_ring_ref = GRANT_INVALID_REF; @@ -1010,13 +1010,17 @@ } info->rx_ring_ref = err; - op.u.alloc_unbound.dom = info->backend_id; + op.cmd = EVTCHNOP_alloc_unbound; + op.u.alloc_unbound.dom = DOMID_SELF; + op.u.alloc_unbound.remote_dom = info->backend_id; err = HYPERVISOR_event_channel_op(&op); if (err) { xenbus_dev_error(dev, err, "allocating event channel"); goto out; } + connect_device(info, op.u.alloc_unbound.port); + return 0; out: diff -r 6f71824a45c1 -r c3d9b7013b14 linux-2.6-xen-sparse/drivers/xen/tpmfront/tpmfront.c --- a/linux-2.6-xen-sparse/drivers/xen/tpmfront/tpmfront.c Wed Oct 5 17:06:42 2005 +++ b/linux-2.6-xen-sparse/drivers/xen/tpmfront/tpmfront.c Wed Oct 5 18:14:13 2005 @@ -244,8 +244,7 @@ { tpmif_tx_interface_t *sring; struct tpm_private *tp = &my_private; - - evtchn_op_t op = { .cmd = EVTCHNOP_alloc_unbound }; + evtchn_op_t op; int err; sring = (void *)__get_free_page(GFP_KERNEL); @@ -269,7 +268,9 @@ } info->ring_ref = err; - op.u.alloc_unbound.dom = backend_id; + op.cmd = EVTCHNOP_alloc_unbound; + op.u.alloc_unbound.dom = DOMID_SELF; + op.u.alloc_unbound.remote_dom = backend_id; err = HYPERVISOR_event_channel_op(&op); if (err) { gnttab_end_foreign_access(info->ring_ref, 0); @@ -278,7 +279,9 @@ xenbus_dev_error(dev, err, "allocating event channel"); return err; } + tpmif_connect(op.u.alloc_unbound.port, backend_id); + return 0; } diff -r 6f71824a45c1 -r c3d9b7013b14 tools/libxc/xc_evtchn.c --- a/tools/libxc/xc_evtchn.c Wed Oct 5 17:06:42 2005 +++ b/tools/libxc/xc_evtchn.c Wed Oct 5 18:14:13 2005 @@ -33,6 +33,7 @@ int xc_evtchn_alloc_unbound(int xc_handle, + u32 remote_dom, u32 dom, int *port) { @@ -40,6 +41,7 @@ int rc; op.cmd = EVTCHNOP_alloc_unbound; + op.u.alloc_unbound.remote_dom = (domid_t)remote_dom; op.u.alloc_unbound.dom = (domid_t)dom; op.u.alloc_unbound.port = (port != NULL) ? *port : 0; diff -r 6f71824a45c1 -r c3d9b7013b14 tools/libxc/xenctrl.h --- a/tools/libxc/xenctrl.h Wed Oct 5 17:06:42 2005 +++ b/tools/libxc/xenctrl.h Wed Oct 5 18:14:13 2005 @@ -306,13 +306,15 @@ * well-known port within a domain to receive events on. * * @parm xc_handle a handle to an open hypervisor interface - * @parm dom the ID of the domain. This maybe DOMID_SELF + * @parm remote_dom the ID of the domain who will later bind + * @parm dom the ID of the local domain (the 'allocatee') * @parm port a pointer to a port. This is an in/out parameter. If *port is * 0, then a new port will be assigned, if port is > 0 then that * port is allocated if the port is unallocated. * @return 0 on success, -1 on failure */ int xc_evtchn_alloc_unbound(int xc_handle, + u32 remote_dom, u32 dom, int *port); diff -r 6f71824a45c1 -r c3d9b7013b14 tools/python/xen/lowlevel/xc/xc.c --- a/tools/python/xen/lowlevel/xc/xc.c Wed Oct 5 17:06:42 2005 +++ b/tools/python/xen/lowlevel/xc/xc.c Wed Oct 5 18:14:13 2005 @@ -432,16 +432,16 @@ { XcObject *xc = (XcObject *)self; - u32 dom; + u32 dom = DOMID_SELF, remote_dom; int port = 0; - static char *kwd_list[] = { "dom", "port", NULL }; - - if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|i", kwd_list, - &dom, &port) ) - return NULL; - - if ( xc_evtchn_alloc_unbound(xc->xc_handle, dom, &port) != 0 ) + static char *kwd_list[] = { "remote_dom", "dom", "port", NULL }; + + if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|ii", kwd_list, + &remote_dom, &dom, &port) ) + return NULL; + + if ( xc_evtchn_alloc_unbound(xc->xc_handle, remote_dom, dom, &port) != 0 ) return PyErr_SetFromErrno(xc_error); return PyInt_FromLong(port); diff -r 6f71824a45c1 -r c3d9b7013b14 xen/common/event_channel.c --- a/xen/common/event_channel.c Wed Oct 5 17:06:42 2005 +++ b/xen/common/event_channel.c Wed Oct 5 18:14:13 2005 @@ -63,9 +63,18 @@ static long evtchn_alloc_unbound(evtchn_alloc_unbound_t *alloc) { struct evtchn *chn; - struct domain *d = current->domain; + struct domain *d; int port = alloc->port; + domid_t dom = alloc->dom; long rc = 0; + + if ( dom == DOMID_SELF ) + dom = current->domain->domain_id; + else if ( !IS_PRIV(current->domain) ) + return -EPERM; + + if ( (d = find_domain_by_id(dom)) == NULL ) + return -ESRCH; spin_lock(&d->evtchn_lock); @@ -84,11 +93,11 @@ { case ECS_FREE: chn->state = ECS_UNBOUND; - chn->u.unbound.remote_domid = alloc->dom; + chn->u.unbound.remote_domid = alloc->remote_dom; break; case ECS_UNBOUND: - if ( chn->u.unbound.remote_domid != alloc->dom ) + if ( chn->u.unbound.remote_domid != alloc->remote_dom ) ERROR_EXIT(-EINVAL); break; @@ -99,7 +108,10 @@ out: spin_unlock(&d->evtchn_lock); + put_domain(d); + alloc->port = port; + return rc; } diff -r 6f71824a45c1 -r c3d9b7013b14 xen/include/public/event_channel.h --- a/xen/include/public/event_channel.h Wed Oct 5 17:06:42 2005 +++ b/xen/include/public/event_channel.h Wed Oct 5 18:14:13 2005 @@ -10,14 +10,16 @@ #define __XEN_PUBLIC_EVENT_CHANNEL_H__ /* - * EVTCHNOP_alloc_unbound: Prepare a local port for binding to <dom>. - * <port> may be wildcarded by setting to zero, in which case a fresh port - * will be allocated, and the field filled in on return. + * EVTCHNOP_alloc_unbound: Allocate a port in <dom> for later binding to + * <remote_dom>. <port> may be wildcarded by setting to zero, in which case a + * fresh port will be allocated, and the field filled in on return. + * NOTES: + * 1. If the caller is unprivileged then <dom> must be DOMID_SELF. */ #define EVTCHNOP_alloc_unbound 6 typedef struct evtchn_alloc_unbound { /* IN parameters */ - domid_t dom; + domid_t dom, remote_dom; /* IN/OUT parameters */ u32 port; } evtchn_alloc_unbound_t; _______________________________________________ Xen-changelog mailing list Xen-changelog@xxxxxxxxxxxxxxxxxxx http://lists.xensource.com/xen-changelog
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |