Skip to content

Commit

Permalink
[INET]: Use pskb_trim_unique when trimming paged unique skbs
Browse files Browse the repository at this point in the history
The IPv4/IPv6 datagram output path was using skb_trim to trim paged
packets because they know that the packet has not been cloned yet
(since the packet hasn't been given to anything else in the system).

This broke because skb_trim no longer allows paged packets to be
trimmed.  Paged packets must be given to one of the pskb_trim functions
instead.

This patch adds a new pskb_trim_unique function to cover the IPv4/IPv6
datagram output path scenario and replaces the corresponding skb_trim
calls with it.

Signed-off-by: Herbert Xu <[email protected]>
Signed-off-by: David S. Miller <[email protected]>
  • Loading branch information
herbertx authored and davem330 committed Aug 14, 2006
1 parent dcb7cd9 commit e9fa4f7
Show file tree
Hide file tree
Showing 3 changed files with 18 additions and 3 deletions.
15 changes: 15 additions & 0 deletions include/linux/skbuff.h
Original file line number Diff line number Diff line change
Expand Up @@ -1039,6 +1039,21 @@ static inline int pskb_trim(struct sk_buff *skb, unsigned int len)
return (len < skb->len) ? __pskb_trim(skb, len) : 0;
}

/**
* pskb_trim_unique - remove end from a paged unique (not cloned) buffer
* @skb: buffer to alter
* @len: new length
*
* This is identical to pskb_trim except that the caller knows that
* the skb is not cloned so we should never get an error due to out-
* of-memory.
*/
static inline void pskb_trim_unique(struct sk_buff *skb, unsigned int len)
{
int err = pskb_trim(skb, len);
BUG_ON(err);
}

/**
* skb_orphan - orphan a buffer
* @skb: buffer to orphan
Expand Down
4 changes: 2 additions & 2 deletions net/ipv4/ip_output.c
Original file line number Diff line number Diff line change
Expand Up @@ -947,7 +947,7 @@ int ip_append_data(struct sock *sk,
skb_prev->csum = csum_sub(skb_prev->csum,
skb->csum);
data += fraggap;
skb_trim(skb_prev, maxfraglen);
pskb_trim_unique(skb_prev, maxfraglen);
}

copy = datalen - transhdrlen - fraggap;
Expand Down Expand Up @@ -1142,7 +1142,7 @@ ssize_t ip_append_page(struct sock *sk, struct page *page,
data, fraggap, 0);
skb_prev->csum = csum_sub(skb_prev->csum,
skb->csum);
skb_trim(skb_prev, maxfraglen);
pskb_trim_unique(skb_prev, maxfraglen);
}

/*
Expand Down
2 changes: 1 addition & 1 deletion net/ipv6/ip6_output.c
Original file line number Diff line number Diff line change
Expand Up @@ -1095,7 +1095,7 @@ int ip6_append_data(struct sock *sk, int getfrag(void *from, char *to,
skb_prev->csum = csum_sub(skb_prev->csum,
skb->csum);
data += fraggap;
skb_trim(skb_prev, maxfraglen);
pskb_trim_unique(skb_prev, maxfraglen);
}
copy = datalen - transhdrlen - fraggap;
if (copy < 0) {
Expand Down

0 comments on commit e9fa4f7

Please sign in to comment.