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

[Xen-changelog] [xen stable-4.8] x86/HPET: fix race triggering ASSERT(cpu < nr_cpu_ids)



commit 4cdd4cc106433921dd46a471148411cb91150a4a
Author:     David Wang <davidwang@xxxxxxxxxxx>
AuthorDate: Fri May 18 12:09:41 2018 +0200
Commit:     Jan Beulich <jbeulich@xxxxxxxx>
CommitDate: Fri May 18 12:09:41 2018 +0200

    x86/HPET: fix race triggering ASSERT(cpu < nr_cpu_ids)
    
    CPUs may share an in-use channel. Hence clearing of a bit from the
    cpumask (in hpet_broadcast_exit()) as well as setting one (in
    hpet_broadcast_enter()) must not race evaluation of that same cpumask.
    Therefore avoid evaluating the cpumask twice in hpet_detach_channel().
    Otherwise cpumask_empty() may e.g.return false while the subsequent
    cpumask_first() could return nr_cpu_ids, which then triggers the
    assertion in cpumask_of() reached through set_channel_irq_affinity().
    
    Signed-off-by: David Wang <davidwang@xxxxxxxxxxx>
    Reviewed-by: Jan Beulich <jbeulich@xxxxxxxx>
    master commit: 8c02a19230502a9522b097ee15742599091064aa
    master date: 2018-04-23 11:00:07 +0200
---
 xen/arch/x86/hpet.c | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/xen/arch/x86/hpet.c b/xen/arch/x86/hpet.c
index f78054da55..72f5a94ad2 100644
--- a/xen/arch/x86/hpet.c
+++ b/xen/arch/x86/hpet.c
@@ -511,6 +511,8 @@ static void hpet_attach_channel(unsigned int cpu,
 static void hpet_detach_channel(unsigned int cpu,
                                 struct hpet_event_channel *ch)
 {
+    unsigned int next;
+
     spin_lock_irq(&ch->lock);
 
     ASSERT(ch == per_cpu(cpu_bc_channel, cpu));
@@ -519,7 +521,7 @@ static void hpet_detach_channel(unsigned int cpu,
 
     if ( cpu != ch->cpu )
         spin_unlock_irq(&ch->lock);
-    else if ( cpumask_empty(ch->cpumask) )
+    else if ( (next = cpumask_first(ch->cpumask)) >= nr_cpu_ids )
     {
         ch->cpu = -1;
         clear_bit(HPET_EVT_USED_BIT, &ch->flags);
@@ -527,7 +529,7 @@ static void hpet_detach_channel(unsigned int cpu,
     }
     else
     {
-        ch->cpu = cpumask_first(ch->cpumask);
+        ch->cpu = next;
         set_channel_irq_affinity(ch);
         local_irq_enable();
     }
--
generated by git-patchbot for /home/xen/git/xen.git#stable-4.8

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxxx
https://lists.xenproject.org/xen-changelog

 


Rackspace

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