diff options
-rw-r--r-- | src/device.c | 5 | ||||
-rw-r--r-- | src/queueing.h | 1 | ||||
-rw-r--r-- | src/send.c | 7 | ||||
-rwxr-xr-x | src/tests/netns.sh | 13 | ||||
-rw-r--r-- | src/tests/qemu/kernel.config | 3 |
5 files changed, 26 insertions, 3 deletions
diff --git a/src/device.c b/src/device.c index 1614d61..d64653d 100644 --- a/src/device.c +++ b/src/device.c @@ -120,6 +120,7 @@ static netdev_tx_t xmit(struct sk_buff *skb, struct net_device *dev) struct sk_buff *next; struct sk_buff_head packets; sa_family_t family; + u32 mtu; int ret; if (unlikely(skb_examine_untrusted_ip_hdr(skb) != skb->protocol)) { @@ -142,6 +143,8 @@ static netdev_tx_t xmit(struct sk_buff *skb, struct net_device *dev) goto err_peer; } + mtu = dst_mtu(skb_dst(skb)); + __skb_queue_head_init(&packets); if (!skb_is_gso(skb)) skb->next = NULL; @@ -168,6 +171,8 @@ static netdev_tx_t xmit(struct sk_buff *skb, struct net_device *dev) */ skb_dst_drop(skb); + PACKET_CB(skb)->mtu = mtu; + __skb_queue_tail(&packets, skb); } while ((skb = next) != NULL); diff --git a/src/queueing.h b/src/queueing.h index d5948f3..c507536 100644 --- a/src/queueing.h +++ b/src/queueing.h @@ -46,6 +46,7 @@ struct packet_cb { u64 nonce; struct noise_keypair *keypair; atomic_t state; + u32 mtu; u8 ds; }; #define PACKET_PEER(skb) (((struct packet_cb *)skb->cb)->keypair->entry.peer) @@ -116,11 +116,11 @@ static inline unsigned int skb_padding(struct sk_buff *skb) * isn't strictly neccessary, but it's better to be cautious here, especially * if that code ever changes. */ - unsigned int last_unit = skb->len % skb->dev->mtu; + unsigned int last_unit = skb->len % PACKET_CB(skb)->mtu; unsigned int padded_size = (last_unit + MESSAGE_PADDING_MULTIPLE - 1) & ~(MESSAGE_PADDING_MULTIPLE - 1); - if (padded_size > skb->dev->mtu) - padded_size = skb->dev->mtu; + if (padded_size > PACKET_CB(skb)->mtu) + padded_size = PACKET_CB(skb)->mtu; return padded_size - last_unit; } @@ -178,6 +178,7 @@ void packet_send_keepalive(struct wireguard_peer *peer) return; skb_reserve(skb, DATA_PACKET_HEAD_ROOM); skb->dev = peer->device->dev; + PACKET_CB(skb)->mtu = skb->dev->mtu; skb_queue_tail(&peer->staged_packet_queue, skb); net_dbg_ratelimited("%s: Sending keepalive packet to peer %llu (%pISpfsc)\n", peer->device->dev->name, peer->internal_id, &peer->endpoint.addr); } diff --git a/src/tests/netns.sh b/src/tests/netns.sh index 57d0b28..d1950a0 100755 --- a/src/tests/netns.sh +++ b/src/tests/netns.sh @@ -169,6 +169,19 @@ ip1 link set wg0 mtu $big_mtu ip2 link set wg0 mtu $big_mtu tests +# Test that route MTUs work with the padding +ip1 link set wg0 mtu 1300 +ip2 link set wg0 mtu 1300 +n1 wg set wg0 peer "$pub2" endpoint 127.0.0.1:2 +n2 wg set wg0 peer "$pub1" endpoint 127.0.0.1:1 +n0 iptables -A INPUT -m length --length 1360 -j DROP +n1 ip route add 192.168.241.2/32 dev wg0 mtu 1299 +n2 ip route add 192.168.241.1/32 dev wg0 mtu 1299 +n2 ping -c 1 -W 1 -s 1269 192.168.241.1 +n2 ip route delete 192.168.241.1/32 dev wg0 mtu 1299 +n1 ip route delete 192.168.241.2/32 dev wg0 mtu 1299 +n0 iptables -F INPUT + ip1 link set wg0 mtu $orig_mtu ip2 link set wg0 mtu $orig_mtu diff --git a/src/tests/qemu/kernel.config b/src/tests/qemu/kernel.config index 1f16016..6c3adc0 100644 --- a/src/tests/qemu/kernel.config +++ b/src/tests/qemu/kernel.config @@ -11,13 +11,16 @@ CONFIG_UNIX=y CONFIG_INET=y CONFIG_IPV6=y CONFIG_NETFILTER=y +CONFIG_NETFILTER_ADVANCED=y CONFIG_NF_CONNTRACK=y CONFIG_NF_NAT=y CONFIG_NETFILTER_XTABLES=y CONFIG_NETFILTER_XT_NAT=y +CONFIG_NETFILTER_XT_MATCH_LENGTH=y CONFIG_NF_CONNTRACK_IPV4=y CONFIG_NF_NAT_IPV4=y CONFIG_IP_NF_IPTABLES=y +CONFIG_IP_NF_FILTER=y CONFIG_IP_NF_NAT=y CONFIG_TTY=y CONFIG_BINFMT_ELF=y |