From 77c1090f94d1b0b5186fb13a1b71b47b1343f87f Mon Sep 17 00:00:00 2001 From: Eric Dumazet Date: Tue, 12 Feb 2013 06:16:53 +0000 Subject: net: fix infinite loop in __skb_recv_datagram() Tommi was fuzzing with trinity and reported the following problem : commit 3f518bf745 (datagram: Add offset argument to __skb_recv_datagram) missed that a raw socket receive queue can contain skbs with no payload. We can loop in __skb_recv_datagram() with MSG_PEEK mode, because wait_for_packet() is not prepared to skip these skbs. [ 83.541011] INFO: rcu_sched detected stalls on CPUs/tasks: {} (detected by 0, t=26002 jiffies, g=27673, c=27672, q=75) [ 83.541011] INFO: Stall ended before state dump start [ 108.067010] BUG: soft lockup - CPU#0 stuck for 22s! [trinity-child31:2847] ... [ 108.067010] Call Trace: [ 108.067010] [] __skb_recv_datagram+0x1a3/0x3b0 [ 108.067010] [] skb_recv_datagram+0x2d/0x30 [ 108.067010] [] rawv6_recvmsg+0xad/0x240 [ 108.067010] [] sock_common_recvmsg+0x34/0x50 [ 108.067010] [] sock_recvmsg+0xbc/0xf0 [ 108.067010] [] sys_recvfrom+0xde/0x150 [ 108.067010] [] system_call_fastpath+0x16/0x1b Reported-by: Tommi Rantala Tested-by: Tommi Rantala Signed-off-by: Eric Dumazet Cc: Pavel Emelyanov Acked-by: Pavel Emelyanov Signed-off-by: David S. Miller --- net/core/datagram.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/core/datagram.c b/net/core/datagram.c index 0337e2b7686..368f9c3f9dc 100644 --- a/net/core/datagram.c +++ b/net/core/datagram.c @@ -187,7 +187,7 @@ struct sk_buff *__skb_recv_datagram(struct sock *sk, unsigned int flags, skb_queue_walk(queue, skb) { *peeked = skb->peeked; if (flags & MSG_PEEK) { - if (*off >= skb->len) { + if (*off >= skb->len && skb->len) { *off -= skb->len; continue; } -- cgit v1.2.3