Reputation: 2899
I'm porting legacy code from Linux 3.14 to 4.1. There are dozens of calls to sleep_on()
functions that I need to convert to calls to wait_event()
functions:
wait_event(wq, condition);
wait_event_interruptible(wq, condition);
wait_event_timeout(wq, condition, timeout);
wait_event_interruptible_timeout(wq, condition, timeout);
The sleep_on()
functions were removed in kernel 3.15 because they cause race conditions.
My problem is it will take a lot of time to understand the tricky code that uses the sleep_on()
functions and make proper changes, test, etc. and I need to release at least a prototype as soon as possible. And consider I'm a Linux device drivers newbie.
Do you know a pattern I could use to replace calls to sleep_on()
functions by calls to wait_event()
functions? For example, if I just replace sleep_on(&wait_queue)
by wait_event(wait_queue, false)
, what will be the impact compared to the legacy code? Will the result be as bad as the legacy code (can have race conditions), or much worse?
Thanks in advance for your advice.
Upvotes: 1
Views: 1058
Reputation: 65928
You may define sleep_on
function as it has been defined in pre-3.15 kernels. Like this:
void
sleep_on(wait_queue_head_t *q)
{
unsigned long flags;
wait_queue_t wait;
init_waitqueue_entry(&wait, current);
__set_current_state(TASK_UNINTERRUPTIBLE);
spin_lock_irqsave(&q->lock, flags);
__add_wait_queue(q, &wait);
spin_unlock(&q->lock);
schedule();
spin_lock_irq(&q->lock);
__remove_wait_queue(q, &wait);
spin_unlock_irqrestore(&q->lock, flags);
}
(originated from the code of sleep_on_common
but with timeout things removed.)
For those who want to see the original code on kernel.org, see sleep_on_common()
with commit 32d01dc7be4e725ab85ce1d74e8f4adc02ad68dd
in April 2014 (a few days before the function was removed).
As for wait_event()
and friends, using constant condition is wrong:
Upvotes: 2