summaryrefslogtreecommitdiffstats
path: root/sys/netinet/tcp_subr.c
diff options
context:
space:
mode:
authorglebius <glebius@FreeBSD.org>2015-09-30 03:37:37 +0000
committerglebius <glebius@FreeBSD.org>2015-09-30 03:37:37 +0000
commit45adeac7f335bcda13b9ae828b2ba0778edf9f14 (patch)
tree67f0173bd74cae9ea93a939b81f85bc1ee875e92 /sys/netinet/tcp_subr.c
parent1373e1739e497918eaad8df7277fcff117dc9615 (diff)
downloadFreeBSD-src-45adeac7f335bcda13b9ae828b2ba0778edf9f14.zip
FreeBSD-src-45adeac7f335bcda13b9ae828b2ba0778edf9f14.tar.gz
When processing ICMP need frag message, ignore the suggested MTU unless it
is smaller than the current one for this connection. This is behavior specified by RFC 1191, and this is how original BSD stack behaved, but this was unintentionally regressed in r182851. Reported & tested by: Richard Russo <russor whatsapp.com> Differential Revision: D3567 Sponsored by: Nginx, Inc.
Diffstat (limited to 'sys/netinet/tcp_subr.c')
-rw-r--r--sys/netinet/tcp_subr.c21
1 files changed, 10 insertions, 11 deletions
diff --git a/sys/netinet/tcp_subr.c b/sys/netinet/tcp_subr.c
index fa278a8..a20bd81 100644
--- a/sys/netinet/tcp_subr.c
+++ b/sys/netinet/tcp_subr.c
@@ -1541,11 +1541,6 @@ tcp_ctlinput(int cmd, struct sockaddr *sa, void *vip)
* in the route to the suggested new
* value (if given) and then notify.
*/
- bzero(&inc, sizeof(inc));
- inc.inc_faddr = faddr;
- inc.inc_fibnum =
- inp->inp_inc.inc_fibnum;
-
mtu = ntohs(icp->icmp_nextmtu);
/*
* If no alternative MTU was
@@ -1560,14 +1555,18 @@ tcp_ctlinput(int cmd, struct sockaddr *sa, void *vip)
mtu = V_tcp_minmss +
sizeof(struct tcpiphdr);
/*
- * Only cache the MTU if it
- * is smaller than the interface
- * or route MTU. tcp_mtudisc()
- * will do right thing by itself.
+ * Only process the offered MTU if it
+ * is smaller than the current one.
*/
- if (mtu <= tcp_maxmtu(&inc, NULL))
+ if (mtu < tp->t_maxopd +
+ sizeof(struct tcpiphdr)) {
+ bzero(&inc, sizeof(inc));
+ inc.inc_faddr = faddr;
+ inc.inc_fibnum =
+ inp->inp_inc.inc_fibnum;
tcp_hc_updatemtu(&inc, mtu);
- tcp_mtudisc(inp, mtu);
+ tcp_mtudisc(inp, mtu);
+ }
} else
inp = (*notify)(inp,
inetctlerrmap[cmd]);
OpenPOWER on IntegriCloud