Skip to content

Commit

Permalink
net: relax rcvbuf limits
Browse files Browse the repository at this point in the history
skb->truesize might be big even for a small packet.

Its even bigger after commit 87fb4b7 (net: more accurate skb
truesize) and big MTU.

We should allow queueing at least one packet per receiver, even with a
low RCVBUF setting.

Reported-by: Michal Simek <[email protected]>
Signed-off-by: Eric Dumazet <[email protected]>
Signed-off-by: David S. Miller <[email protected]>
  • Loading branch information
Eric Dumazet authored and davem330 committed Dec 23, 2011
1 parent a0a129f commit 0fd7bac
Show file tree
Hide file tree
Showing 3 changed files with 6 additions and 10 deletions.
4 changes: 3 additions & 1 deletion include/net/sock.h
Original file line number Diff line number Diff line change
Expand Up @@ -637,12 +637,14 @@ static inline void __sk_add_backlog(struct sock *sk, struct sk_buff *skb)

/*
* Take into account size of receive queue and backlog queue
* Do not take into account this skb truesize,
* to allow even a single big packet to come.
*/
static inline bool sk_rcvqueues_full(const struct sock *sk, const struct sk_buff *skb)
{
unsigned int qsize = sk->sk_backlog.len + atomic_read(&sk->sk_rmem_alloc);

return qsize + skb->truesize > sk->sk_rcvbuf;
return qsize > sk->sk_rcvbuf;
}

/* The per-socket spinlock must be held here. */
Expand Down
6 changes: 1 addition & 5 deletions net/core/sock.c
Original file line number Diff line number Diff line change
Expand Up @@ -288,11 +288,7 @@ int sock_queue_rcv_skb(struct sock *sk, struct sk_buff *skb)
unsigned long flags;
struct sk_buff_head *list = &sk->sk_receive_queue;

/* Cast sk->rcvbuf to unsigned... It's pointless, but reduces
number of warnings when compiling with -W --ANK
*/
if (atomic_read(&sk->sk_rmem_alloc) + skb->truesize >=
(unsigned)sk->sk_rcvbuf) {
if (atomic_read(&sk->sk_rmem_alloc) >= sk->sk_rcvbuf) {
atomic_inc(&sk->sk_drops);
trace_sock_rcvqueue_full(sk, skb);
return -ENOMEM;
Expand Down
6 changes: 2 additions & 4 deletions net/packet/af_packet.c
Original file line number Diff line number Diff line change
Expand Up @@ -1630,8 +1630,7 @@ static int packet_rcv(struct sk_buff *skb, struct net_device *dev,
if (snaplen > res)
snaplen = res;

if (atomic_read(&sk->sk_rmem_alloc) + skb->truesize >=
(unsigned)sk->sk_rcvbuf)
if (atomic_read(&sk->sk_rmem_alloc) >= sk->sk_rcvbuf)
goto drop_n_acct;

if (skb_shared(skb)) {
Expand Down Expand Up @@ -1762,8 +1761,7 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev,
if (po->tp_version <= TPACKET_V2) {
if (macoff + snaplen > po->rx_ring.frame_size) {
if (po->copy_thresh &&
atomic_read(&sk->sk_rmem_alloc) + skb->truesize
< (unsigned)sk->sk_rcvbuf) {
atomic_read(&sk->sk_rmem_alloc) < sk->sk_rcvbuf) {
if (skb_shared(skb)) {
copy_skb = skb_clone(skb, GFP_ATOMIC);
} else {
Expand Down

0 comments on commit 0fd7bac

Please sign in to comment.