forked from Minki/linux
packet: round up linear to header len
Link layer protocols may unconditionally pull headers, as Ethernet does in eth_type_trans. Ensure that the entire link layer header always lies in the skb linear segment. tpacket_snd has such a check. Extend this to packet_snd. Variable length link layer headers complicate the computation somewhat. Here skb->len may be smaller than dev->hard_header_len. Round up the linear length to be at least as long as the smallest of the two. Reported-by: Dmitry Vyukov <dvyukov@google.com> Signed-off-by: Willem de Bruijn <willemb@google.com> Acked-by: Eric Dumazet <edumazet@google.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
217e6fa24c
commit
57031eb794
@ -2755,7 +2755,7 @@ static int packet_snd(struct socket *sock, struct msghdr *msg, size_t len)
|
||||
struct virtio_net_hdr vnet_hdr = { 0 };
|
||||
int offset = 0;
|
||||
struct packet_sock *po = pkt_sk(sk);
|
||||
int hlen, tlen;
|
||||
int hlen, tlen, linear;
|
||||
int extra_len = 0;
|
||||
|
||||
/*
|
||||
@ -2816,8 +2816,9 @@ static int packet_snd(struct socket *sock, struct msghdr *msg, size_t len)
|
||||
err = -ENOBUFS;
|
||||
hlen = LL_RESERVED_SPACE(dev);
|
||||
tlen = dev->needed_tailroom;
|
||||
skb = packet_alloc_skb(sk, hlen + tlen, hlen, len,
|
||||
__virtio16_to_cpu(vio_le(), vnet_hdr.hdr_len),
|
||||
linear = __virtio16_to_cpu(vio_le(), vnet_hdr.hdr_len);
|
||||
linear = max(linear, min_t(int, len, dev->hard_header_len));
|
||||
skb = packet_alloc_skb(sk, hlen + tlen, hlen, len, linear,
|
||||
msg->msg_flags & MSG_DONTWAIT, &err);
|
||||
if (skb == NULL)
|
||||
goto out_unlock;
|
||||
|
Loading…
Reference in New Issue
Block a user