mirror of
https://github.com/torvalds/linux.git
synced 2026-11-07 06:17:02 +01:00
bpf: Don't leave a stale MAC header in bpf_lwt_push_ip_encap()
With BPF_LWT_ENCAP_IP, bpf_lwt_push_encap() pushes a new IP header. The new
header overwrites the MAC header of a received skb. But skb->mac_header
continues to point to the same bytes. Code that reads the MAC header after
the push, for example netfilter, gets bytes of the new header.
before the push | MAC header | old IP | payload
^ mac_header ^ network_header
today | new header | old IP | payload
network_header ^ ^ mac_header
this patch, lwt_in | MAC header | new header | old IP | payload
^ mac_header ^ network_header
this patch, lwt_xmit | new header | old IP | payload
network_header ^ mac_header is not set
For lwt_in, move the MAC header in front of the new header before the
memcpy(), as __seg6_do_srh_encap() does. skb_cow_head() already reserves
len + skb->mac_len bytes.
For lwt_xmit, the output path makes a new MAC header. Thus mark
skb->mac_header as not set. This is the state of a locally generated skb.
Fixes: 52f278774e ("bpf: implement BPF_LWT_ENCAP_IP mode in bpf_lwt_push_encap")
Signed-off-by: Alexei Starovoitov <ast@kernel.org>
Link: https://patch.msgid.link/20261101190535.1454146-22-alexei.starovoitov@gmail.com
This commit is contained in:
parent
0fcb3f11a9
commit
701ffd202b
|
|
@ -649,6 +649,14 @@ int bpf_lwt_push_ip_encap(struct sk_buff *skb, void *hdr, u32 len, bool ingress)
|
|||
if (ingress)
|
||||
skb_postpush_rcsum(skb, iph, len);
|
||||
skb_reset_network_header(skb);
|
||||
/*
|
||||
* The new header goes over the MAC header. On ingress move it first.
|
||||
* On egress the packet gets a new one, so forget the old one.
|
||||
*/
|
||||
if (ingress)
|
||||
skb_mac_header_rebuild(skb);
|
||||
else
|
||||
skb_unset_mac_header(skb);
|
||||
if (is_udp_tunnel) {
|
||||
size_t iph_sz = ipv4 ? iph->ihl * 4 : sizeof(struct ipv6hdr);
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user