[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-changelog] [linux-2.6.18-xen] xen/evtchn: Clean up round-robin evtchn scan.
# HG changeset patch # User Keir Fraser <keir.fraser@xxxxxxxxxx> # Date 1264751868 0 # Node ID c88a02a22a057a632e6c21442e42e56e07904988 # Parent 91224343eeee460c9aafdaadc1bdedab54e92256 xen/evtchn: Clean up round-robin evtchn scan. Also fixes a couple of boundary cases. Signed-off-by: Keir Fraser <keir.fraser@xxxxxxxxxx> --- drivers/xen/core/evtchn.c | 45 +++++++++++++++++++++------------------------ 1 files changed, 21 insertions(+), 24 deletions(-) diff -r 91224343eeee -r c88a02a22a05 drivers/xen/core/evtchn.c --- a/drivers/xen/core/evtchn.c Thu Jan 21 15:05:02 2010 +0000 +++ b/drivers/xen/core/evtchn.c Fri Jan 29 07:57:48 2010 +0000 @@ -229,9 +229,9 @@ void force_evtchn_callback(void) /* Not a GPL symbol: used in ubiquitous macros, so too restrictive. */ EXPORT_SYMBOL(force_evtchn_callback); -static DEFINE_PER_CPU(unsigned int, upcall_count) = { 0 }; -static DEFINE_PER_CPU(unsigned int, last_processed_l1i) = { BITS_PER_LONG - 1 }; -static DEFINE_PER_CPU(unsigned int, last_processed_l2i) = { BITS_PER_LONG - 1 }; +static DEFINE_PER_CPU(unsigned int, upcall_count); +static DEFINE_PER_CPU(unsigned int, current_l1i); +static DEFINE_PER_CPU(unsigned int, current_l2i); /* NB. Interrupts are disabled on entry. */ asmlinkage void evtchn_do_upcall(struct pt_regs *regs) @@ -261,32 +261,23 @@ asmlinkage void evtchn_do_upcall(struct #endif l1 = xchg(&vcpu_info->evtchn_pending_sel, 0); - l1i = per_cpu(last_processed_l1i, cpu); - l2i = per_cpu(last_processed_l2i, cpu); + l1i = per_cpu(current_l1i, cpu); + l2i = per_cpu(current_l2i, cpu); while (l1 != 0) { - - l1i = (l1i + 1) % BITS_PER_LONG; masked_l1 = l1 & ((~0UL) << l1i); - - if (masked_l1 == 0) { /* if we masked out all events, wrap around to the beginning */ - l1i = BITS_PER_LONG - 1; - l2i = BITS_PER_LONG - 1; + /* If we masked out all events, wrap to beginning. */ + if (masked_l1 == 0) { + l1i = l2i = 0; continue; } l1i = __ffs(masked_l1); do { l2 = active_evtchns(cpu, s, l1i); - - l2i = (l2i + 1) % BITS_PER_LONG; masked_l2 = l2 & ((~0UL) << l2i); - - if (masked_l2 == 0) { /* if we masked out all events, move on */ - l2i = BITS_PER_LONG - 1; + if (masked_l2 == 0) break; - } - l2i = __ffs(masked_l2); /* process port */ @@ -296,16 +287,22 @@ asmlinkage void evtchn_do_upcall(struct else evtchn_device_upcall(port); - /* if this is the final port processed, we'll pick up here+1 next time */ - per_cpu(last_processed_l1i, cpu) = l1i; - per_cpu(last_processed_l2i, cpu) = l2i; - - } while (l2i != BITS_PER_LONG - 1); + l2i = (l2i + 1) % BITS_PER_LONG; + + /* Next caller starts at last processed + 1 */ + per_cpu(current_l1i, cpu) = + l2i ? l1i : (l1i + 1) % BITS_PER_LONG; + per_cpu(current_l2i, cpu) = l2i; + + } while (l2i != 0); l2 = active_evtchns(cpu, s, l1i); - if (l2 == 0) /* we handled all ports, so we can clear the selector bit */ + /* If we handled all ports, clear the selector bit. */ + if (l2 == 0) l1 &= ~(1UL << l1i); + l1i = (l1i + 1) % BITS_PER_LONG; + l2i = 0; } /* If there were nested callbacks then we have more to do. */ _______________________________________________ Xen-changelog mailing list Xen-changelog@xxxxxxxxxxxxxxxxxxx http://lists.xensource.com/xen-changelog
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |