Skip to content

Commit

Permalink
evl/mutex: detect lingering PI/PP boost
Browse files Browse the repository at this point in the history
A thread which owns neither PI mutex claimed by others nor
PP-activated mutex should not be boosted. Add a couple of assertions
revealing that kind of brokenness.

Signed-off-by: Philippe Gerum <rpm@xenomai.org>
  • Loading branch information
pgerum committed Jan 8, 2025
1 parent 07b821d commit 81472b8
Show file tree
Hide file tree
Showing 2 changed files with 33 additions and 0 deletions.
14 changes: 14 additions & 0 deletions kernel/evl/mutex.c
Original file line number Diff line number Diff line change
Expand Up @@ -833,6 +833,20 @@ void __evl_unlock_mutex(struct evl_mutex *mutex)
atomic_set(mutex->fastlock, EVL_NO_HANDLE);

raw_spin_unlock_irqrestore(&mutex->wchan.lock, flags);

/*
* Check for spuriously lingering PI/PP boosts. This check
* happens here and in the rescheduling procedure too in order
* to cover cases which would -wrongly- skip the in-kernel
* unlock path.
*/
if (IS_ENABLED(CONFIG_EVL_DEBUG_CORE)) {
bool bad;
raw_spin_lock_irqsave(&curr->lock, flags);
bad = curr->state & T_BOOST && list_empty(&curr->boosters);
raw_spin_unlock_irqrestore(&curr->lock, flags);
EVL_WARN_ON_ONCE(CORE, bad);
}
}

void evl_unlock_mutex(struct evl_mutex *mutex)
Expand Down
19 changes: 19 additions & 0 deletions kernel/evl/sched/core.c
Original file line number Diff line number Diff line change
Expand Up @@ -988,6 +988,11 @@ void __evl_schedule(void) /* oob or/and hard irqs off (CPU migration-safe) */
*/
EVL_WARN_ON(CORE, curr->info & T_WCHAN);

/*
* Priority protection for mutexes is only available to
* applications. Kernel users stick with the priority
* inheritance protocol (see evl_init_kmutex()).
*/
if (curr->state & T_USER)
evl_commit_monitor_ceiling();

Expand All @@ -997,6 +1002,20 @@ void __evl_schedule(void) /* oob or/and hard irqs off (CPU migration-safe) */
* locking order safe from ABBA deadlocking.
*/
raw_spin_lock(&curr->lock);

/*
* Detect any lingering priority boost which should not be in
* effect anymore. Since this situation is likely to stick,
* warn only once. If that message ever appears, something
* would be really wrong in the PI/PP implementation anyway.
*/
if (IS_ENABLED(CONFIG_EVL_DEBUG_CORE) &&
curr->state & T_BOOST && list_empty(&curr->boosters)) {
raw_spin_unlock(&curr->lock);
EVL_WARN_ON_ONCE(CORE, 1);
raw_spin_lock(&curr->lock);
}

raw_spin_lock(&this_rq->lock);

if (unlikely(!test_resched(this_rq))) {
Expand Down

0 comments on commit 81472b8

Please sign in to comment.