[patch] sleep_on() done with cli(), NetROM, 2.2.2

Ingo Molnar (mingo@chiara.csoma.elte.hu)
Tue, 2 Mar 1999 10:48:30 +0100 (CET)


and theres one place in the NetROM code. My fix only removes the lockup
but i think there is still a race there.

the conceptual problem is this: the code relies on the global IRQ lock to
keep asynchron events from happening. But we must not hold the tasklist
lock inside of the IRQ lock. I can see no good way to make sleep_on*()
'just work' with the old assumptions... I guess that part has to be
rewritten to: add to the runqueue and lose TASK_RUNNING state, _then_
check the condition (atomically) and go sleeping if condition is not yet
ready.

-- mingo

--- linux/net/netrom/af_netrom.c.orig Tue Mar 2 10:36:56 1999
+++ linux/net/netrom/af_netrom.c Tue Mar 2 10:39:16 1999
@@ -722,11 +722,11 @@
* A Connect Ack with Choke or timeout or failed routing will go to closed.
*/
while (sk->state == TCP_SYN_SENT) {
+ sti();
interruptible_sleep_on(sk->sleep);
- if (signal_pending(current)) {
- sti();
+ if (signal_pending(current))
return -ERESTARTSYS;
- }
+ cli();
}

if (sk->state != TCP_ESTABLISHED) {
@@ -769,15 +769,13 @@
do {
cli();
if ((skb = skb_dequeue(&sk->receive_queue)) == NULL) {
- if (flags & O_NONBLOCK) {
- sti();
+ sti();
+ if (flags & O_NONBLOCK)
return -EWOULDBLOCK;
- }
interruptible_sleep_on(sk->sleep);
- if (signal_pending(current)) {
- sti();
+ if (signal_pending(current))
return -ERESTARTSYS;
- }
+ cli();
}
} while (skb == NULL);

-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.rutgers.edu
Please read the FAQ at http://www.tux.org/lkml/