projects
/
firefly-linux-kernel-4.4.55.git
/ blobdiff
commit
grep
author
committer
pickaxe
?
search:
re
summary
|
shortlog
|
log
|
commit
|
commitdiff
|
tree
raw
|
inline
| side by side
Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/linville/wirel...
[firefly-linux-kernel-4.4.55.git]
/
net
/
ipv4
/
tcp.c
diff --git
a/net/ipv4/tcp.c
b/net/ipv4/tcp.c
index 1ca253635f7acdda23624c28ae1ead4645bd0dd5..2aa69c8ae60c1990c76e69fe5aef46b990b6da6e 100644
(file)
--- a/
net/ipv4/tcp.c
+++ b/
net/ipv4/tcp.c
@@
-1428,12
+1428,12
@@
static void tcp_service_net_dma(struct sock *sk, bool wait)
}
#endif
}
#endif
-static
inline
struct sk_buff *tcp_recv_skb(struct sock *sk, u32 seq, u32 *off)
+static struct sk_buff *tcp_recv_skb(struct sock *sk, u32 seq, u32 *off)
{
struct sk_buff *skb;
u32 offset;
{
struct sk_buff *skb;
u32 offset;
-
skb_queue_walk(&sk->sk_receive_queue, skb
) {
+
while ((skb = skb_peek(&sk->sk_receive_queue)) != NULL
) {
offset = seq - TCP_SKB_CB(skb)->seq;
if (tcp_hdr(skb)->syn)
offset--;
offset = seq - TCP_SKB_CB(skb)->seq;
if (tcp_hdr(skb)->syn)
offset--;
@@
-1441,6
+1441,11
@@
static inline struct sk_buff *tcp_recv_skb(struct sock *sk, u32 seq, u32 *off)
*off = offset;
return skb;
}
*off = offset;
return skb;
}
+ /* This looks weird, but this can happen if TCP collapsing
+ * splitted a fat GRO packet, while we released socket lock
+ * in skb_splice_bits()
+ */
+ sk_eat_skb(sk, skb, false);
}
return NULL;
}
}
return NULL;
}
@@
-1482,7
+1487,7
@@
int tcp_read_sock(struct sock *sk, read_descriptor_t *desc,
break;
}
used = recv_actor(desc, skb, offset, len);
break;
}
used = recv_actor(desc, skb, offset, len);
- if (used < 0) {
+ if (used <
=
0) {
if (!copied)
copied = used;
break;
if (!copied)
copied = used;
break;
@@
-1520,8
+1525,10
@@
int tcp_read_sock(struct sock *sk, read_descriptor_t *desc,
tcp_rcv_space_adjust(sk);
/* Clean up data we have read: This will do ACK frames. */
tcp_rcv_space_adjust(sk);
/* Clean up data we have read: This will do ACK frames. */
- if (copied > 0)
+ if (copied > 0) {
+ tcp_recv_skb(sk, seq, &offset);
tcp_cleanup_rbuf(sk, copied);
tcp_cleanup_rbuf(sk, copied);
+ }
return copied;
}
EXPORT_SYMBOL(tcp_read_sock);
return copied;
}
EXPORT_SYMBOL(tcp_read_sock);