All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH] New XEN_DOMCTL_set_target and IS_PRIV_FOR
@ 2008-01-23 11:55 ` Samuel Thibault
  2008-01-23 14:28   ` John Levon
  0 siblings, 1 reply; 8+ messages in thread
From: Samuel Thibault @ 2008-01-23 11:55 UTC (permalink / raw)
  To: xen-devel

New XEN_DOMCTL_set_target
Stubdomains (and probably other domain disagregation elements too) need
to be able to tinker with another domain.  This adds IS_PRIV_FOR that
extends IS_PRIV by allowing domains to have privileges over a given
"target" domain.  XEN_DOMCTL_set_target permits to set this "target".  A
new 'target' configuration option makes the domain builder use it.

Signed-off-by: Samuel Thibault <samuel.thibault@eu.citrix.com>

diff -r bcae9d2cc2f8 tools/libxc/xc_domain.c
--- a/tools/libxc/xc_domain.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/libxc/xc_domain.c	Wed Jan 23 11:36:15 2008 +0000
@@ -875,6 +875,20 @@
     return do_domctl(xc_handle, &domctl);
 }
 
+int xc_domain_set_target(
+    int xc_handle,
+    uint32_t domid,
+    uint32_t target)
+{
+    DECLARE_DOMCTL;
+
+    domctl.cmd = XEN_DOMCTL_set_target;
+    domctl.domain = domid;
+    domctl.u.set_target.target = target;
+
+    return do_domctl(xc_handle, &domctl);
+}
+
 /*
  * Local variables:
  * mode: C
--- a/tools/libxc/xenctrl.h	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/libxc/xenctrl.h	Wed Jan 23 11:36:15 2008 +0000
@@ -952,4 +952,9 @@
                               uint32_t domid,
                               uint8_t machine_irq);
 
+/* Set the target domain */
+int xc_domain_set_target(int xc_handle,
+                         uint32_t domid,
+                         uint32_t target);
+
 #endif /* XENCTRL_H */
--- a/tools/python/xen/lowlevel/xc/xc.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/python/xen/lowlevel/xc/xc.c	Wed Jan 23 11:36:15 2008 +0000
@@ -96,17 +96,17 @@
                                     PyObject *args,
                                     PyObject *kwds)
 {
-    uint32_t dom = 0, ssidref = 0, flags = 0;
+    uint32_t dom = 0, ssidref = 0, flags = 0, target = 0;
     int      ret, i, hvm = 0;
     PyObject *pyhandle = NULL;
     xen_domain_handle_t handle = { 
         0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef,
         0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef };
 
-    static char *kwd_list[] = { "domid", "ssidref", "handle", "hvm", NULL };
+    static char *kwd_list[] = { "domid", "ssidref", "handle", "hvm", "target", NULL };
 
-    if ( !PyArg_ParseTupleAndKeywords(args, kwds, "|iiOi", kwd_list,
-                                      &dom, &ssidref, &pyhandle, &hvm))
+    if ( !PyArg_ParseTupleAndKeywords(args, kwds, "|iiOii", kwd_list,
+				      &dom, &ssidref, &pyhandle, &hvm, &target))
         return NULL;
 
     if ( pyhandle != NULL )
@@ -130,6 +130,11 @@
     if ( (ret = xc_domain_create(self->xc_handle, ssidref,
                                  handle, flags, &dom)) < 0 )
         return pyxc_error_to_exception();
+
+    if ( target )
+        if ( (ret = xc_domain_set_target(self->xc_handle, dom, target)) < 0 )
+            return pyxc_error_to_exception();
+
 
     return PyInt_FromLong(dom);
 
--- a/tools/python/xen/xend/XendConfig.py	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/python/xen/xend/XendConfig.py	Wed Jan 23 11:36:15 2008 +0000
@@ -170,6 +170,7 @@
     'platform': dict,
     'tools_version': dict,
     'other_config': dict,
+    'target': int,
     'security_label': str,
     'pci': str,
 }
@@ -336,7 +337,8 @@
             'vbd_refs': [],
             'vtpm_refs': [],
             'other_config': {},
-            'platform': {}
+            'platform': {},
+            'target': 0,
         }
         
         return defaults
@@ -1585,6 +1587,9 @@
     def is_hvm(self):
         return self['HVM_boot_policy'] != ''
 
+    def target(self):
+	return self['target']
+
     def image_type(self):
         stored_type = self['platform'].get('image_type')
         return stored_type or (self.is_hvm() and 'hvm' or 'linux')
--- a/tools/python/xen/xend/XendDomainInfo.py	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/python/xen/xend/XendDomainInfo.py	Wed Jan 23 11:36:15 2008 +0000
@@ -1640,7 +1640,8 @@
                 domid = 0,
                 ssidref = ssidref,
                 handle = uuid.fromString(self.info['uuid']),
-                hvm = int(hvm))
+                hvm = int(hvm),
+                target = self.info.target())
         except Exception, e:
             # may get here if due to ACM the operation is not permitted
             if security.on():
--- a/tools/python/xen/xm/create.py	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/python/xen/xm/create.py	Wed Jan 23 11:36:15 2008 +0000
@@ -521,6 +521,10 @@
           - suspend:        Domain is suspended;
           """)
 
+gopts.var('target', val='TARGET',
+          fn=set_int, default=0,
+          use="Set domain target.")
+
 def err(msg):
     """Print an error to stderr and exit.
     """
@@ -748,7 +752,7 @@
     map(add_conf, ['name', 'memory', 'maxmem', 'shadow_memory',
                    'restart', 'on_poweroff',
                    'on_reboot', 'on_crash', 'vcpus', 'vcpu_avail', 'features',
-                   'on_xend_start', 'on_xend_stop'])
+                   'on_xend_start', 'on_xend_stop', 'target'])
 
     if vals.uuid is not None:
         config.append(['uuid', vals.uuid])
--- a/xen/arch/ia64/vmx/vmx_hypercall.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/arch/ia64/vmx/vmx_hypercall.c	Wed Jan 23 11:36:15 2008 +0000
@@ -47,15 +47,16 @@
     if ( copy_from_guest(&op, uop, 1) )
         return -EFAULT;
 
-    if ( !IS_PRIV(current->domain) )
-        return -EPERM;
-
     if ( op.isa_irq > 15 )
         return -EINVAL;
 
     d = rcu_lock_domain_by_id(op.domid);
     if ( d == NULL )
         return -ESRCH;
+
+    rc = -EPERM;
+    if ( !IS_PRIV_FOR(current->domain, d) )
+        goto out;
 
     rc = -EINVAL;
     if ( !is_hvm_domain(d) )
@@ -79,15 +80,16 @@
     if ( copy_from_guest(&op, uop, 1) )
         return -EFAULT;
 
-    if ( !IS_PRIV(current->domain) )
-        return -EPERM;
-
     if ( (op.domain > 0) || (op.bus > 0) || (op.device > 31) || (op.intx > 3) )
         return -EINVAL;
 
     d = rcu_lock_domain_by_id(op.domid);
     if ( d == NULL )
         return -ESRCH;
+
+    rc = -EPERM;
+    if ( !IS_PRIV_FOR(current->domain, d) )
+        goto out;
 
     rc = -EINVAL;
     if ( !is_hvm_domain(d) )
@@ -124,13 +126,15 @@
         if (a.domid == DOMID_SELF) {
             d = rcu_lock_current_domain();
         }
-        else if (IS_PRIV(current->domain)) {
+        else {
             d = rcu_lock_domain_by_id(a.domid);
             if (d == NULL)
                 return -ESRCH;
+            if (!IS_PRIV_FOR(current->domain, d)) {
+                rcu_unlock_domain(d);
+                return -EPERM;
+            }
         }
-        else
-            return -EPERM;
 
         if (op == HVMOP_set_param) {
             struct vmx_ioreq_page *iorp;
--- a/xen/arch/ia64/xen/dom0_ops.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/arch/ia64/xen/dom0_ops.c	Wed Jan 23 11:36:15 2008 +0000
@@ -37,9 +37,6 @@
 {
     long ret = 0;
 
-    if ( !IS_PRIV(current->domain) )
-        return -EPERM;
-
     switch ( op->cmd )
     {
     case XEN_DOMCTL_getmemlist:
@@ -54,6 +51,13 @@
             ret = -EINVAL;
             break;
         }
+
+        if ( !IS_PRIV_FOR(current->domain, d) ) {
+            ret = -EPERM;
+            rcu_unlock_domain(d);
+            break;
+        }
+
         for (i = 0 ; i < nr_pages ; i++) {
             pte_t *pte;
 
@@ -84,6 +88,12 @@
 
         if ( d == NULL) {
             ret = -EINVAL;
+            break;
+        }
+
+        if ( !IS_PRIV_FOR(current->domain, d) ) {
+            ret = -EPERM;
+            rcu_unlock_domain(d);
             break;
         }
 
@@ -153,6 +163,12 @@
         d = rcu_lock_domain_by_id(op->domain);
         if ( d != NULL )
         {
+            if ( !IS_PRIV_FOR(current->domain, d) ) {
+                ret = -EPERM;
+                rcu_unlock_domain(d);
+                break;
+            }
+
             ret = shadow_mode_control(d, &op->u.shadow_op);
             rcu_unlock_domain(d);
             if (copy_to_guest(u_domctl, op, 1))
@@ -172,6 +188,12 @@
         d = rcu_lock_domain_by_id(op->domain);
         if (unlikely(d == NULL))
             break;
+
+        if ( !IS_PRIV_FOR(current->domain, d) ) {
+            ret = -EPERM;
+            rcu_unlock_domain(d);
+            break;
+        }
 
         if (np == 0)
             ret = 0;
@@ -195,6 +217,11 @@
         d = rcu_lock_domain_by_id(op->domain);
         if ( d == NULL )
             break;
+
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) ) {
+            goto sendtrigger_out;
+        }
 
         ret = -EINVAL;
         if ( op->u.sendtrigger.vcpu >= MAX_VIRT_CPUS )
@@ -239,6 +266,10 @@
         if (d == NULL)
             break;
 
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto sethvmcontext_out;
+
 #ifdef CONFIG_X86
         ret = xsm_hvmcontext(d, op->cmd);
         if (ret)
@@ -279,6 +310,10 @@
         d = rcu_lock_domain_by_id(op->domain);
         if (d == NULL)
             break;
+
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto gethvmcontext_out;
 
 #ifdef CONFIG_X86
         ret = xsm_hvmcontext(d, op->cmd);
@@ -341,7 +376,10 @@
             break;
         }
 
-        ret = domain_opt_feature(d, optf);
+        ret = -EPERM;
+        if ( IS_PRIV_FOR(current->domain, d) )
+            ret = domain_opt_feature(d, optf);
+
         rcu_unlock_domain(d);
     }
     break;
--- a/xen/arch/ia64/xen/hypercall.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/arch/ia64/xen/hypercall.c	Wed Jan 23 11:36:15 2008 +0000
@@ -500,13 +500,15 @@
     struct domain *d;
     long ret = 0;
 
-    if (!IS_PRIV(current->domain))
-        return -EPERM;
     if (copy_from_guest(op, u_debug_op, 1))
         return -EFAULT;
     d = rcu_lock_domain_by_id(domain);
     if (d == NULL)
         return -ESRCH;
+    if (!IS_PRIV_FOR(current->domain, d)) {
+        ret = -EPERM;
+        goto out;
+    }
 
     switch (cmd) {
     case XEN_IA64_DEBUG_OP_SET_FLAGS:
@@ -520,6 +522,7 @@
     default:
         ret = -ENOSYS;
     }
+out:
     rcu_unlock_domain(d);
     return ret;
 }
--- a/xen/arch/ia64/xen/mm.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/arch/ia64/xen/mm.c	Wed Jan 23 11:36:15 2008 +0000
@@ -2787,10 +2787,14 @@
 
         if (xatp.domid == DOMID_SELF)
             d = rcu_lock_current_domain();
-        else if (!IS_PRIV(current->domain))
-            return -EPERM;
-        else if ((d = rcu_lock_domain_by_id(xatp.domid)) == NULL)
-            return -ESRCH;
+        else {
+            if ((d = rcu_lock_domain_by_id(xatp.domid)) == NULL)
+                return -ESRCH;
+            if (!IS_PRIV_FOR(current->domain,d)) {
+                rcu_lock_domain(d);
+                return -EPERM;
+            }
+        }
 
         /* This hypercall is used for VT-i domain only */
         if (!VMX_DOMAIN(d->vcpu[0])) {
--- a/xen/arch/ia64/xen/xensetup.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/arch/ia64/xen/xensetup.c	Wed Jan 23 11:36:15 2008 +0000
@@ -642,6 +642,7 @@
         panic("Cannot allocate dom0 vcpu 0\n");
 
     dom0->is_privileged = 1;
+    dom0->target = NULL;
 
     /*
      * We're going to setup domain0 using the module(s) that we stashed safely
--- a/xen/arch/powerpc/setup.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/arch/powerpc/setup.c	Wed Jan 23 11:36:15 2008 +0000
@@ -375,6 +375,7 @@
     dom0->vcpu[0]->cpu_affinity = cpumask_of_cpu(0);
 
     dom0->is_privileged = 1;
+    dom0->target = NULL;
 
     /* scrub_heap_pages() requires IRQs enabled, and we're post IRQ setup... */
     local_irq_enable();
--- a/xen/arch/x86/hvm/hvm.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/arch/x86/hvm/hvm.c	Wed Jan 23 11:36:15 2008 +0000
@@ -1740,15 +1740,16 @@
     if ( copy_from_guest(&op, uop, 1) )
         return -EFAULT;
 
-    if ( !IS_PRIV(current->domain) )
-        return -EPERM;
-
     if ( (op.domain > 0) || (op.bus > 0) || (op.device > 31) || (op.intx > 3) )
         return -EINVAL;
 
     d = rcu_lock_domain_by_id(op.domid);
     if ( d == NULL )
         return -ESRCH;
+
+    rc = -EPERM;
+    if ( !IS_PRIV_FOR(current->domain, d) )
+        goto out;
 
     rc = -EINVAL;
     if ( !is_hvm_domain(d) )
@@ -1787,15 +1788,16 @@
     if ( copy_from_guest(&op, uop, 1) )
         return -EFAULT;
 
-    if ( !IS_PRIV(current->domain) )
-        return -EPERM;
-
     if ( op.isa_irq > 15 )
         return -EINVAL;
 
     d = rcu_lock_domain_by_id(op.domid);
     if ( d == NULL )
         return -ESRCH;
+
+    rc = -EPERM;
+    if ( !IS_PRIV_FOR(current->domain, d) )
+        goto out;
 
     rc = -EINVAL;
     if ( !is_hvm_domain(d) )
@@ -1834,15 +1836,16 @@
     if ( copy_from_guest(&op, uop, 1) )
         return -EFAULT;
 
-    if ( !IS_PRIV(current->domain) )
-        return -EPERM;
-
     if ( (op.link > 3) || (op.isa_irq > 15) )
         return -EINVAL;
 
     d = rcu_lock_domain_by_id(op.domid);
     if ( d == NULL )
         return -ESRCH;
+
+    rc = -EPERM;
+    if ( !IS_PRIV_FOR(current->domain, d) )
+        goto out;
 
     rc = -EINVAL;
     if ( !is_hvm_domain(d) )
@@ -1921,13 +1924,16 @@
 
         if ( a.domid == DOMID_SELF )
             d = rcu_lock_current_domain();
-        else if ( IS_PRIV(current->domain) )
+        else {
             d = rcu_lock_domain_by_id(a.domid);
-        else
-            return -EPERM;
+            if ( d == NULL )
+                return -ESRCH;
+            if ( !IS_PRIV_FOR(current->domain, d) ) {
+                rc = -EPERM;
+                goto param_fail;
+            }
+        }
 
-        if ( d == NULL )
-            return -ESRCH;
 
         rc = -EINVAL;
         if ( !is_hvm_domain(d) )
--- a/xen/arch/x86/mm.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/arch/x86/mm.c	Wed Jan 23 11:36:15 2008 +0000
@@ -2056,38 +2056,35 @@
         MEM_LOG("Cannot mix foreign mappings with translated domains");
         okay = 0;
     }
-    else if ( !IS_PRIV(d) )
+    else switch ( domid )
     {
-        switch ( domid )
-        {
-        case DOMID_IO:
-            info->foreign = rcu_lock_domain(dom_io);
-            break;
-        default:
+    case DOMID_IO:
+        info->foreign = rcu_lock_domain(dom_io);
+        break;
+    case DOMID_XEN:
+        if (!IS_PRIV(d)) {
             MEM_LOG("Cannot set foreign dom");
             okay = 0;
             break;
         }
-    }
-    else
-    {
-        info->foreign = e = rcu_lock_domain_by_id(domid);
+        info->foreign = rcu_lock_domain(dom_xen);
+        break;
+    default:
+        e = rcu_lock_domain_by_id(domid);
         if ( e == NULL )
         {
-            switch ( domid )
-            {
-            case DOMID_XEN:
-                info->foreign = rcu_lock_domain(dom_xen);
-                break;
-            case DOMID_IO:
-                info->foreign = rcu_lock_domain(dom_io);
-                break;
-            default:
-                MEM_LOG("Unknown domain '%u'", domid);
-                okay = 0;
-                break;
-            }
+            MEM_LOG("Unknown domain '%u'", domid);
+            okay = 0;
+            break;
         }
+        if (!IS_PRIV_FOR(d, e)) {
+            MEM_LOG("Cannot set foreign dom");
+            okay = 0;
+            rcu_unlock_domain(e);
+            break;
+        }
+        info->foreign = e;
+        break;
     }
 
  out:
@@ -3043,9 +3040,6 @@
 {
     int rc;
 
-    if ( unlikely(!IS_PRIV(current->domain)) )
-        return -EPERM;
-
     if ( !set_foreigndom(domid) )
         return -ESRCH;
 
@@ -3222,10 +3216,15 @@
 
         if ( xatp.domid == DOMID_SELF )
             d = rcu_lock_current_domain();
-        else if ( !IS_PRIV(current->domain) )
-            return -EPERM;
-        else if ( (d = rcu_lock_domain_by_id(xatp.domid)) == NULL )
-            return -ESRCH;
+        else {
+            d = rcu_lock_domain_by_id(xatp.domid);
+            if ( d == NULL )
+                return -ESRCH;
+            if ( !IS_PRIV_FOR(current->domain, d) ) {
+                rcu_unlock_domain(d);
+                return -EPERM;
+            }
+        }
 
         if ( xsm_add_to_physmap(current->domain, d) )
         {
@@ -3313,10 +3312,15 @@
 
         if ( fmap.domid == DOMID_SELF )
             d = rcu_lock_current_domain();
-        else if ( !IS_PRIV(current->domain) )
-            return -EPERM;
-        else if ( (d = rcu_lock_domain_by_id(fmap.domid)) == NULL )
-            return -ESRCH;
+        else {
+            d = rcu_lock_domain_by_id(fmap.domid);
+            if ( d == NULL )
+                return -ESRCH;
+            if ( !IS_PRIV_FOR(current->domain, d) ) {
+                rcu_unlock_domain(d);
+                return -EPERM;
+            }
+        }
 
         rc = xsm_domain_memory_map(d);
         if ( rc )
--- a/xen/arch/x86/mm/shadow/multi.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/arch/x86/mm/shadow/multi.c	Wed Jan 23 11:36:15 2008 +0000
@@ -993,11 +993,11 @@
     // not own, we let it succeed anyway.
     //
     if ( unlikely(!res) &&
-         IS_PRIV(d) &&
          !shadow_mode_translate(d) &&
          mfn_valid(mfn = shadow_l1e_get_mfn(sl1e)) &&
          (owner = page_get_owner(mfn_to_page(mfn))) &&
-         (d != owner) )
+         (d != owner) &&
+         IS_PRIV_FOR(d, owner))
     {
         res = get_page_from_l1e(sl1e, owner);
         SHADOW_PRINTK("privileged domain %d installs map of mfn %05lx "
--- a/xen/arch/x86/setup.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/arch/x86/setup.c	Wed Jan 23 11:36:15 2008 +0000
@@ -959,6 +959,7 @@
         panic("Error creating domain 0\n");
 
     dom0->is_privileged = 1;
+    dom0->target = NULL;
 
     /* Grab the DOM0 command line. */
     cmdline = (char *)(mod[0].string ? __va(mod[0].string) : NULL);
--- a/xen/common/domain.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/common/domain.c	Wed Jan 23 11:36:15 2008 +0000
@@ -502,6 +502,9 @@
         if ( (v = d->vcpu[i]) != NULL )
             free_vcpu_struct(v);
 
+    if (d->target)
+        put_domain(d->target);
+
     free_domain(d);
 
     send_guest_global_virq(dom0, VIRQ_DOM_EXC);
--- a/xen/common/domctl.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/common/domctl.c	Wed Jan 23 11:36:15 2008 +0000
@@ -182,9 +182,6 @@
     struct xen_domctl curop, *op = &curop;
     static DEFINE_SPINLOCK(domctl_lock);
 
-    if ( !IS_PRIV(current->domain) )
-        return -EPERM;
-
     if ( copy_from_guest(op, u_domctl, 1) )
         return -EFAULT;
 
@@ -206,6 +203,10 @@
         ret = -ESRCH;
         if ( d == NULL )
             break;
+
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto svc_out;
 
         ret = xsm_setvcpucontext(d);
         if ( ret )
@@ -258,6 +259,10 @@
         ret = -ESRCH;
         if ( d != NULL )
         {
+            ret = -EPERM;
+            if ( !IS_PRIV_FOR(current->domain, d) )
+                goto pausedomain_out;
+
             ret = xsm_pausedomain(d);
             if ( ret )
                 goto pausedomain_out;
@@ -282,16 +287,18 @@
         if ( d == NULL )
             break;
 
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto unpausedomain_out;
+
         ret = xsm_unpausedomain(d);
         if ( ret )
-        {
-            rcu_unlock_domain(d);
-            break;
-        }
+            goto unpausedomain_out;
 
         domain_unpause_by_systemcontroller(d);
+        ret = 0;
+unpausedomain_out:
         rcu_unlock_domain(d);
-        ret = 0;
     }
     break;
 
@@ -303,16 +310,18 @@
         if ( d == NULL )
             break;
 
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto resumedomain_out;
+
         ret = xsm_resumedomain(d);
         if ( ret )
-        {
-            rcu_unlock_domain(d);
-            break;
-        }
+            goto resumedomain_out;
 
         domain_resume(d);
+        ret = 0;
+resumedomain_out:
         rcu_unlock_domain(d);
-        ret = 0;
     }
     break;
 
@@ -322,6 +331,10 @@
         domid_t        dom;
         static domid_t rover = 0;
         unsigned int domcr_flags;
+
+        ret = -EPERM;
+        if ( !IS_PRIV(current->domain) )
+            break;
 
         ret = -EINVAL;
         if ( supervisor_mode_kernel ||
@@ -385,12 +398,13 @@
         if ( (d = rcu_lock_domain_by_id(op->domain)) == NULL )
             break;
 
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto maxvcpu_out2;
+
         ret = xsm_max_vcpus(d);
         if ( ret )
-        {
-            rcu_unlock_domain(d);
-            break;
-        }
+            goto maxvcpu_out2;
 
         /* Needed, for example, to ensure writable p.t. state is synced. */
         domain_pause(d);
@@ -418,6 +432,7 @@
 
     maxvcpu_out:
         domain_unpause(d);
+    maxvcpu_out2:
         rcu_unlock_domain(d);
     }
     break;
@@ -428,7 +443,9 @@
         ret = -ESRCH;
         if ( d != NULL )
         {
-            ret = xsm_destroydomain(d) ? : domain_kill(d);
+            ret = -EPERM;
+            if ( IS_PRIV_FOR(current->domain, d) )
+                ret = xsm_destroydomain(d) ? : domain_kill(d);
             rcu_unlock_domain(d);
         }
     }
@@ -445,6 +462,10 @@
         ret = -ESRCH;
         if ( d == NULL )
             break;
+
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto vcpuaffinity_out;
 
         ret = xsm_vcpuaffinity(op->cmd, d);
         if ( ret )
@@ -484,6 +505,10 @@
         if ( (d = rcu_lock_domain_by_id(op->domain)) == NULL )
             break;
 
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto scheduler_op_out;
+
         ret = xsm_scheduler(d);
         if ( ret )
             goto scheduler_op_out;
@@ -505,7 +530,7 @@
         rcu_read_lock(&domlist_read_lock);
 
         for_each_domain ( d )
-            if ( d->domain_id >= dom )
+            if ( d->domain_id >= dom && IS_PRIV_FOR(current->domain, d))
                 break;
 
         if ( d == NULL )
@@ -539,6 +564,10 @@
         ret = -ESRCH;
         if ( (d = rcu_lock_domain_by_id(op->domain)) == NULL )
             break;
+
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto getvcpucontext_out;
 
         ret = xsm_getvcpucontext(d);
         if ( ret )
@@ -600,6 +629,10 @@
         if ( (d = rcu_lock_domain_by_id(op->domain)) == NULL )
             break;
 
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto getvcpuinfo_out;
+
         ret = xsm_getvcpuinfo(d);
         if ( ret )
             goto getvcpuinfo_out;
@@ -639,6 +672,10 @@
         if ( d == NULL )
             break;
 
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto max_mem_out;
+
         ret = xsm_setdomainmaxmem(d);
         if ( ret )
             goto max_mem_out;
@@ -655,6 +692,8 @@
             d->max_pages = new_max;
             ret = 0;
         }
+        else
+            printk("new max %ld, tot pages %d\n", new_max, d->tot_pages);
         spin_unlock(&d->page_alloc_lock);
 
     max_mem_out:
@@ -671,17 +710,19 @@
         if ( d == NULL )
             break;
 
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto setdomainhandle_out;
+
         ret = xsm_setdomainhandle(d);
         if ( ret )
-        {
-            rcu_unlock_domain(d);
-            break;
-        }
+            goto setdomainhandle_out;
 
         memcpy(d->handle, op->u.setdomainhandle.handle,
                sizeof(xen_domain_handle_t));
+        ret = 0;
+setdomainhandle_out:
         rcu_unlock_domain(d);
-        ret = 0;
     }
     break;
 
@@ -694,18 +735,20 @@
         if ( d == NULL )
             break;
 
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto setdebugging_out;
+
         ret = xsm_setdebugging(d);
         if ( ret )
-        {
-            rcu_unlock_domain(d);
-            break;
-        }
+            goto setdebugging_out;
 
         domain_pause(d);
         d->debugger_attached = !!op->u.setdebugging.enable;
         domain_unpause(d); /* causes guest to latch new status */
+        ret = 0;
+setdebugging_out:
         rcu_unlock_domain(d);
-        ret = 0;
     }
     break;
 
@@ -722,6 +765,10 @@
         d = rcu_lock_domain_by_id(op->domain);
         if ( d == NULL )
             break;
+
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto irq_permission_out;
 
         ret = xsm_irq_permission(d, pirq, op->u.irq_permission.allow_access);
         if ( ret )
@@ -752,6 +799,10 @@
         if ( d == NULL )
             break;
 
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto iomem_permission_out;
+
         ret = xsm_iomem_permission(d, mfn, op->u.iomem_permission.allow_access);
         if ( ret )
             goto iomem_permission_out;
@@ -772,19 +823,61 @@
 
         ret = -ESRCH;
         d = rcu_lock_domain_by_id(op->domain);
-        if ( d != NULL )
-        {
-            ret = xsm_domain_settime(d);
-            if ( ret )
-            {
-                rcu_unlock_domain(d);
-                break;
-            }
+        if ( d == NULL )
+            break;
 
-            d->time_offset_seconds = op->u.settimeoffset.time_offset_seconds;
-            rcu_unlock_domain(d);
-            ret = 0;
+        ret = -EPERM;
+        if ( !IS_PRIV_FOR(current->domain, d) )
+            goto settimeoffset_out;
+
+        ret = xsm_domain_settime(d);
+        if ( ret )
+            goto settimeoffset_out;
+
+        d->time_offset_seconds = op->u.settimeoffset.time_offset_seconds;
+
+        ret = 0;
+settimeoffset_out:
+        rcu_unlock_domain(d);
+    }
+    break;
+
+    case XEN_DOMCTL_set_target:
+    {
+        struct domain *d, *e;
+
+        ret = -ESRCH;
+        d = rcu_lock_domain_by_id(op->domain);
+        if ( d == NULL )
+            break;
+
+        ret = -EPERM;
+        if (!IS_PRIV_FOR(current->domain, d))
+            goto set_target_out;
+
+        ret = -ESRCH;
+        e = get_domain_by_id(op->u.set_target.target);
+        if ( e == NULL )
+            goto set_target_out;
+
+        if ( d == e ) {
+            ret = -EINVAL;
+            put_domain(e);
+            goto set_target_out;
         }
+
+        if (!IS_PRIV_FOR(current->domain, e)) {
+            ret = -EPERM;
+            put_domain(e);
+            goto set_target_out;
+        }
+
+        d->target = e;
+        /* and we keep the reference on e, released when destroying d */
+        ret = 0;
+
+set_target_out:
+        rcu_unlock_domain(d);
     }
     break;
 
--- a/xen/common/event_channel.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/common/event_channel.c	Wed Jan 23 11:36:15 2008 +0000
@@ -130,12 +130,15 @@
     long           rc;
 
     if ( dom == DOMID_SELF )
-        dom = current->domain->domain_id;
-    else if ( !IS_PRIV(current->domain) )
-        return -EPERM;
-
-    if ( (d = rcu_lock_domain_by_id(dom)) == NULL )
-        return -ESRCH;
+        d = current->domain;
+    else {
+        if ( (d = rcu_lock_domain_by_id(dom)) == NULL )
+            return -ESRCH;
+        if ( !IS_PRIV_FOR(current->domain, d) ) {
+            rc = -EPERM;
+            goto out2;
+        }
+    }
 
     spin_lock(&d->evtchn_lock);
 
@@ -156,6 +159,7 @@
  out:
     spin_unlock(&d->evtchn_lock);
 
+ out2:
     rcu_unlock_domain(d);
 
     return rc;
@@ -197,7 +201,7 @@
         ERROR_EXIT_DOM(-EINVAL, rd);
     rchn = evtchn_from_port(rd, rport);
     if ( (rchn->state != ECS_UNBOUND) ||
-         (rchn->u.unbound.remote_domid != ld->domain_id) )
+            (rchn->u.unbound.remote_domid != ld->domain_id && !IS_PRIV_FOR(ld, rd)))
         ERROR_EXIT_DOM(-EINVAL, rd);
 
     rc = xsm_evtchn_interdomain(ld, lchn, rd, rchn);
@@ -628,12 +632,15 @@
     long             rc = 0;
 
     if ( dom == DOMID_SELF )
-        dom = current->domain->domain_id;
-    else if ( !IS_PRIV(current->domain) )
-        return -EPERM;
-
-    if ( (d = rcu_lock_domain_by_id(dom)) == NULL )
-        return -ESRCH;
+        d = current->domain;
+    else {
+        if ( (d = rcu_lock_domain_by_id(dom)) == NULL )
+            return -ESRCH;
+        if ( !IS_PRIV_FOR(current->domain, d) ) {
+            rc = -EPERM;
+            goto out2;
+        }
+    }
 
     spin_lock(&d->evtchn_lock);
 
@@ -684,6 +691,7 @@
 
  out:
     spin_unlock(&d->evtchn_lock);
+ out2:
     rcu_unlock_domain(d);
     return rc;
 }
@@ -782,26 +790,28 @@
     int rc;
 
     if ( dom == DOMID_SELF )
-        dom = current->domain->domain_id;
-    else if ( !IS_PRIV(current->domain) )
-        return -EPERM;
-
-    if ( (d = rcu_lock_domain_by_id(dom)) == NULL )
-        return -ESRCH;
+        d = current->domain;
+    else {
+        if ( (d = rcu_lock_domain_by_id(dom)) == NULL )
+            return -ESRCH;
+        if ( !IS_PRIV_FOR(current->domain, d) ) {
+            rc = -EPERM;
+            goto out;
+        }
+    }
 
     rc = xsm_evtchn_reset(current->domain, d);
     if ( rc )
-    {
-        rcu_unlock_domain(d);
-        return rc;
-    }
+        goto out;
 
     for ( i = 0; port_is_valid(d, i); i++ )
         (void)__evtchn_close(d, i);
 
+    rc = 0;
+out:
     rcu_unlock_domain(d);
 
-    return 0;
+    return rc;
 }
 
 
--- a/xen/common/grant_table.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/common/grant_table.c	Wed Jan 23 11:36:15 2008 +0000
@@ -834,19 +834,19 @@
     dom = op.dom;
     if ( dom == DOMID_SELF )
     {
-        dom = current->domain->domain_id;
+        d = current->domain;
     }
-    else if ( unlikely(!IS_PRIV(current->domain)) )
-    {
-        op.status = GNTST_permission_denied;
-        goto out;
-    }
-
-    if ( unlikely((d = rcu_lock_domain_by_id(dom)) == NULL) )
-    {
-        gdprintk(XENLOG_INFO, "Bad domid %d.\n", dom);
-        op.status = GNTST_bad_domain;
-        goto out;
+    else {
+        if ( unlikely((d = rcu_lock_domain_by_id(dom)) == NULL) )
+        {
+            gdprintk(XENLOG_INFO, "Bad domid %d.\n", dom);
+            op.status = GNTST_bad_domain;
+            goto out;
+        }
+        if ( unlikely(!IS_PRIV_FOR(current->domain, d)) ) {
+            op.status = GNTST_permission_denied;
+            goto setup_unlock_out2;
+        }
     }
 
     if ( xsm_grant_setup(current->domain, d) )
@@ -880,6 +880,7 @@
  setup_unlock_out:
     spin_unlock(&d->grant_table->lock);
 
+ setup_unlock_out2:
     rcu_unlock_domain(d);
 
  out:
@@ -910,27 +911,26 @@
     dom = op.dom;
     if ( dom == DOMID_SELF )
     {
-        dom = current->domain->domain_id;
+        d = current->domain;
     }
-    else if ( unlikely(!IS_PRIV(current->domain)) )
-    {
-        op.status = GNTST_permission_denied;
-        goto query_out;
-    }
-
-    if ( unlikely((d = rcu_lock_domain_by_id(dom)) == NULL) )
-    {
-        gdprintk(XENLOG_INFO, "Bad domid %d.\n", dom);
-        op.status = GNTST_bad_domain;
-        goto query_out;
+    else {
+        if ( unlikely((d = rcu_lock_domain_by_id(dom)) == NULL) )
+        {
+            gdprintk(XENLOG_INFO, "Bad domid %d.\n", dom);
+            op.status = GNTST_bad_domain;
+            goto query_out;
+        }
+        if ( unlikely(!IS_PRIV_FOR(current->domain, d)) ) {
+            op.status = GNTST_permission_denied;
+            goto query_out_unlock;
+        }
     }
 
     rc = xsm_grant_query_size(current->domain, d);
     if ( rc )
     {
-        rcu_unlock_domain(d);
         op.status = GNTST_permission_denied;
-        goto query_out;
+        goto query_out_unlock;
     }
 
     spin_lock(&d->grant_table->lock);
@@ -941,6 +941,8 @@
 
     spin_unlock(&d->grant_table->lock);
 
+ 
+ query_out_unlock:
     rcu_unlock_domain(d);
 
  query_out:
--- a/xen/common/memory.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/common/memory.c	Wed Jan 23 11:36:15 2008 +0000
@@ -232,12 +232,17 @@
         return -EFAULT;
 
     if ( op.domid == DOMID_SELF )
-        op.domid = current->domain->domain_id;
-    else if ( !IS_PRIV(current->domain) )
-        return -EPERM;
+        d = current->domain;
+    else {
+        d = rcu_lock_domain_by_id(op.domid);
+        if ( d == NULL )
+            return -ESRCH;
+        if ( !IS_PRIV_FOR(current->domain, d) ) {
+            rcu_unlock_domain(d);
+            return -EPERM;
+        }
+    }
 
-    if ( (d = rcu_lock_domain_by_id(op.domid)) == NULL )
-        return -ESRCH;
 
     if ( !paging_mode_translate(d) )
     {
@@ -535,9 +540,15 @@
 
         if ( likely(reservation.domid == DOMID_SELF) )
             d = current->domain;
-        else if ( !IS_PRIV(current->domain) ||
-                  ((d = rcu_lock_domain_by_id(reservation.domid)) == NULL) )
-            return start_extent;
+        else {
+            d = rcu_lock_domain_by_id(reservation.domid);
+            if ( d == NULL)
+                return start_extent;
+            if ( !IS_PRIV_FOR(current->domain, d) ) {
+                rcu_unlock_domain(d);
+                return start_extent;
+            }
+        }
         args.domain = d;
 
         rc = xsm_memory_adjust_reservation(current->domain, d);
@@ -589,10 +600,15 @@
 
         if ( likely(domid == DOMID_SELF) )
             d = current->domain;
-        else if ( !IS_PRIV(current->domain) )
-            return -EPERM;
-        else if ( (d = rcu_lock_domain_by_id(domid)) == NULL )
-            return -ESRCH;
+        else {
+            d = rcu_lock_domain_by_id(domid);
+            if ( d == NULL )
+                return -ESRCH;
+            if ( !IS_PRIV_FOR(current->domain, d) ) {
+                rcu_unlock_domain(d);
+                return -EPERM;
+            }
+        }
 
         rc = xsm_memory_stat_reservation(current->domain, d);
         if ( rc )
--- a/xen/common/schedule.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/common/schedule.c	Wed Jan 23 11:36:15 2008 +0000
@@ -461,9 +461,6 @@
         struct domain *d;
         struct sched_remote_shutdown sched_remote_shutdown;
 
-        if ( !IS_PRIV(current->domain) )
-            return -EPERM;
-
         ret = -EFAULT;
         if ( copy_from_guest(&sched_remote_shutdown, arg, 1) )
             break;
@@ -472,6 +469,12 @@
         d = rcu_lock_domain_by_id(sched_remote_shutdown.domain_id);
         if ( d == NULL )
             break;
+
+        if ( !IS_PRIV_FOR(current->domain, d) )
+        {
+            rcu_unlock_domain(d);
+            return -EPERM;
+        }
 
         ret = xsm_schedop_shutdown(current->domain, d);
         if ( ret )
--- a/xen/include/public/domctl.h	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/include/public/domctl.h	Wed Jan 23 11:36:15 2008 +0000
@@ -554,6 +554,17 @@
 typedef struct xen_domctl_set_opt_feature xen_domctl_set_opt_feature_t;
 DEFINE_XEN_GUEST_HANDLE(xen_domctl_set_opt_feature_t);
 
+/*
+ * Set the target domain for a domain
+ */
+#define XEN_DOMCTL_set_target    46
+struct xen_domctl_set_target {
+    domid_t target;
+};
+typedef struct xen_domctl_set_target xen_domctl_set_target_t;
+DEFINE_XEN_GUEST_HANDLE(xen_domctl_set_target_t);
+
+
 struct xen_domctl {
     uint32_t cmd;
     uint32_t interface_version; /* XEN_DOMCTL_INTERFACE_VERSION */
@@ -590,6 +601,7 @@
         struct xen_domctl_pin_mem_cacheattr pin_mem_cacheattr;
         struct xen_domctl_ext_vcpucontext   ext_vcpucontext;
         struct xen_domctl_set_opt_feature   set_opt_feature;
+        struct xen_domctl_set_target        set_target;
         uint8_t                             pad[128];
     } u;
 };
--- a/xen/include/xen/sched.h	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/include/xen/sched.h	Wed Jan 23 11:36:15 2008 +0000
@@ -187,6 +187,8 @@
     bool_t           is_hvm;
     /* Is this guest fully privileged (aka dom0)? */
     bool_t           is_privileged;
+    /* Which guest this guest has privileges on */
+    struct domain   *target;
     /* Is this guest being debugged by dom0? */
     bool_t           debugger_attached;
     /* Are any VCPUs polling event channels (SCHEDOP_poll)? */
@@ -493,6 +495,7 @@
 }
 
 #define IS_PRIV(_d) ((_d)->is_privileged)
+#define IS_PRIV_FOR(_d, _t) (IS_PRIV(_d) || ((_d)->target && (_d)->target == (_t)))
 
 #ifndef IS_COMPAT
 #define IS_COMPAT(d) 0
--- a/xen/xsm/acm/acm_simple_type_enforcement_hooks.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/xsm/acm/acm_simple_type_enforcement_hooks.c	Wed Jan 23 11:36:15 2008 +0000
@@ -817,17 +817,19 @@
         return ACM_ACCESS_PERMITTED;
     }
     atomic_inc(&ste_bin_pol.gt_eval_count);
+    subj = current->domain;
+    obj = rcu_lock_domain_by_id(id);
+
     /* a) check authorization (eventually use specific capabilities) */
-    if ( !IS_PRIV(current->domain) )
+    if ( obj && !IS_PRIV_FOR(current->domain, obj) )
     {
         printk("%s: Grant table management authorization denied ERROR!\n",
                __func__);
+        rcu_unlock_domain(obj);
         return ACM_ACCESS_DENIED;
     }
+
     /* b) check types */
-    subj = current->domain;
-    obj = rcu_lock_domain_by_id(id);
-
     if ( share_common_type(subj, obj) )
     {
         cache_result(subj, obj);

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

* [PATCH] New XS_SET_TARGET
@ 2008-01-23 12:06 Samuel Thibault
  2008-01-23 11:55 ` [PATCH] New XEN_DOMCTL_set_target and IS_PRIV_FOR Samuel Thibault
  2008-01-23 14:29 ` [PATCH] New XS_SET_TARGET John Levon
  0 siblings, 2 replies; 8+ messages in thread
From: Samuel Thibault @ 2008-01-23 12:06 UTC (permalink / raw)
  To: xen-devel

New XS_SET_TARGET
Stubdomains (and probably other domain disagregation elements too) need
to be able to tinker with another domain.  This adds XS_SET_TARGET so
that XenStore allows domains to have permissions on files on which the
"target" has permissions.  This also adds xs_set_target, called by the
domain builder when the 'target' option is used in the configuration.

Signed-off-by: Samuel Thibault <samuel.thibault@eu.citrix.com>

---
This patch depends on the previous "New XEN_DOMCTL_set_target and
IS_PRIV_FOR" patch.

diff -u b/tools/python/xen/xend/XendDomainInfo.py b/tools/python/xen/xend/XendDomainInfo.py
--- b/tools/python/xen/xend/XendDomainInfo.py	Wed Jan 23 11:36:15 2008 +0000
+++ b/tools/python/xen/xend/XendDomainInfo.py	Wed Jan 23 11:36:15 2008 +0000
@@ -47,7 +47,7 @@
 from xen.xend.XendDevices import XendDevices
 from xen.xend.XendTask import XendTask
 from xen.xend.xenstore.xstransact import xstransact, complete
-from xen.xend.xenstore.xsutil import GetDomainPath, IntroduceDomain, ResumeDomain
+from xen.xend.xenstore.xsutil import GetDomainPath, IntroduceDomain, SetTarget, ResumeDomain
 from xen.xend.xenstore.xswatch import xswatch
 from xen.xend.XendConstants import *
 from xen.xend.XendAPIConstants import *
@@ -883,6 +883,9 @@
     def storeVm(self, *args):
         return xstransact.Store(self.vmpath, *args)
 
+    def permissionsVm(self, *args):
+        return xstransact.SetPermissions(self.vmpath, *args)
+
 
     def _readVmTxn(self, transaction,  *args):
         paths = map(lambda x: self.vmpath + "/" + x, args)
@@ -905,4 +908,8 @@
         return transaction.store(*paths)
 
+    def permissionsVmTxn(self, transaction,  *args):
+        paths = map(lambda x: self.vmpath + "/" + x, args)
+        return transaction.set_permissions(*paths)
+
     #
     # Function to update xenstore /dom/*
@@ -1694,0 +1702,9 @@
+    def _setTarget(self, target):
+        assert self.domid is not None
+
+        try:
+            SetTarget(self.domid, target)
+            self.storeDom('target', target)
+        except RuntimeError, exn:
+            raise XendError(str(exn))
+
@@ -1756,6 +1772,8 @@
                 self.native_protocol = channel_details['native_protocol'];
 
             self._introduceDomain()
+            if self.info.target():
+                self._setTarget(self.info.target())
 
             self._createDevices()
 
--- a/tools/python/xen/lowlevel/xs/xs.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/python/xen/lowlevel/xs/xs.c	Wed Jan 23 11:36:15 2008 +0000
@@ -619,6 +619,36 @@
     return none(result);
 }
 
+#define xspy_set_target_doc "\n"					\
+        "Tell xenstore that a domain is targetting another one so it\n" \
+        "should let it tinker with it.\n"	                        \
+	" dom    [int]   : domain id\n"					\
+	" target [int]   : domain id of the target\n"			\
+	"\n"								\
+	"Returns None on success.\n"					\
+	"Raises xen.lowlevel.xs.Error on error.\n"			\
+	"\n"
+
+static PyObject *xspy_set_target(XsHandle *self, PyObject *args)
+{
+    uint32_t dom;
+    uint32_t target;
+
+    struct xs_handle *xh = xshandle(self);
+    bool result = 0;
+
+    if (!xh)
+        return NULL;
+    if (!PyArg_ParseTuple(args, "ii", &dom, &target))
+        return NULL;
+
+    Py_BEGIN_ALLOW_THREADS
+    result = xs_set_target(xh, dom, target);
+    Py_END_ALLOW_THREADS
+
+    return none(result);
+}
+
 #define xspy_resume_domain_doc "\n"                                \
 	"Tell xenstore to clear its shutdown flag for a domain.\n" \
 	"This ensures that a subsequent shutdown will fire the\n"  \
@@ -817,6 +847,7 @@
     XSPY_METH(transaction_start, METH_NOARGS),
     XSPY_METH(transaction_end,   METH_VARARGS | METH_KEYWORDS),
     XSPY_METH(introduce_domain,  METH_VARARGS),
+    XSPY_METH(set_target,        METH_VARARGS),
     XSPY_METH(resume_domain,     METH_VARARGS),
     XSPY_METH(release_domain,    METH_VARARGS),
     XSPY_METH(close,             METH_NOARGS),
--- a/tools/python/xen/xend/image.py	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/python/xen/xend/image.py	Wed Jan 23 11:36:15 2008 +0000
@@ -222,6 +222,7 @@
             vncopts = ""
             if passwd:
                 self.vm.storeVm("vncpasswd", passwd)
+                self.vm.permissionsVm("vncpasswd", { 'dom': self.vm.getDomid(), 'read': True } )
                 vncopts = vncopts + ",password"
                 log.debug("Stored a VNC password for vfb access")
             else:
@@ -280,6 +281,9 @@
             env['XAUTHORITY'] = self.xauthority
         if self.vncconsole:
             args = args + ([ "-vncviewer" ])
+        xstransact.Mkdir("/local/domain/0/device-model/%i" % self.vm.getDomid())
+        xstransact.SetPermissions("/local/domain/0/device-model/%i" % self.vm.getDomid(),
+                        { 'dom': self.vm.getDomid(), 'read': True, 'write': True })
         log.info("spawning device models: %s %s", self.device_model, args)
         # keep track of pid and spawned options to kill it later
         self.pid = os.spawnve(os.P_NOWAIT, self.device_model, args, env)
@@ -422,7 +426,9 @@
         self.vm.storeVm(("image/dmargs", " ".join(self.dmargs)),
                         ("image/device-model", self.device_model),
                         ("image/display", self.display))
+        self.vm.permissionsVm("image/dmargs", { 'dom': self.vm.getDomid(), 'read': True } )
         self.vm.storeVm(("rtc/timeoffset", rtc_timeoffset))
+        self.vm.permissionsVm("rtc/timeoffset", { 'dom': self.vm.getDomid(), 'read': True } )
 
         self.apic = int(vmConfig['platform'].get('apic', 0))
         self.acpi = int(vmConfig['platform'].get('acpi', 0))
only in patch2:
--- a/tools/python/xen/xend/xenstore/xsutil.py	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/python/xen/xend/xenstore/xsutil.py	Wed Jan 23 11:36:15 2008 +0000
@@ -22,6 +22,9 @@
 def IntroduceDomain(domid, page, port):
     return xshandle().introduce_domain(domid, page, port)
 
+def SetTarget(domid, target):
+    return xshandle().set_target(domid, target)
+
 def GetDomainPath(domid):
     return xshandle().get_domain_path(domid)
 
--- a/tools/xenstore/xenstored_core.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/xenstore/xenstored_core.c	Wed Jan 23 11:36:15 2008 +0000
@@ -119,6 +119,7 @@
 	case XS_ERROR: return "ERROR";
 	case XS_IS_DOMAIN_INTRODUCED: return "XS_IS_DOMAIN_INTRODUCED";
 	case XS_RESUME: return "RESUME";
+	case XS_SET_TARGET: return "SET_TARGET";
 	default:
 		return "**UNKNOWN**";
 	}
@@ -283,6 +284,8 @@
 				break;
 		close(conn->fd);
 	}
+        if (conn->target)
+                talloc_unlink(conn, conn->target);
 	list_del(&conn->list);
 	trace_destroy(conn, "connection");
 	return 0;
@@ -472,11 +475,13 @@
 		mask &= ~XS_PERM_WRITE;
 
 	/* Owners and tools get it all... */
-	if (!conn->id || perms[0].id == conn->id)
+	if (!conn->id || perms[0].id == conn->id
+                || (conn->target && perms[0].id == conn->target->id))
 		return (XS_PERM_READ|XS_PERM_WRITE|XS_PERM_OWNER) & mask;
 
 	for (i = 1; i < num; i++)
-		if (perms[i].id == conn->id)
+		if (perms[i].id == conn->id
+                        || (conn->target && perms[i].id == conn->target->id))
 			return perms[i].perms & mask;
 
 	return perms[0].perms & mask;
@@ -1245,6 +1250,10 @@
 		do_resume(conn, onearg(in));
 		break;
 
+	case XS_SET_TARGET:
+		do_set_target(conn, in);
+		break;
+
 	default:
 		eprintf("Client unknown operation %i", in->hdr.msg.type);
 		send_error(conn, ENOSYS);
--- a/tools/xenstore/xenstored_core.h	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/xenstore/xenstored_core.h	Wed Jan 23 11:36:15 2008 +0000
@@ -84,6 +84,9 @@
 	/* The domain I'm associated with, if any. */
 	struct domain *domain;
 
+        /* The target of the domain I'm associated with. */
+        struct connection *target;
+
 	/* My watches. */
 	struct list_head watches;
 
--- a/tools/xenstore/xenstored_domain.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/xenstore/xenstored_domain.c	Wed Jan 23 11:36:15 2008 +0000
@@ -379,6 +379,51 @@
 	domain_conn_reset(domain);
 
 	send_ack(conn, XS_INTRODUCE);
+}
+
+void do_set_target(struct connection *conn, struct buffered_data *in)
+{
+	char *vec[2];
+	unsigned int domid, tdomid;
+        struct domain *domain, *tdomain;
+	if (get_strings(in, vec, ARRAY_SIZE(vec)) < ARRAY_SIZE(vec)) {
+		send_error(conn, EINVAL);
+		return;
+	}
+
+	if (conn->id != 0 || !conn->can_write) {
+		send_error(conn, EACCES);
+		return;
+	}
+
+	domid = atoi(vec[0]);
+	tdomid = atoi(vec[1]);
+
+        domain = find_domain_by_domid(domid);
+	if (!domain) {
+		send_error(conn, ENOENT);
+		return;
+	}
+        if (!domain->conn) {
+		send_error(conn, EINVAL);
+		return;
+	}
+
+        tdomain = find_domain_by_domid(tdomid);
+	if (!tdomain) {
+		send_error(conn, ENOENT);
+		return;
+	}
+
+        if (!tdomain->conn) {
+		send_error(conn, EINVAL);
+		return;
+	}
+
+        talloc_reference(domain->conn, tdomain->conn);
+        domain->conn->target = tdomain->conn;
+
+	send_ack(conn, XS_SET_TARGET);
 }
 
 /* domid */
--- a/tools/xenstore/xenstored_domain.h	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/xenstore/xenstored_domain.h	Wed Jan 23 11:36:15 2008 +0000
@@ -34,6 +34,9 @@
 /* domid */
 void do_resume(struct connection *conn, const char *domid_str);
 
+/* domid, target */
+void do_set_target(struct connection *conn, struct buffered_data *in);
+
 /* domid */
 void do_get_domain_path(struct connection *conn, const char *domid_str);
 
--- a/tools/xenstore/xs.c	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/xenstore/xs.c	Wed Jan 23 11:36:15 2008 +0000
@@ -708,6 +708,25 @@
 				ARRAY_SIZE(iov), NULL));
 }
 
+bool xs_set_target(struct xs_handle *h,
+			 unsigned int domid, unsigned int target)
+{
+	char domid_str[MAX_STRLEN(domid)];
+	char target_str[MAX_STRLEN(target)];
+	struct iovec iov[2];
+
+	snprintf(domid_str, sizeof(domid_str), "%u", domid);
+	snprintf(target_str, sizeof(target_str), "%u", target);
+
+	iov[0].iov_base = domid_str;
+	iov[0].iov_len = strlen(domid_str) + 1;
+	iov[1].iov_base = target_str;
+	iov[1].iov_len = strlen(target_str) + 1;
+
+	return xs_bool(xs_talkv(h, XBT_NULL, XS_SET_TARGET, iov,
+				ARRAY_SIZE(iov), NULL));
+}
+
 static void * single_with_domid(struct xs_handle *h,
 				enum xsd_sockmsg_type type,
 				unsigned int domid)
--- a/tools/xenstore/xs.h	Wed Jan 23 11:21:35 2008 +0000
+++ b/tools/xenstore/xs.h	Wed Jan 23 11:36:15 2008 +0000
@@ -132,6 +132,15 @@
 			 unsigned int domid,
 			 unsigned long mfn,
                          unsigned int eventchn); 
+
+/* Set the target of a domain
+ * This tells the store daemon that a domain is targetting another one, so
+ * it should let it tinker with it.
+ */
+bool xs_set_target(struct xs_handle *h,
+		   unsigned int domid,
+		   unsigned int target);
+
 /* Resume a domain.
  * Clear the shutdown flag for this domain in the store.
  */
--- a/xen/include/public/io/xs_wire.h	Wed Jan 23 11:21:35 2008 +0000
+++ b/xen/include/public/io/xs_wire.h	Wed Jan 23 11:36:15 2008 +0000
@@ -46,7 +46,8 @@
     XS_WATCH_EVENT,
     XS_ERROR,
     XS_IS_DOMAIN_INTRODUCED,
-    XS_RESUME
+    XS_RESUME,
+    XS_SET_TARGET
 };
 
 #define XS_WRITE_NONE "NONE"

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

* Re: [PATCH] New XEN_DOMCTL_set_target and IS_PRIV_FOR
  2008-01-23 11:55 ` [PATCH] New XEN_DOMCTL_set_target and IS_PRIV_FOR Samuel Thibault
@ 2008-01-23 14:28   ` John Levon
  2008-01-23 14:36     ` Samuel Thibault
  0 siblings, 1 reply; 8+ messages in thread
From: John Levon @ 2008-01-23 14:28 UTC (permalink / raw)
  To: Samuel Thibault, xen-devel

On Wed, Jan 23, 2008 at 11:55:29AM +0000, Samuel Thibault wrote:

> New XEN_DOMCTL_set_target

This is missing a change to docs/ChangeLog

regards
john

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

* Re: [PATCH] New XS_SET_TARGET
  2008-01-23 12:06 [PATCH] New XS_SET_TARGET Samuel Thibault
  2008-01-23 11:55 ` [PATCH] New XEN_DOMCTL_set_target and IS_PRIV_FOR Samuel Thibault
@ 2008-01-23 14:29 ` John Levon
  2008-01-23 14:36   ` Keir Fraser
  1 sibling, 1 reply; 8+ messages in thread
From: John Levon @ 2008-01-23 14:29 UTC (permalink / raw)
  To: Samuel Thibault, xen-devel

On Wed, Jan 23, 2008 at 12:06:12PM +0000, Samuel Thibault wrote:

> New XS_SET_TARGET
> Stubdomains (and probably other domain disagregation elements too) need

This is missing a ChangeLog entry too

regards
john

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

* Re: [PATCH] New XEN_DOMCTL_set_target and IS_PRIV_FOR
  2008-01-23 14:28   ` John Levon
@ 2008-01-23 14:36     ` Samuel Thibault
  0 siblings, 0 replies; 8+ messages in thread
From: Samuel Thibault @ 2008-01-23 14:36 UTC (permalink / raw)
  To: John Levon; +Cc: xen-devel

John Levon, le Wed 23 Jan 2008 14:28:19 +0000, a écrit :
> On Wed, Jan 23, 2008 at 11:55:29AM +0000, Samuel Thibault wrote:
> 
> > New XEN_DOMCTL_set_target
> 
> This is missing a change to docs/ChangeLog
> 
> > New XS_SET_TARGET
> > Stubdomains (and probably other domain disagregation elements too) need
> 
> This is missing a ChangeLog entry too

Keir kindly did it for me.

Thanks for the reminder anyway,
Samuel

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

* Re: [PATCH] New XS_SET_TARGET
  2008-01-23 14:29 ` [PATCH] New XS_SET_TARGET John Levon
@ 2008-01-23 14:36   ` Keir Fraser
  2008-01-23 14:42     ` John Levon
  0 siblings, 1 reply; 8+ messages in thread
From: Keir Fraser @ 2008-01-23 14:36 UTC (permalink / raw)
  To: John Levon, Samuel Thibault, xen-devel

I've taken to documenting in a later changeset as that lets me put in a link
to the xenbits web page. I did this already for these two interface changes.

 -- Keir

On 23/1/08 14:29, "John Levon" <levon@movementarian.org> wrote:

> On Wed, Jan 23, 2008 at 12:06:12PM +0000, Samuel Thibault wrote:
> 
>> New XS_SET_TARGET
>> Stubdomains (and probably other domain disagregation elements too) need
> 
> This is missing a ChangeLog entry too
> 
> regards
> john
> 
> _______________________________________________
> Xen-devel mailing list
> Xen-devel@lists.xensource.com
> http://lists.xensource.com/xen-devel

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

* Re: [PATCH] New XS_SET_TARGET
  2008-01-23 14:36   ` Keir Fraser
@ 2008-01-23 14:42     ` John Levon
  2008-01-23 14:46       ` Keir Fraser
  0 siblings, 1 reply; 8+ messages in thread
From: John Levon @ 2008-01-23 14:42 UTC (permalink / raw)
  To: Keir Fraser; +Cc: xen-devel, Samuel Thibault

On Wed, Jan 23, 2008 at 02:36:32PM +0000, Keir Fraser wrote:

> I've taken to documenting in a later changeset as that lets me put in a link
> to the xenbits web page. I did this already for these two interface changes.

OK. So what should people submitting patches do? Put the changelog entry
as part of the email message?

cheers,
john

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

* Re: [PATCH] New XS_SET_TARGET
  2008-01-23 14:42     ` John Levon
@ 2008-01-23 14:46       ` Keir Fraser
  0 siblings, 0 replies; 8+ messages in thread
From: Keir Fraser @ 2008-01-23 14:46 UTC (permalink / raw)
  To: John Levon; +Cc: xen-devel, Samuel Thibault

On 23/1/08 14:42, "John Levon" <levon@movementarian.org> wrote:

> On Wed, Jan 23, 2008 at 02:36:32PM +0000, Keir Fraser wrote:
> 
>> I've taken to documenting in a later changeset as that lets me put in a link
>> to the xenbits web page. I did this already for these two interface changes.
> 
> OK. So what should people submitting patches do? Put the changelog entry
> as part of the email message?

It's helpful to at least point out that a changelog entry is needed. If they
want to provide text that's great, otherwise it's not really hard to
synthesize something appropriate from the patch comment.

 -- Keir

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

end of thread, other threads:[~2008-01-23 14:46 UTC | newest]

Thread overview: 8+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2008-01-23 12:06 [PATCH] New XS_SET_TARGET Samuel Thibault
2008-01-23 11:55 ` [PATCH] New XEN_DOMCTL_set_target and IS_PRIV_FOR Samuel Thibault
2008-01-23 14:28   ` John Levon
2008-01-23 14:36     ` Samuel Thibault
2008-01-23 14:29 ` [PATCH] New XS_SET_TARGET John Levon
2008-01-23 14:36   ` Keir Fraser
2008-01-23 14:42     ` John Levon
2008-01-23 14:46       ` Keir Fraser

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.