[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-changelog] [xen-4.1-testing] adjust a few RCU domain locking calls
# HG changeset patch # User Jan Beulich <jbeulich@xxxxxxxx> # Date 1349339669 -7200 # Node ID 16e98ef904f97e1a824c1d67a2a78e928dca89cf # Parent 99818c48b1e2107aa8c095ce7696cc3016f80893 adjust a few RCU domain locking calls x86's do_physdev_op() had a case where the locking was entirely superfluous. Its physdev_map_pirq() further had a case where the lock was being obtained too early, needlessly complicating early exit paths. Grant table code had two open coded instances of rcu_lock_target_domain_by_id(), and a third code section could be consolidated by using the newly introduced helper function. The memory hypercall code had two more instances of open coding rcu_lock_target_domain_by_id(), but note that here this is not just cleanup, but also fixes an error return path in memory_exchange() to actually return an error. Signed-off-by: Jan Beulich <jbeulich@xxxxxxxx> Acked-by: Keir Fraser <keir@xxxxxxx> xen-unstable changeset: 25835:c70d70d85306 xen-unstable date: Fri Sep 7 15:58:12 UTC 2012 --- diff -r 99818c48b1e2 -r 16e98ef904f9 xen/arch/x86/physdev.c --- a/xen/arch/x86/physdev.c Thu Oct 04 10:31:45 2012 +0200 +++ b/xen/arch/x86/physdev.c Thu Oct 04 10:34:29 2012 +0200 @@ -89,15 +89,11 @@ static int physdev_hvm_map_pirq( static int physdev_map_pirq(struct physdev_map_pirq *map) { - struct domain *d; + struct domain *d = current->domain; int pirq, irq, ret = 0; struct msi_info _msi; void *map_data = NULL; - ret = rcu_lock_target_domain_by_id(map->domid, &d); - if ( ret ) - return ret; - if ( map->domid == DOMID_SELF && is_hvm_domain(d) ) { /* @@ -105,14 +101,15 @@ static int physdev_map_pirq(struct physd * calls back into itself and deadlocks on hvm_domain.irq_lock. */ if ( !is_hvm_pv_evtchn_domain(d) ) - { - ret = -EINVAL; - goto free_domain; - } - ret = physdev_hvm_map_pirq(d, map); - goto free_domain; + return -EINVAL; + + return physdev_hvm_map_pirq(d, map); } + ret = rcu_lock_target_domain_by_id(map->domid, &d); + if ( ret ) + return ret; + if ( !IS_PRIV_FOR(current->domain, d) ) { ret = -EPERM; @@ -585,10 +582,8 @@ ret_t do_physdev_op(int cmd, XEN_GUEST_H } case PHYSDEVOP_get_free_pirq: { struct physdev_get_free_pirq out; - struct domain *d; + struct domain *d = v->domain; - d = rcu_lock_current_domain(); - ret = -EFAULT; if ( copy_from_guest(&out, arg, 1) != 0 ) break; @@ -605,7 +600,6 @@ ret_t do_physdev_op(int cmd, XEN_GUEST_H ret = copy_to_guest(arg, &out, 1) ? -EFAULT : 0; } - rcu_unlock_domain(d); break; } default: diff -r 99818c48b1e2 -r 16e98ef904f9 xen/common/grant_table.c --- a/xen/common/grant_table.c Thu Oct 04 10:31:45 2012 +0200 +++ b/xen/common/grant_table.c Thu Oct 04 10:34:29 2012 +0200 @@ -24,7 +24,7 @@ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ -#include <xen/config.h> +#include <xen/err.h> #include <xen/iocap.h> #include <xen/lib.h> #include <xen/sched.h> @@ -172,6 +172,30 @@ static int __get_paged_frame(unsigned lo return rc; } +static struct domain *gt_lock_target_domain_by_id(domid_t dom) +{ + struct domain *d; + int rc = GNTST_general_error; + + switch ( rcu_lock_target_domain_by_id(dom, &d) ) + { + case 0: + return d; + + case -ESRCH: + gdprintk(XENLOG_INFO, "Bad domid %d.\n", dom); + rc = GNTST_bad_domain; + break; + + case -EPERM: + rc = GNTST_permission_denied; + break; + } + + ASSERT(rc < 0 && -rc <= MAX_ERRNO); + return ERR_PTR(rc); +} + static inline int __get_maptrack_handle( struct grant_table *t) @@ -1216,7 +1240,6 @@ gnttab_setup_table( struct domain *d; int i; unsigned long gmfn; - domid_t dom; if ( count != 1 ) return -EINVAL; @@ -1236,25 +1259,11 @@ gnttab_setup_table( goto out1; } - dom = op.dom; - if ( dom == DOMID_SELF ) + d = gt_lock_target_domain_by_id(op.dom); + if ( IS_ERR(d) ) { - d = rcu_lock_current_domain(); - } - 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 out1; - } - - if ( unlikely(!IS_PRIV_FOR(current->domain, d)) ) - { - op.status = GNTST_permission_denied; - goto out2; - } + op.status = PTR_ERR(d); + goto out1; } if ( xsm_grant_setup(current->domain, d) ) @@ -1309,7 +1318,6 @@ gnttab_query_size( { struct gnttab_query_size op; struct domain *d; - domid_t dom; int rc; if ( count != 1 ) @@ -1321,25 +1329,11 @@ gnttab_query_size( return -EFAULT; } - dom = op.dom; - if ( dom == DOMID_SELF ) + d = gt_lock_target_domain_by_id(op.dom); + if ( IS_ERR(d) ) { - d = rcu_lock_current_domain(); - } - 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; - } + op.status = PTR_ERR(d); + goto query_out; } rc = xsm_grant_query_size(current->domain, d); @@ -2179,7 +2173,6 @@ gnttab_get_status_frames(XEN_GUEST_HANDL struct grant_table *gt; uint64_t gmfn; int i; - int rc; if ( count != 1 ) return -EINVAL; @@ -2191,15 +2184,10 @@ gnttab_get_status_frames(XEN_GUEST_HANDL return -EFAULT; } - rc = rcu_lock_target_domain_by_id(op.dom, &d); - if ( rc < 0 ) + d = gt_lock_target_domain_by_id(op.dom); + if ( IS_ERR(d) ) { - if ( rc == -ESRCH ) - op.status = GNTST_bad_domain; - else if ( rc == -EPERM ) - op.status = GNTST_permission_denied; - else - op.status = GNTST_general_error; + op.status = PTR_ERR(d); goto out1; } diff -r 99818c48b1e2 -r 16e98ef904f9 xen/common/memory.c --- a/xen/common/memory.c Thu Oct 04 10:31:45 2012 +0200 +++ b/xen/common/memory.c Thu Oct 04 10:34:29 2012 +0200 @@ -310,22 +310,9 @@ static long memory_exchange(XEN_GUEST_HA out_chunk_order = exch.in.extent_order - exch.out.extent_order; } - if ( likely(exch.in.domid == DOMID_SELF) ) - { - d = rcu_lock_current_domain(); - } - else - { - if ( (d = rcu_lock_domain_by_id(exch.in.domid)) == NULL ) - goto fail_early; - - if ( !IS_PRIV_FOR(current->domain, d) ) - { - rcu_unlock_domain(d); - rc = -EPERM; - goto fail_early; - } - } + rc = rcu_lock_target_domain_by_id(exch.in.domid, &d); + if ( rc ) + goto fail_early; memflags |= MEMF_bits(domain_clamp_alloc_bitsize( d, @@ -556,20 +543,8 @@ long do_memory_op(unsigned long cmd, XEN && (reservation.mem_flags & XENMEMF_populate_on_demand) ) args.memflags |= MEMF_populate_on_demand; - if ( likely(reservation.domid == DOMID_SELF) ) - { - d = rcu_lock_current_domain(); - } - else - { - if ( (d = rcu_lock_domain_by_id(reservation.domid)) == NULL ) - return start_extent; - if ( !IS_PRIV_FOR(current->domain, d) ) - { - rcu_unlock_domain(d); - return start_extent; - } - } + if ( unlikely(rcu_lock_target_domain_by_id(reservation.domid, &d)) ) + return start_extent; args.domain = d; rc = xsm_memory_adjust_reservation(current->domain, d); _______________________________________________ Xen-changelog mailing list Xen-changelog@xxxxxxxxxxxxx http://lists.xensource.com/xen-changelog
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |