summaryrefslogtreecommitdiffstats
path: root/usr.sbin/nsd/server.c
diff options
context:
space:
mode:
authorflorian <florian@openbsd.org>2019-03-30 01:20:29 +0000
committerflorian <florian@openbsd.org>2019-03-30 01:20:29 +0000
commita1bac035f347a6dc3f99510e706aacd2ec98dd3f (patch)
tree2cbf530d96073b94b1bf10cd6ce2b9b3ac445843 /usr.sbin/nsd/server.c
parentmove the HARDWARE sections in line with other wireless pages; (diff)
downloadwireguard-openbsd-a1bac035f347a6dc3f99510e706aacd2ec98dd3f.tar.xz
wireguard-openbsd-a1bac035f347a6dc3f99510e706aacd2ec98dd3f.zip
Update to nsd 4.1.27
OK sthen
Diffstat (limited to 'usr.sbin/nsd/server.c')
-rw-r--r--usr.sbin/nsd/server.c56
1 files changed, 49 insertions, 7 deletions
diff --git a/usr.sbin/nsd/server.c b/usr.sbin/nsd/server.c
index edde352117b..ff2f62fff82 100644
--- a/usr.sbin/nsd/server.c
+++ b/usr.sbin/nsd/server.c
@@ -740,13 +740,55 @@ server_init_ifs(struct nsd *nsd, size_t from, size_t to, int* reuseport_works)
#endif
#if defined(AF_INET)
if (addr->ai_family == AF_INET) {
-# if defined(IP_MTU_DISCOVER) && defined(IP_PMTUDISC_DONT)
- int action = IP_PMTUDISC_DONT;
- if (setsockopt(nsd->udp[i].s, IPPROTO_IP,
- IP_MTU_DISCOVER, &action, sizeof(action)) < 0)
- {
- log_msg(LOG_ERR, "setsockopt(..., IP_MTU_DISCOVER, IP_PMTUDISC_DONT...) failed: %s",
- strerror(errno));
+# if defined(IP_MTU_DISCOVER)
+ int mtudisc_disabled = 0;
+# if defined(IP_PMTUDISC_OMIT)
+ /* Try IP_PMTUDISC_OMIT first */
+
+ /*
+ * Linux 3.15 has IP_PMTUDISC_OMIT which makes sockets
+ * ignore PMTU information and send packets with DF=0.
+ * Fragmentation is allowed if and only if the packet
+ * size exceeds the outgoing interface MTU or the packet
+ * encounters smaller MTU link in network.
+ * This mitigates DNS fragmentation attacks by preventing
+ * forged PMTU information.
+ * FreeBSD already has same semantics without setting
+ * the option.
+ */
+ int action_omit = IP_PMTUDISC_OMIT;
+ if (!mtudisc_disabled) {
+ if(setsockopt(nsd->udp[i].s, IPPROTO_IP,
+ IP_MTU_DISCOVER, &action_omit,
+ sizeof(action_omit)) < 0)
+ {
+ log_msg(LOG_ERR, "setsockopt(..., IP_MTU_DISCOVER, IP_PMTUDISC_OMIT...) failed: %s",
+ strerror(errno));
+ } else {
+ mtudisc_disabled = 1;
+ }
+ }
+# endif /* IP_PMTUDISC_OMIT */
+# if defined(IP_PMTUDISC_DONT)
+ /*
+ * Use IP_PMTUDISC_DONT
+ * if IP_PMTUDISC_OMIT failed / undefined
+ */
+ if (!mtudisc_disabled) {
+ int action_dont = IP_PMTUDISC_DONT;
+ if (setsockopt(nsd->udp[i].s, IPPROTO_IP,
+ IP_MTU_DISCOVER, &action_dont,
+ sizeof(action_dont)) < 0)
+ {
+ log_msg(LOG_ERR, "setsockopt(..., IP_MTU_DISCOVER, IP_PMTUDISC_DONT...) failed: %s",
+ strerror(errno));
+ } else {
+ mtudisc_disabled = 1;
+ }
+ }
+# endif /* IP_PMTUDISC_DONT */
+ /* exit if all methods to disable PMTUD failed */
+ if(!mtudisc_disabled) {
return -1;
}
# elif defined(IP_DONTFRAG)