patch-2.2.17 linux/net/ipv4/tcp.c
Next file: linux/net/ipv4/tcp_input.c
Previous file: linux/net/ipv4/proc.c
Back to the patch index
Back to the overall index
- Lines: 77
- Date:
Mon Sep 4 18:39:29 2000
- Orig file:
v2.2.16/net/ipv4/tcp.c
- Orig date:
Mon Sep 4 18:37:23 2000
diff -u --recursive --new-file v2.2.16/net/ipv4/tcp.c linux/net/ipv4/tcp.c
@@ -697,32 +697,39 @@
}
/*
- * Wait for more memory for a socket
+ * Wait for more memory for a socket.
+ * Special case is err == -ENOMEM, in this case just sleep a bit waiting
+ * for the system to free up some memory.
*/
-static void wait_for_tcp_memory(struct sock * sk)
+static void wait_for_tcp_memory(struct sock * sk, int err)
{
- release_sock(sk);
- if (!tcp_memory_free(sk)) {
+ if (1) {
struct wait_queue wait = { current, NULL };
-
+
sk->socket->flags &= ~SO_NOSPACE;
add_wait_queue(sk->sleep, &wait);
+ release_sock(sk);
for (;;) {
if (signal_pending(current))
break;
current->state = TASK_INTERRUPTIBLE;
- if (tcp_memory_free(sk))
+ if (tcp_memory_free(sk) && !err)
break;
if (sk->shutdown & SEND_SHUTDOWN)
break;
if (sk->err)
break;
- schedule();
+ if (!err)
+ schedule();
+ else {
+ schedule_timeout(net_random()%(HZ/5) + 1);
+ break;
+ }
}
+ lock_sock(sk);
current->state = TASK_RUNNING;
remove_wait_queue(sk->sleep, &wait);
}
- lock_sock(sk);
}
/*
@@ -915,12 +922,12 @@
tmp += copy;
queue_it = 0;
}
- skb = sock_wmalloc(sk, tmp, 0, GFP_KERNEL);
+ skb = sock_wmalloc_err(sk, tmp, 0, GFP_KERNEL, &err);
/* If we didn't get any memory, we need to sleep. */
if (skb == NULL) {
sk->socket->flags |= SO_NOSPACE;
- if (flags&MSG_DONTWAIT) {
+ if ((flags&MSG_DONTWAIT) && !err) {
err = -EAGAIN;
goto do_interrupted;
}
@@ -928,8 +935,11 @@
err = -ERESTARTSYS;
goto do_interrupted;
}
- tcp_push_pending_frames(sk, tp);
- wait_for_tcp_memory(sk);
+
+ /* In OOM that would fail anyways so do not bother. */
+ if (!err)
+ tcp_push_pending_frames(sk, tp);
+ wait_for_tcp_memory(sk, err);
/* If SACK's were formed or PMTU events happened,
* we must find out about it.
FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)