Module: xenomai-3
Branch: master
Commit: 9a8be3bd8fdaca6654a7db16c886af7d508f5477
URL:    
http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=9a8be3bd8fdaca6654a7db16c886af7d508f5477

Author: Gilles Chanteperdrix <gilles.chanteperd...@xenomai.org>
Date:   Sun Oct 11 19:10:23 2015 +0200

cobalt/sched: bypass scheduler lock in irq

When preempting a relaxed thread, in case the thread is in the middle of
a call to xnthread_relax().

---

 kernel/cobalt/sched.c |   22 +++++++++++++++++++---
 1 file changed, 19 insertions(+), 3 deletions(-)

diff --git a/kernel/cobalt/sched.c b/kernel/cobalt/sched.c
index 56014e0..792bb80 100644
--- a/kernel/cobalt/sched.c
+++ b/kernel/cobalt/sched.c
@@ -322,7 +322,8 @@ struct xnsched *xnsched_finish_unlocked_switch(struct 
xnsched *sched)
 
 void xnsched_lock(void)
 {
-       struct xnthread *curr = xnthread_current();
+       struct xnsched *sched = xnsched_current();
+       struct xnthread *curr = sched->curr;
 
        /*
         * CAUTION: The fast xnthread_current() accessor carries the
@@ -333,8 +334,16 @@ void xnsched_lock(void)
         * Either way, we don't need to grab the super lock.
         */
        if (unlikely(curr == NULL || xnthread_test_state(curr, XNRELAX))) {
+               /*
+                * In IRQ: scheduler already locked, and we may have
+                * interrupted xnthread_relax() where the BUG_ON condition is
+                * temporarily false.
+                */
+               if (sched->lflags & XNINIRQ)
+                       return;
+
                irqoff_only();
-               curr = &xnsched_current()->rootcb;
+               curr = &sched->rootcb;
                XENO_BUG_ON(COBALT, xnsched_current()->curr != curr);
        }
 
@@ -344,9 +353,16 @@ EXPORT_SYMBOL_GPL(xnsched_lock);
 
 void xnsched_unlock(void)
 {
-       struct xnthread *curr = xnthread_current();
+       struct xnsched *sched = xnsched_current();
+       struct xnthread *curr = sched->curr;
 
        if (unlikely(curr == NULL || xnthread_test_state(curr, XNRELAX))) {
+               /*
+                * In IRQ
+                */
+               if (sched->lflags & XNINIRQ)
+                       return;
+
                irqoff_only();
                curr = &xnsched_current()->rootcb;
        }


_______________________________________________
Xenomai-git mailing list
Xenomai-git@xenomai.org
http://xenomai.org/mailman/listinfo/xenomai-git

Reply via email to