diff --git a/contrib/unbound/Makefile.in b/contrib/unbound/Makefile.in index 033b026cc911..1c33070336ef 100644 --- a/contrib/unbound/Makefile.in +++ b/contrib/unbound/Makefile.in @@ -426,7 +426,7 @@ libunbound/python/libunbound_wrap.c: $(srcdir)/libunbound/python/libunbound.i un # Pyunbound python unbound wrapper _unbound.la: libunbound_wrap.lo libunbound.la - $(LIBTOOL) --tag=CC --mode=link $(CC) $(RUNTIME_PATH) $(CPPFLAGS) $(CFLAGS) $(LDFLAGS) -module -avoid-version -no-undefined -shared -o $@ libunbound_wrap.lo -rpath $(PYTHON_SITE_PKG) L. -L.libs -lunbound + $(LIBTOOL) --tag=CC --mode=link $(CC) $(RUNTIME_PATH) $(CPPFLAGS) $(CFLAGS) $(LDFLAGS) -module -avoid-version -no-undefined -shared -o $@ libunbound_wrap.lo -rpath $(PYTHON_SITE_PKG) -L. -L.libs -lunbound util/config_file.c: util/configparser.h util/configlexer.c: $(srcdir)/util/configlexer.lex util/configparser.h @@ -735,9 +735,9 @@ iter_utils.lo iter_utils.o: $(srcdir)/iterator/iter_utils.c config.h $(srcdir)/i $(srcdir)/sldns/str2wire.h listen_dnsport.lo listen_dnsport.o: $(srcdir)/services/listen_dnsport.c config.h \ $(srcdir)/services/listen_dnsport.h $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/services/outside_network.h \ - $(srcdir)/util/rbtree.h $(srcdir)/util/log.h $(srcdir)/util/config_file.h \ - $(srcdir)/util/net_help.h $(srcdir)/sldns/sbuffer.h + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/log.h \ + $(srcdir)/services/outside_network.h $(srcdir)/util/rbtree.h \ + $(srcdir)/util/config_file.h $(srcdir)/util/net_help.h $(srcdir)/sldns/sbuffer.h localzone.lo localzone.o: $(srcdir)/services/localzone.c config.h $(srcdir)/services/localzone.h \ $(srcdir)/util/rbtree.h $(srcdir)/util/locks.h $(srcdir)/util/log.h $(srcdir)/util/storage/dnstree.h \ $(srcdir)/util/module.h $(srcdir)/util/storage/lruhash.h $(srcdir)/util/data/msgreply.h \ @@ -749,8 +749,8 @@ localzone.lo localzone.o: $(srcdir)/services/localzone.c config.h $(srcdir)/serv $(srcdir)/util/as112.h mesh.lo mesh.o: $(srcdir)/services/mesh.c config.h $(srcdir)/services/mesh.h $(srcdir)/util/rbtree.h \ $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/util/data/msgparse.h $(srcdir)/util/storage/lruhash.h $(srcdir)/util/locks.h \ - $(srcdir)/util/log.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h $(srcdir)/util/module.h \ + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/log.h $(srcdir)/util/data/msgparse.h \ + $(srcdir)/util/storage/lruhash.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h $(srcdir)/util/module.h \ $(srcdir)/util/data/msgreply.h $(srcdir)/util/data/packed_rrset.h $(srcdir)/services/modstack.h \ $(srcdir)/services/outbound_list.h $(srcdir)/services/cache/dns.h $(srcdir)/util/net_help.h \ $(srcdir)/util/regional.h $(srcdir)/util/data/msgencode.h $(srcdir)/util/timehist.h $(srcdir)/util/fptr_wlist.h \ @@ -777,12 +777,12 @@ view.lo view.o: $(srcdir)/services/view.c config.h $(srcdir)/services/view.h $(s outbound_list.lo outbound_list.o: $(srcdir)/services/outbound_list.c config.h \ $(srcdir)/services/outbound_list.h $(srcdir)/services/outside_network.h $(srcdir)/util/rbtree.h \ $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/log.h outside_network.lo outside_network.o: $(srcdir)/services/outside_network.c config.h \ $(srcdir)/services/outside_network.h $(srcdir)/util/rbtree.h $(srcdir)/util/netevent.h \ $(srcdir)/dnscrypt/dnscrypt.h $(srcdir)/dnscrypt/cert.h \ - $(srcdir)/services/listen_dnsport.h $(srcdir)/services/cache/infra.h \ - $(srcdir)/util/storage/lruhash.h $(srcdir)/util/locks.h $(srcdir)/util/log.h $(srcdir)/util/storage/dnstree.h \ + $(srcdir)/util/locks.h $(srcdir)/util/log.h $(srcdir)/services/listen_dnsport.h \ + $(srcdir)/services/cache/infra.h $(srcdir)/util/storage/lruhash.h $(srcdir)/util/storage/dnstree.h \ $(srcdir)/util/rtt.h $(srcdir)/util/data/msgreply.h $(srcdir)/util/data/packed_rrset.h \ $(srcdir)/util/data/msgparse.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h $(srcdir)/util/data/msgencode.h \ $(srcdir)/util/data/dname.h $(srcdir)/util/net_help.h $(srcdir)/util/random.h $(srcdir)/util/fptr_wlist.h \ @@ -830,7 +830,7 @@ authzone.lo authzone.o: $(srcdir)/services/authzone.c config.h $(srcdir)/service $(srcdir)/validator/val_secalgo.h fptr_wlist.lo fptr_wlist.o: $(srcdir)/util/fptr_wlist.c config.h $(srcdir)/util/fptr_wlist.h \ $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/util/storage/lruhash.h $(srcdir)/util/locks.h $(srcdir)/util/log.h \ + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/log.h $(srcdir)/util/storage/lruhash.h \ $(srcdir)/util/module.h $(srcdir)/util/data/msgreply.h $(srcdir)/util/data/packed_rrset.h \ $(srcdir)/util/data/msgparse.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h $(srcdir)/util/tube.h \ $(srcdir)/services/mesh.h $(srcdir)/util/rbtree.h $(srcdir)/services/modstack.h $(srcdir)/util/mini_event.h \ @@ -851,8 +851,8 @@ locks.lo locks.o: $(srcdir)/util/locks.c config.h $(srcdir)/util/locks.h $(srcdi log.lo log.o: $(srcdir)/util/log.c config.h $(srcdir)/util/log.h $(srcdir)/util/locks.h $(srcdir)/sldns/sbuffer.h mini_event.lo mini_event.o: $(srcdir)/util/mini_event.c config.h $(srcdir)/util/mini_event.h $(srcdir)/util/rbtree.h \ $(srcdir)/util/fptr_wlist.h $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/util/storage/lruhash.h \ - $(srcdir)/util/locks.h $(srcdir)/util/log.h $(srcdir)/util/module.h $(srcdir)/util/data/msgreply.h \ + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/log.h \ + $(srcdir)/util/storage/lruhash.h $(srcdir)/util/module.h $(srcdir)/util/data/msgreply.h \ $(srcdir)/util/data/packed_rrset.h $(srcdir)/util/data/msgparse.h $(srcdir)/sldns/pkthdr.h \ $(srcdir)/sldns/rrdef.h $(srcdir)/util/tube.h $(srcdir)/services/mesh.h $(srcdir)/util/rbtree.h \ $(srcdir)/services/modstack.h @@ -860,8 +860,8 @@ module.lo module.o: $(srcdir)/util/module.c config.h $(srcdir)/util/module.h $(s $(srcdir)/util/locks.h $(srcdir)/util/log.h $(srcdir)/util/data/msgreply.h $(srcdir)/util/data/packed_rrset.h \ $(srcdir)/util/data/msgparse.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h $(srcdir)/sldns/wire2str.h netevent.lo netevent.o: $(srcdir)/util/netevent.c config.h $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/util/ub_event.h $(srcdir)/util/log.h \ - $(srcdir)/util/net_help.h $(srcdir)/util/fptr_wlist.h $(srcdir)/util/storage/lruhash.h $(srcdir)/util/locks.h \ + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/log.h \ + $(srcdir)/util/ub_event.h $(srcdir)/util/net_help.h $(srcdir)/util/fptr_wlist.h $(srcdir)/util/storage/lruhash.h \ $(srcdir)/util/module.h $(srcdir)/util/data/msgreply.h $(srcdir)/util/data/packed_rrset.h \ $(srcdir)/util/data/msgparse.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h $(srcdir)/util/tube.h \ $(srcdir)/services/mesh.h $(srcdir)/util/rbtree.h $(srcdir)/services/modstack.h $(srcdir)/sldns/sbuffer.h \ @@ -876,7 +876,7 @@ net_help.lo net_help.o: $(srcdir)/util/net_help.c config.h $(srcdir)/util/net_he random.lo random.o: $(srcdir)/util/random.c config.h $(srcdir)/util/random.h $(srcdir)/util/log.h rbtree.lo rbtree.o: $(srcdir)/util/rbtree.c config.h $(srcdir)/util/log.h $(srcdir)/util/fptr_wlist.h \ $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/util/storage/lruhash.h $(srcdir)/util/locks.h $(srcdir)/util/log.h \ + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/log.h $(srcdir)/util/storage/lruhash.h \ $(srcdir)/util/module.h $(srcdir)/util/data/msgreply.h $(srcdir)/util/data/packed_rrset.h \ $(srcdir)/util/data/msgparse.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h $(srcdir)/util/tube.h \ $(srcdir)/services/mesh.h $(srcdir)/util/rbtree.h $(srcdir)/services/modstack.h @@ -897,19 +897,19 @@ slabhash.lo slabhash.o: $(srcdir)/util/storage/slabhash.c config.h $(srcdir)/uti timehist.lo timehist.o: $(srcdir)/util/timehist.c config.h $(srcdir)/util/timehist.h $(srcdir)/util/log.h tube.lo tube.o: $(srcdir)/util/tube.c config.h $(srcdir)/util/tube.h $(srcdir)/util/log.h $(srcdir)/util/net_help.h \ $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/util/fptr_wlist.h $(srcdir)/util/storage/lruhash.h $(srcdir)/util/locks.h \ + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/fptr_wlist.h $(srcdir)/util/storage/lruhash.h \ $(srcdir)/util/module.h $(srcdir)/util/data/msgreply.h $(srcdir)/util/data/packed_rrset.h \ $(srcdir)/util/data/msgparse.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h $(srcdir)/services/mesh.h \ $(srcdir)/util/rbtree.h $(srcdir)/services/modstack.h $(srcdir)/util/ub_event.h ub_event.lo ub_event.o: $(srcdir)/util/ub_event.c config.h $(srcdir)/util/ub_event.h $(srcdir)/util/log.h \ $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/util/tube.h $(srcdir)/util/mini_event.h $(srcdir)/util/rbtree.h + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/tube.h $(srcdir)/util/mini_event.h $(srcdir)/util/rbtree.h ub_event_pluggable.lo ub_event_pluggable.o: $(srcdir)/util/ub_event_pluggable.c config.h $(srcdir)/util/ub_event.h \ $(srcdir)/libunbound/unbound-event.h $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/util/log.h $(srcdir)/util/fptr_wlist.h \ - $(srcdir)/util/storage/lruhash.h $(srcdir)/util/locks.h $(srcdir)/util/module.h $(srcdir)/util/data/msgreply.h \ - $(srcdir)/util/data/packed_rrset.h $(srcdir)/util/data/msgparse.h $(srcdir)/sldns/pkthdr.h \ - $(srcdir)/sldns/rrdef.h $(srcdir)/util/tube.h $(srcdir)/services/mesh.h $(srcdir)/util/rbtree.h \ + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/log.h \ + $(srcdir)/util/fptr_wlist.h $(srcdir)/util/storage/lruhash.h $(srcdir)/util/module.h \ + $(srcdir)/util/data/msgreply.h $(srcdir)/util/data/packed_rrset.h $(srcdir)/util/data/msgparse.h \ + $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h $(srcdir)/util/tube.h $(srcdir)/services/mesh.h $(srcdir)/util/rbtree.h \ $(srcdir)/services/modstack.h $(srcdir)/util/mini_event.h $(srcdir)/util/rbtree.h winsock_event.lo winsock_event.o: $(srcdir)/util/winsock_event.c config.h autotrust.lo autotrust.o: $(srcdir)/validator/autotrust.c config.h $(srcdir)/validator/autotrust.h \ @@ -1040,7 +1040,9 @@ checklocks.lo checklocks.o: $(srcdir)/testcode/checklocks.c config.h $(srcdir)/u $(srcdir)/testcode/checklocks.h dnscrypt.lo dnscrypt.o: $(srcdir)/dnscrypt/dnscrypt.c config.h $(srcdir)/sldns/sbuffer.h \ $(srcdir)/util/config_file.h $(srcdir)/util/net_help.h $(srcdir)/util/log.h $(srcdir)/util/netevent.h \ - $(srcdir)/dnscrypt/dnscrypt.h $(srcdir)/dnscrypt/cert.h + $(srcdir)/dnscrypt/dnscrypt.h $(srcdir)/dnscrypt/cert.h \ + $(srcdir)/util/locks.h $(srcdir)/util/storage/slabhash.h $(srcdir)/util/storage/lruhash.h \ + $(srcdir)/util/storage/lookup3.h ipsecmod.lo ipsecmod.o: $(srcdir)/ipsecmod/ipsecmod.c config.h $(srcdir)/ipsecmod/ipsecmod.h \ $(srcdir)/util/module.h $(srcdir)/util/storage/lruhash.h $(srcdir)/util/locks.h $(srcdir)/util/log.h \ $(srcdir)/util/data/msgreply.h $(srcdir)/util/data/packed_rrset.h $(srcdir)/util/data/msgparse.h \ @@ -1174,9 +1176,10 @@ stats.lo stats.o: $(srcdir)/daemon/stats.c config.h $(srcdir)/daemon/stats.h $(s $(srcdir)/daemon/daemon.h $(srcdir)/services/modstack.h \ $(srcdir)/services/mesh.h $(srcdir)/util/rbtree.h $(srcdir)/services/outside_network.h \ $(srcdir)/services/listen_dnsport.h $(srcdir)/util/config_file.h $(srcdir)/util/tube.h $(srcdir)/util/net_help.h \ - $(srcdir)/validator/validator.h $(srcdir)/validator/val_utils.h $(srcdir)/services/cache/rrset.h \ - $(srcdir)/util/storage/slabhash.h $(srcdir)/services/cache/infra.h $(srcdir)/util/storage/dnstree.h \ - $(srcdir)/util/rtt.h $(srcdir)/validator/val_kcache.h + $(srcdir)/validator/validator.h $(srcdir)/validator/val_utils.h $(srcdir)/iterator/iterator.h \ + $(srcdir)/services/outbound_list.h $(srcdir)/services/cache/rrset.h $(srcdir)/util/storage/slabhash.h \ + $(srcdir)/services/cache/infra.h $(srcdir)/util/storage/dnstree.h $(srcdir)/util/rtt.h \ + $(srcdir)/validator/val_kcache.h unbound.lo unbound.o: $(srcdir)/daemon/unbound.c config.h $(srcdir)/util/log.h $(srcdir)/daemon/daemon.h \ $(srcdir)/util/locks.h $(srcdir)/util/alloc.h $(srcdir)/services/modstack.h \ $(srcdir)/daemon/remote.h \ @@ -1207,16 +1210,15 @@ worker.lo worker.o: $(srcdir)/daemon/worker.c config.h $(srcdir)/util/log.h $(sr $(srcdir)/libunbound/libworker.h $(srcdir)/sldns/wire2str.h $(srcdir)/util/shm_side/shm_main.h testbound.lo testbound.o: $(srcdir)/testcode/testbound.c config.h $(srcdir)/testcode/testpkts.h \ $(srcdir)/testcode/replay.h $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/util/rbtree.h \ - $(srcdir)/testcode/fake_event.h $(srcdir)/daemon/remote.h \ - $(srcdir)/util/config_file.h $(srcdir)/sldns/keyraw.h $(srcdir)/daemon/unbound.c $(srcdir)/util/log.h \ - $(srcdir)/daemon/daemon.h $(srcdir)/util/locks.h $(srcdir)/util/alloc.h $(srcdir)/services/modstack.h \ - $(srcdir)/util/storage/slabhash.h $(srcdir)/util/storage/lruhash.h \ - $(srcdir)/services/listen_dnsport.h $(srcdir)/services/cache/rrset.h \ - $(srcdir)/util/data/packed_rrset.h $(srcdir)/services/cache/infra.h $(srcdir)/util/storage/dnstree.h \ - $(srcdir)/util/rtt.h $(srcdir)/util/data/msgreply.h $(srcdir)/util/fptr_wlist.h $(srcdir)/util/module.h \ - $(srcdir)/util/data/msgparse.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h $(srcdir)/util/tube.h \ - $(srcdir)/services/mesh.h $(srcdir)/util/net_help.h $(srcdir)/util/ub_event.h + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/log.h \ + $(srcdir)/util/rbtree.h $(srcdir)/testcode/fake_event.h $(srcdir)/daemon/remote.h \ + $(srcdir)/util/config_file.h $(srcdir)/sldns/keyraw.h $(srcdir)/daemon/unbound.c $(srcdir)/daemon/daemon.h \ + $(srcdir)/util/alloc.h $(srcdir)/services/modstack.h \ + $(srcdir)/util/storage/slabhash.h $(srcdir)/util/storage/lruhash.h $(srcdir)/services/listen_dnsport.h \ + $(srcdir)/services/cache/rrset.h $(srcdir)/util/data/packed_rrset.h $(srcdir)/services/cache/infra.h \ + $(srcdir)/util/storage/dnstree.h $(srcdir)/util/rtt.h $(srcdir)/util/data/msgreply.h $(srcdir)/util/fptr_wlist.h \ + $(srcdir)/util/module.h $(srcdir)/util/data/msgparse.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h \ + $(srcdir)/util/tube.h $(srcdir)/services/mesh.h $(srcdir)/util/net_help.h $(srcdir)/util/ub_event.h testpkts.lo testpkts.o: $(srcdir)/testcode/testpkts.c config.h $(srcdir)/testcode/testpkts.h \ $(srcdir)/util/net_help.h $(srcdir)/util/log.h $(srcdir)/sldns/sbuffer.h $(srcdir)/sldns/rrdef.h $(srcdir)/sldns/pkthdr.h \ $(srcdir)/sldns/str2wire.h $(srcdir)/sldns/wire2str.h @@ -1266,17 +1268,19 @@ stats.lo stats.o: $(srcdir)/daemon/stats.c config.h $(srcdir)/daemon/stats.h $(s $(srcdir)/daemon/daemon.h $(srcdir)/services/modstack.h \ $(srcdir)/services/mesh.h $(srcdir)/util/rbtree.h $(srcdir)/services/outside_network.h \ $(srcdir)/services/listen_dnsport.h $(srcdir)/util/config_file.h $(srcdir)/util/tube.h $(srcdir)/util/net_help.h \ - $(srcdir)/validator/validator.h $(srcdir)/validator/val_utils.h $(srcdir)/services/cache/rrset.h \ - $(srcdir)/util/storage/slabhash.h $(srcdir)/services/cache/infra.h $(srcdir)/util/storage/dnstree.h \ - $(srcdir)/util/rtt.h $(srcdir)/validator/val_kcache.h + $(srcdir)/validator/validator.h $(srcdir)/validator/val_utils.h $(srcdir)/iterator/iterator.h \ + $(srcdir)/services/outbound_list.h $(srcdir)/services/cache/rrset.h $(srcdir)/util/storage/slabhash.h \ + $(srcdir)/services/cache/infra.h $(srcdir)/util/storage/dnstree.h $(srcdir)/util/rtt.h \ + $(srcdir)/validator/val_kcache.h replay.lo replay.o: $(srcdir)/testcode/replay.c config.h $(srcdir)/util/log.h $(srcdir)/util/net_help.h \ $(srcdir)/util/config_file.h $(srcdir)/testcode/replay.h $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/testcode/testpkts.h \ - $(srcdir)/util/rbtree.h $(srcdir)/testcode/fake_event.h $(srcdir)/sldns/str2wire.h $(srcdir)/sldns/rrdef.h + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h \ + $(srcdir)/testcode/testpkts.h $(srcdir)/util/rbtree.h $(srcdir)/testcode/fake_event.h $(srcdir)/sldns/str2wire.h \ + $(srcdir)/sldns/rrdef.h fake_event.lo fake_event.o: $(srcdir)/testcode/fake_event.c config.h $(srcdir)/testcode/fake_event.h \ $(srcdir)/util/netevent.h $(srcdir)/dnscrypt/dnscrypt.h \ - $(srcdir)/dnscrypt/cert.h $(srcdir)/util/net_help.h $(srcdir)/util/log.h $(srcdir)/util/data/msgparse.h \ - $(srcdir)/util/storage/lruhash.h $(srcdir)/util/locks.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h \ + $(srcdir)/dnscrypt/cert.h $(srcdir)/util/locks.h $(srcdir)/util/log.h $(srcdir)/util/net_help.h \ + $(srcdir)/util/data/msgparse.h $(srcdir)/util/storage/lruhash.h $(srcdir)/sldns/pkthdr.h $(srcdir)/sldns/rrdef.h \ $(srcdir)/util/data/msgreply.h $(srcdir)/util/data/packed_rrset.h $(srcdir)/util/data/msgencode.h \ $(srcdir)/util/data/dname.h $(srcdir)/util/config_file.h $(srcdir)/services/listen_dnsport.h \ $(srcdir)/services/outside_network.h $(srcdir)/util/rbtree.h \ @@ -1309,7 +1313,8 @@ unbound-checkconf.lo unbound-checkconf.o: $(srcdir)/smallapp/unbound-checkconf.c $(srcdir)/iterator/iterator.h $(srcdir)/services/outbound_list.h $(srcdir)/iterator/iter_fwd.h \ $(srcdir)/util/rbtree.h $(srcdir)/iterator/iter_hints.h $(srcdir)/util/storage/dnstree.h \ $(srcdir)/validator/validator.h $(srcdir)/validator/val_utils.h $(srcdir)/services/localzone.h \ - $(srcdir)/services/view.h $(srcdir)/respip/respip.h $(srcdir)/sldns/sbuffer.h $(PYTHONMOD_HEADER) + $(srcdir)/services/view.h $(srcdir)/respip/respip.h $(srcdir)/sldns/sbuffer.h $(PYTHONMOD_HEADER) \ + $(srcdir)/edns-subnet/subnet-whitelist.h worker_cb.lo worker_cb.o: $(srcdir)/smallapp/worker_cb.c config.h $(srcdir)/libunbound/context.h \ $(srcdir)/util/locks.h $(srcdir)/util/log.h $(srcdir)/util/alloc.h $(srcdir)/util/rbtree.h $(srcdir)/services/modstack.h \ $(srcdir)/libunbound/unbound.h $(srcdir)/util/data/packed_rrset.h $(srcdir)/util/storage/lruhash.h \ diff --git a/contrib/unbound/acx_nlnetlabs.m4 b/contrib/unbound/acx_nlnetlabs.m4 index a6c174f1c421..8eccc15b0d80 100644 --- a/contrib/unbound/acx_nlnetlabs.m4 +++ b/contrib/unbound/acx_nlnetlabs.m4 @@ -688,8 +688,8 @@ AC_DEFUN([ACX_SSL_CHECKS], [ # check if -lwsock32 or -lgdi32 are needed. BAKLIBS="$LIBS" BAKSSLLIBS="$LIBSSL_LIBS" - LIBS="$LIBS -lgdi32" - LIBSSL_LIBS="$LIBSSL_LIBS -lgdi32" + LIBS="$LIBS -lgdi32 -lws2_32" + LIBSSL_LIBS="$LIBSSL_LIBS -lgdi32 -lws2_32" AC_MSG_CHECKING([if -lcrypto needs -lgdi32]) AC_TRY_LINK([], [ int HMAC_Update(void); @@ -839,7 +839,11 @@ dnl see if on windows if test "$ac_cv_header_windows_h" = "yes"; then AC_DEFINE(USE_WINSOCK, 1, [Whether the windows socket API is used]) USE_WINSOCK="1" - LIBS="$LIBS -lws2_32" + if echo $LIBS | grep 'lws2_32' >/dev/null; then + : + else + LIBS="$LIBS -lws2_32" + fi fi ], dnl no quick getaddrinfo, try mingw32 and winsock2 library. diff --git a/contrib/unbound/cachedb/cachedb.c b/contrib/unbound/cachedb/cachedb.c index 9a63101edee3..f5f6937eeeed 100644 --- a/contrib/unbound/cachedb/cachedb.c +++ b/contrib/unbound/cachedb/cachedb.c @@ -61,6 +61,8 @@ /** the unit test testframe for cachedb, its module state contains * a cache for a couple queries (in memory). */ struct testframe_moddata { + /** lock for mutex */ + lock_basic_type lock; /** key for single stored data element, NULL if none */ char* stored_key; /** data for single stored data element, NULL if none */ @@ -72,14 +74,18 @@ struct testframe_moddata { static int testframe_init(struct module_env* env, struct cachedb_env* cachedb_env) { + struct testframe_moddata* d; (void)env; verbose(VERB_ALGO, "testframe_init"); - cachedb_env->backend_data = (void*)calloc(1, + d = (struct testframe_moddata*)calloc(1, sizeof(struct testframe_moddata)); + cachedb_env->backend_data = (void*)d; if(!cachedb_env->backend_data) { log_err("out of memory"); return 0; } + lock_basic_init(&d->lock); + lock_protect(&d->lock, d, sizeof(*d)); return 1; } @@ -92,6 +98,7 @@ testframe_deinit(struct module_env* env, struct cachedb_env* cachedb_env) verbose(VERB_ALGO, "testframe_deinit"); if(!d) return; + lock_basic_destroy(&d->lock); free(d->stored_key); free(d->stored_data); free(d); @@ -105,17 +112,22 @@ testframe_lookup(struct module_env* env, struct cachedb_env* cachedb_env, cachedb_env->backend_data; (void)env; verbose(VERB_ALGO, "testframe_lookup of %s", key); + lock_basic_lock(&d->lock); if(d->stored_key && strcmp(d->stored_key, key) == 0) { - if(d->stored_datalen > sldns_buffer_capacity(result_buffer)) + if(d->stored_datalen > sldns_buffer_capacity(result_buffer)) { + lock_basic_unlock(&d->lock); return 0; /* too large */ + } verbose(VERB_ALGO, "testframe_lookup found %d bytes", (int)d->stored_datalen); sldns_buffer_clear(result_buffer); sldns_buffer_write(result_buffer, d->stored_data, d->stored_datalen); sldns_buffer_flip(result_buffer); + lock_basic_unlock(&d->lock); return 1; } + lock_basic_unlock(&d->lock); return 0; } @@ -126,6 +138,7 @@ testframe_store(struct module_env* env, struct cachedb_env* cachedb_env, struct testframe_moddata* d = (struct testframe_moddata*) cachedb_env->backend_data; (void)env; + lock_basic_lock(&d->lock); verbose(VERB_ALGO, "testframe_store %s (%d bytes)", key, (int)data_len); /* free old data element (if any) */ @@ -137,6 +150,7 @@ testframe_store(struct module_env* env, struct cachedb_env* cachedb_env, d->stored_data = memdup(data, data_len); if(!d->stored_data) { + lock_basic_unlock(&d->lock); log_err("out of memory"); return; } @@ -146,8 +160,10 @@ testframe_store(struct module_env* env, struct cachedb_env* cachedb_env, free(d->stored_data); d->stored_data = NULL; d->stored_datalen = 0; + lock_basic_unlock(&d->lock); return; } + lock_basic_unlock(&d->lock); /* (key,data) successfully stored */ } @@ -170,16 +186,17 @@ cachedb_find_backend(const char* str) static int cachedb_apply_cfg(struct cachedb_env* cachedb_env, struct config_file* cfg) { - const char* backend_str = "testframe"; /* TODO get from cfg */ - (void)cfg; /* need this until the TODO is implemented */ - if(backend_str && backend_str[0]) { - cachedb_env->backend = cachedb_find_backend(backend_str); - if(!cachedb_env->backend) { - log_err("cachedb: cannot find backend name '%s", - backend_str); - return 0; - } + const char* backend_str = cfg->cachedb_backend; + + /* If unspecified we use the in-memory test DB. */ + if(!backend_str) + backend_str = "testframe"; + cachedb_env->backend = cachedb_find_backend(backend_str); + if(!cachedb_env->backend) { + log_err("cachedb: cannot find backend name '%s'", backend_str); + return 0; } + /* TODO see if more configuration needs to be applied or not */ return 1; } @@ -277,9 +294,10 @@ calc_hash(struct module_qstate* qstate, char* buf, size_t len) size_t clen = 0; uint8_t hash[CACHEDB_HASHSIZE/8]; const char* hex = "0123456789ABCDEF"; - const char* secret = "default"; /* TODO: from qstate->env->cfg */ + const char* secret = qstate->env->cfg->cachedb_secret ? + qstate->env->cfg->cachedb_secret : "default"; size_t i; - + /* copy the hash info into the clear buffer */ if(clen + qstate->qinfo.qname_len < sizeof(clear)) { memmove(clear+clen, qstate->qinfo.qname, diff --git a/contrib/unbound/config.h b/contrib/unbound/config.h index 9d3a60e46cc2..a6e5d7cb0618 100644 --- a/contrib/unbound/config.h +++ b/contrib/unbound/config.h @@ -297,6 +297,9 @@ /* Define to 1 if you have the header file. */ /* #undef HAVE_NETTLE_DSA_COMPAT_H */ +/* Define to 1 if you have the header file. */ +/* #undef HAVE_NETTLE_EDDSA_H */ + /* Use libnss for crypto */ /* #undef HAVE_NSS */ @@ -602,7 +605,7 @@ #define PACKAGE_NAME "unbound" /* Define to the full name and version of this package. */ -#define PACKAGE_STRING "unbound 1.6.4" +#define PACKAGE_STRING "unbound 1.6.6" /* Define to the one symbol short name of this package. */ #define PACKAGE_TARNAME "unbound" @@ -611,7 +614,7 @@ #define PACKAGE_URL "" /* Define to the version of this package. */ -#define PACKAGE_VERSION "1.6.4" +#define PACKAGE_VERSION "1.6.6" /* default pidfile location */ #define PIDFILE "/var/unbound/unbound.pid" @@ -630,7 +633,7 @@ #define ROOT_CERT_FILE "/var/unbound/icannbundle.pem" /* version number for resource files */ -#define RSRC_PACKAGE_VERSION 1,6,4,0 +#define RSRC_PACKAGE_VERSION 1,6,6,0 /* Directory to chdir to */ #define RUN_DIR "/var/unbound" diff --git a/contrib/unbound/config.h.in b/contrib/unbound/config.h.in index 04aa762c58a9..16a7b0281a1f 100644 --- a/contrib/unbound/config.h.in +++ b/contrib/unbound/config.h.in @@ -296,6 +296,9 @@ /* Define to 1 if you have the header file. */ #undef HAVE_NETTLE_DSA_COMPAT_H +/* Define to 1 if you have the header file. */ +#undef HAVE_NETTLE_EDDSA_H + /* Use libnss for crypto */ #undef HAVE_NSS diff --git a/contrib/unbound/configure b/contrib/unbound/configure index 9b8496c4b859..2821d3209fbd 100755 --- a/contrib/unbound/configure +++ b/contrib/unbound/configure @@ -1,6 +1,6 @@ #! /bin/sh # Guess values for system-dependent variables and create Makefiles. -# Generated by GNU Autoconf 2.69 for unbound 1.6.5. +# Generated by GNU Autoconf 2.69 for unbound 1.6.6. # # Report bugs to . # @@ -590,8 +590,8 @@ MAKEFLAGS= # Identity of this package. PACKAGE_NAME='unbound' PACKAGE_TARNAME='unbound' -PACKAGE_VERSION='1.6.5' -PACKAGE_STRING='unbound 1.6.5' +PACKAGE_VERSION='1.6.6' +PACKAGE_STRING='unbound 1.6.6' PACKAGE_BUGREPORT='unbound-bugs@nlnetlabs.nl' PACKAGE_URL='' @@ -1437,7 +1437,7 @@ if test "$ac_init_help" = "long"; then # Omit some internal or obsolete options to make the list less imposing. # This message is too long to be a string in the A/UX 3.1 sh. cat <<_ACEOF -\`configure' configures unbound 1.6.5 to adapt to many kinds of systems. +\`configure' configures unbound 1.6.6 to adapt to many kinds of systems. Usage: $0 [OPTION]... [VAR=VALUE]... @@ -1502,7 +1502,7 @@ fi if test -n "$ac_init_help"; then case $ac_init_help in - short | recursive ) echo "Configuration of unbound 1.6.5:";; + short | recursive ) echo "Configuration of unbound 1.6.6:";; esac cat <<\_ACEOF @@ -1714,7 +1714,7 @@ fi test -n "$ac_init_help" && exit $ac_status if $ac_init_version; then cat <<\_ACEOF -unbound configure 1.6.5 +unbound configure 1.6.6 generated by GNU Autoconf 2.69 Copyright (C) 2012 Free Software Foundation, Inc. @@ -2423,7 +2423,7 @@ cat >config.log <<_ACEOF This file contains any messages produced by compilers while running configure, to aid debugging if configure makes a mistake. -It was created by unbound $as_me 1.6.5, which was +It was created by unbound $as_me 1.6.6, which was generated by GNU Autoconf 2.69. Invocation command line was $ $0 $@ @@ -2775,11 +2775,11 @@ UNBOUND_VERSION_MAJOR=1 UNBOUND_VERSION_MINOR=6 -UNBOUND_VERSION_MICRO=5 +UNBOUND_VERSION_MICRO=6 LIBUNBOUND_CURRENT=7 -LIBUNBOUND_REVISION=4 +LIBUNBOUND_REVISION=5 LIBUNBOUND_AGE=5 # 1.0.0 had 0:12:0 # 1.0.1 had 0:13:0 @@ -2835,6 +2835,7 @@ LIBUNBOUND_AGE=5 # 1.6.3 had 7:2:5 # 1.6.4 had 7:3:5 # 1.6.5 had 7:4:5 +# 1.6.6 had 7:5:5 # Current -- the number of the binary API that we're implementing # Revision -- which iteration of the implementation of the binary @@ -16464,7 +16465,9 @@ if test x"$ax_pthread_ok" = xyes; then $as_echo "#define HAVE_PTHREAD 1" >>confdefs.h - LIBS="$PTHREAD_LIBS $LIBS" + if test -n "$PTHREAD_LIBS"; then + LIBS="$PTHREAD_LIBS $LIBS" + fi CFLAGS="$CFLAGS $PTHREAD_CFLAGS" CC="$PTHREAD_CC" ub_have_pthreads=yes @@ -16894,8 +16897,16 @@ ac_compiler_gnu=$ac_cv_c_compiler_gnu $as_echo "#define HAVE_PYTHON 1" >>confdefs.h - LIBS="$PYTHON_LDFLAGS $LIBS" - CPPFLAGS="$CPPFLAGS $PYTHON_CPPFLAGS" + if test -n "$LIBS"; then + LIBS="$PYTHON_LDFLAGS $LIBS" + else + LIBS="$PYTHON_LDFLAGS" + fi + if test -n "$CPPFLAGS"; then + CPPFLAGS="$CPPFLAGS $PYTHON_CPPFLAGS" + else + CPPFLAGS="$PYTHON_CPPFLAGS" + fi ub_have_python=yes PC_PY_DEPENDENCY="python" @@ -17250,8 +17261,8 @@ $as_echo "no" >&6; } # check if -lwsock32 or -lgdi32 are needed. BAKLIBS="$LIBS" BAKSSLLIBS="$LIBSSL_LIBS" - LIBS="$LIBS -lgdi32" - LIBSSL_LIBS="$LIBSSL_LIBS -lgdi32" + LIBS="$LIBS -lgdi32 -lws2_32" + LIBSSL_LIBS="$LIBSSL_LIBS -lgdi32 -lws2_32" { $as_echo "$as_me:${as_lineno-$LINENO}: checking if -lcrypto needs -lgdi32" >&5 $as_echo_n "checking if -lcrypto needs -lgdi32... " >&6; } cat confdefs.h - <<_ACEOF >conftest.$ac_ext @@ -18053,6 +18064,7 @@ case "$enable_dsa" in ;; *) # detect if DSA is supported, and turn it off if not. + if test $USE_NSS = "no" -a $USE_NETTLE = "no"; then ac_fn_c_check_func "$LINENO" "DSA_SIG_new" "ac_cv_func_DSA_SIG_new" if test "x$ac_cv_func_DSA_SIG_new" = xyes; then : @@ -18067,6 +18079,13 @@ else fi fi + else + +cat >>confdefs.h <<_ACEOF +#define USE_DSA 1 +_ACEOF + + fi ;; esac @@ -18096,11 +18115,6 @@ cat >>confdefs.h <<_ACEOF _ACEOF if test $ac_have_decl = 1; then : - -cat >>confdefs.h <<_ACEOF -#define USE_ED25519 1 -_ACEOF - use_ed25519="yes" else @@ -18108,6 +18122,28 @@ else fi fi + fi + if test $USE_NETTLE = "yes"; then + for ac_header in nettle/eddsa.h +do : + ac_fn_c_check_header_compile "$LINENO" "nettle/eddsa.h" "ac_cv_header_nettle_eddsa_h" "$ac_includes_default +" +if test "x$ac_cv_header_nettle_eddsa_h" = xyes; then : + cat >>confdefs.h <<_ACEOF +#define HAVE_NETTLE_EDDSA_H 1 +_ACEOF + use_ed25519="yes" +fi + +done + + fi + if test $use_ed25519 = "yes"; then + +cat >>confdefs.h <<_ACEOF +#define USE_ED25519 1 +_ACEOF + fi ;; esac @@ -18621,7 +18657,12 @@ if test x_$enable_static_exe = x_yes; then if test "$on_mingw" = yes; then staticexe="-all-static" # for static compile, include gdi32 and zlib here. - LIBS="$LIBS -lgdi32 -lz" + if echo $LIBS | grep 'lgdi32' >/dev/null; then + : + else + LIBS="$LIBS -lgdi32" + fi + LIBS="$LIBS -lz" fi fi @@ -18979,7 +19020,11 @@ if test "$ac_cv_header_windows_h" = "yes"; then $as_echo "#define USE_WINSOCK 1" >>confdefs.h USE_WINSOCK="1" - LIBS="$LIBS -lws2_32" + if echo $LIBS | grep 'lws2_32' >/dev/null; then + : + else + LIBS="$LIBS -lws2_32" + fi fi else @@ -20633,7 +20678,12 @@ $as_echo "#define OMITTED__D_LARGEFILE_SOURCE_1 1" >>confdefs.h fi -LDFLAGS="$LATE_LDFLAGS $LDFLAGS" +if test -n "$LATE_LDFLAGS"; then + LDFLAGS="$LATE_LDFLAGS $LDFLAGS" +fi +# remove start spaces +LDFLAGS=`echo "$LDFLAGS"|sed -e 's/^ *//'` +LIBS=`echo "$LIBS"|sed -e 's/^ *//'` cat >>confdefs.h <<_ACEOF @@ -20643,7 +20693,7 @@ _ACEOF -version=1.6.5 +version=1.6.6 date=`date +'%b %e, %Y'` @@ -21162,7 +21212,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # report actual input values of CONFIG_FILES etc. instead of their # values after options handling. ac_log=" -This file was extended by unbound $as_me 1.6.5, which was +This file was extended by unbound $as_me 1.6.6, which was generated by GNU Autoconf 2.69. Invocation command line was CONFIG_FILES = $CONFIG_FILES @@ -21228,7 +21278,7 @@ _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`" ac_cs_version="\\ -unbound config.status 1.6.5 +unbound config.status 1.6.6 configured by $0, generated by GNU Autoconf 2.69, with options \\"\$ac_cs_config\\" diff --git a/contrib/unbound/configure.ac b/contrib/unbound/configure.ac index ccbb33d49c41..23a318ee5b77 100644 --- a/contrib/unbound/configure.ac +++ b/contrib/unbound/configure.ac @@ -11,14 +11,14 @@ sinclude(dnscrypt/dnscrypt.m4) # must be numbers. ac_defun because of later processing m4_define([VERSION_MAJOR],[1]) m4_define([VERSION_MINOR],[6]) -m4_define([VERSION_MICRO],[5]) +m4_define([VERSION_MICRO],[6]) AC_INIT(unbound, m4_defn([VERSION_MAJOR]).m4_defn([VERSION_MINOR]).m4_defn([VERSION_MICRO]), unbound-bugs@nlnetlabs.nl, unbound) AC_SUBST(UNBOUND_VERSION_MAJOR, [VERSION_MAJOR]) AC_SUBST(UNBOUND_VERSION_MINOR, [VERSION_MINOR]) AC_SUBST(UNBOUND_VERSION_MICRO, [VERSION_MICRO]) LIBUNBOUND_CURRENT=7 -LIBUNBOUND_REVISION=4 +LIBUNBOUND_REVISION=5 LIBUNBOUND_AGE=5 # 1.0.0 had 0:12:0 # 1.0.1 had 0:13:0 @@ -74,6 +74,7 @@ LIBUNBOUND_AGE=5 # 1.6.3 had 7:2:5 # 1.6.4 had 7:3:5 # 1.6.5 had 7:4:5 +# 1.6.6 had 7:5:5 # Current -- the number of the binary API that we're implementing # Revision -- which iteration of the implementation of the binary @@ -456,7 +457,9 @@ ub_have_pthreads=no if test x_$withval != x_no; then AX_PTHREAD([ AC_DEFINE(HAVE_PTHREAD,1,[Define if you have POSIX threads libraries and header files.]) - LIBS="$PTHREAD_LIBS $LIBS" + if test -n "$PTHREAD_LIBS"; then + LIBS="$PTHREAD_LIBS $LIBS" + fi CFLAGS="$CFLAGS $PTHREAD_CFLAGS" CC="$PTHREAD_CC" ub_have_pthreads=yes @@ -558,8 +561,16 @@ if test x_$ub_test_python != x_no; then AC_SUBST(PY_MAJOR_VERSION) # Have Python AC_DEFINE(HAVE_PYTHON,1,[Define if you have Python libraries and header files.]) - LIBS="$PYTHON_LDFLAGS $LIBS" - CPPFLAGS="$CPPFLAGS $PYTHON_CPPFLAGS" + if test -n "$LIBS"; then + LIBS="$PYTHON_LDFLAGS $LIBS" + else + LIBS="$PYTHON_LDFLAGS" + fi + if test -n "$CPPFLAGS"; then + CPPFLAGS="$CPPFLAGS $PYTHON_CPPFLAGS" + else + CPPFLAGS="$PYTHON_CPPFLAGS" + fi ub_have_python=yes PC_PY_DEPENDENCY="python" AC_SUBST(PC_PY_DEPENDENCY) @@ -912,10 +923,14 @@ case "$enable_dsa" in ;; *) # detect if DSA is supported, and turn it off if not. + if test $USE_NSS = "no" -a $USE_NETTLE = "no"; then AC_CHECK_FUNC(DSA_SIG_new, [ AC_DEFINE_UNQUOTED([USE_DSA], [1], [Define this to enable DSA support.]) ], [if test "x$enable_dsa" = "xyes"; then AC_MSG_ERROR([OpenSSL does not support DSA and you used --enable-dsa.]) fi ]) + else + AC_DEFINE_UNQUOTED([USE_DSA], [1], [Define this to enable DSA support.]) + fi ;; esac @@ -927,13 +942,18 @@ case "$enable_ed25519" in *) if test $USE_NSS = "no" -a $USE_NETTLE = "no"; then AC_CHECK_DECLS([NID_ED25519], [ - AC_DEFINE_UNQUOTED([USE_ED25519], [1], [Define this to enable ED25519 support.]) use_ed25519="yes" ], [ if test "x$enable_ed25519" = "xyes"; then AC_MSG_ERROR([OpenSSL does not support ED25519 and you used --enable-ed25519.]) fi ], [AC_INCLUDES_DEFAULT #include ]) fi + if test $USE_NETTLE = "yes"; then + AC_CHECK_HEADERS([nettle/eddsa.h], use_ed25519="yes",, [AC_INCLUDES_DEFAULT]) + fi + if test $use_ed25519 = "yes"; then + AC_DEFINE_UNQUOTED([USE_ED25519], [1], [Define this to enable ED25519 support.]) + fi ;; esac @@ -1106,7 +1126,12 @@ if test x_$enable_static_exe = x_yes; then if test "$on_mingw" = yes; then staticexe="-all-static" # for static compile, include gdi32 and zlib here. - LIBS="$LIBS -lgdi32 -lz" + if echo $LIBS | grep 'lgdi32' >/dev/null; then + : + else + LIBS="$LIBS -lgdi32" + fi + LIBS="$LIBS -lz" fi fi @@ -1448,7 +1473,12 @@ AC_SUBST(ALLTARGET) AC_SUBST(INSTALLTARGET) ACX_STRIP_EXT_FLAGS -LDFLAGS="$LATE_LDFLAGS $LDFLAGS" +if test -n "$LATE_LDFLAGS"; then + LDFLAGS="$LATE_LDFLAGS $LDFLAGS" +fi +# remove start spaces +LDFLAGS=`echo "$LDFLAGS"|sed -e 's/^ *//'` +LIBS=`echo "$LIBS"|sed -e 's/^ *//'` AC_DEFINE_UNQUOTED([MAXSYSLOGMSGLEN], [10240], [Define to the maximum message length to pass to syslog.]) diff --git a/contrib/unbound/contrib/fastrpz.patch b/contrib/unbound/contrib/fastrpz.patch index aa8c1ece0e20..362e07cc6a8d 100644 --- a/contrib/unbound/contrib/fastrpz.patch +++ b/contrib/unbound/contrib/fastrpz.patch @@ -3263,15 +3263,15 @@ diff -u --unidirectional-new-file -r1.1 ./util/configparser.y %token VAR_RESPONSE_IP_TAG VAR_RESPONSE_IP VAR_RESPONSE_IP_DATA %token VAR_HARDEN_ALGO_DOWNGRADE VAR_IP_TRANSPARENT %token VAR_DISABLE_DNSSEC_LAME_CHECK -@@ -150,7 +151,7 @@ +@@ -153,7 +154,7 @@ toplevelvar: serverstart contents_server | stubstart contents_stub | forwardstart contents_forward | pythonstart contents_py | rcstart contents_rc | dtstart contents_dt | viewstart - contents_view | + contents_view | rpzstart contents_rpz | - dnscstart contents_dnsc + dnscstart contents_dnsc | + cachedbstart contents_cachedb ; - @@ -2160,6 +2161,50 @@ (strcmp($2, "yes")==0); } diff --git a/contrib/unbound/daemon/daemon.c b/contrib/unbound/daemon/daemon.c index dad9f86b344e..7411fabe7573 100644 --- a/contrib/unbound/daemon/daemon.c +++ b/contrib/unbound/daemon/daemon.c @@ -221,7 +221,9 @@ daemon_init(void) # ifdef HAVE_ERR_LOAD_CRYPTO_STRINGS ERR_load_crypto_strings(); # endif +#if OPENSSL_VERSION_NUMBER < 0x10100000 || !defined(HAVE_OPENSSL_INIT_SSL) ERR_load_SSL_strings(); +#endif # ifdef USE_GOST (void)sldns_key_EVP_load_gost_id(); # endif @@ -239,7 +241,7 @@ daemon_init(void) # if OPENSSL_VERSION_NUMBER < 0x10100000 || !defined(HAVE_OPENSSL_INIT_SSL) (void)SSL_library_init(); # else - (void)OPENSSL_init_ssl(0, NULL); + (void)OPENSSL_init_ssl(OPENSSL_INIT_LOAD_SSL_STRINGS, NULL); # endif # if defined(HAVE_SSL) && defined(OPENSSL_THREADS) && !defined(THREADS_DISABLED) if(!ub_openssl_lock_init()) @@ -421,8 +423,8 @@ daemon_create_workers(struct daemon* daemon) daemon->rand = ub_initstate(seed, NULL); if(!daemon->rand) fatal_exit("could not init random generator"); + hash_set_raninit((uint32_t)ub_random(daemon->rand)); } - hash_set_raninit((uint32_t)ub_random(daemon->rand)); shufport = (int*)calloc(65536, sizeof(int)); if(!shufport) fatal_exit("out of memory during daemon init"); @@ -690,6 +692,9 @@ daemon_cleanup(struct daemon* daemon) daemon->num = 0; #ifdef USE_DNSTAP dt_delete(daemon->dtenv); +#endif +#ifdef USE_DNSCRYPT + dnsc_delete(daemon->dnscenv); #endif daemon->cfg = NULL; } diff --git a/contrib/unbound/daemon/remote.c b/contrib/unbound/daemon/remote.c index bb41cc5df2db..243d94c49aa1 100644 --- a/contrib/unbound/daemon/remote.c +++ b/contrib/unbound/daemon/remote.c @@ -229,42 +229,10 @@ daemon_remote_create(struct config_file* cfg) free(rc); return NULL; } - /* no SSLv2, SSLv3 because has defects */ - if((SSL_CTX_set_options(rc->ctx, SSL_OP_NO_SSLv2) & SSL_OP_NO_SSLv2) - != SSL_OP_NO_SSLv2){ - log_crypto_err("could not set SSL_OP_NO_SSLv2"); + if(!listen_sslctx_setup(rc->ctx)) { daemon_remote_delete(rc); return NULL; } - if((SSL_CTX_set_options(rc->ctx, SSL_OP_NO_SSLv3) & SSL_OP_NO_SSLv3) - != SSL_OP_NO_SSLv3){ - log_crypto_err("could not set SSL_OP_NO_SSLv3"); - daemon_remote_delete(rc); - return NULL; - } -#if defined(SSL_OP_NO_TLSv1) && defined(SSL_OP_NO_TLSv1_1) - /* if we have tls 1.1 disable 1.0 */ - if((SSL_CTX_set_options(rc->ctx, SSL_OP_NO_TLSv1) & SSL_OP_NO_TLSv1) - != SSL_OP_NO_TLSv1){ - log_crypto_err("could not set SSL_OP_NO_TLSv1"); - daemon_remote_delete(rc); - return NULL; - } -#endif -#if defined(SSL_OP_NO_TLSv1_1) && defined(SSL_OP_NO_TLSv1_2) - /* if we have tls 1.2 disable 1.1 */ - if((SSL_CTX_set_options(rc->ctx, SSL_OP_NO_TLSv1_1) & SSL_OP_NO_TLSv1_1) - != SSL_OP_NO_TLSv1_1){ - log_crypto_err("could not set SSL_OP_NO_TLSv1_1"); - daemon_remote_delete(rc); - return NULL; - } -#endif -#if defined(SHA256_DIGEST_LENGTH) && defined(USE_ECDSA) - /* if we have sha256, set the cipher list to have no known vulns */ - if(!SSL_CTX_set_cipher_list(rc->ctx, "ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256")) - log_crypto_err("could not set cipher list with SSL_CTX_set_cipher_list"); -#endif if (cfg->remote_control_use_cert == 0) { /* No certificates are requested */ @@ -314,23 +282,7 @@ daemon_remote_create(struct config_file* cfg) log_crypto_err("Error in SSL_CTX check_private_key"); goto setup_error; } -#if HAVE_DECL_SSL_CTX_SET_ECDH_AUTO - if(!SSL_CTX_set_ecdh_auto(rc->ctx,1)) { - log_crypto_err("Error in SSL_CTX_ecdh_auto, not enabling ECDHE"); - } -#elif defined(USE_ECDSA) - if(1) { - EC_KEY *ecdh = EC_KEY_new_by_curve_name (NID_X9_62_prime256v1); - if (!ecdh) { - log_crypto_err("could not find p256, not enabling ECDHE"); - } else { - if (1 != SSL_CTX_set_tmp_ecdh (rc->ctx, ecdh)) { - log_crypto_err("Error in SSL_CTX_set_tmp_ecdh, not enabling ECDHE"); - } - EC_KEY_free (ecdh); - } - } -#endif + listen_sslctx_setup_2(rc->ctx); if(!SSL_CTX_load_verify_locations(rc->ctx, s_cert, NULL)) { log_crypto_err("Error setting up SSL_CTX verify locations"); setup_error: @@ -415,7 +367,7 @@ add_open(const char* ip, int nr, struct listen_port** list, int noproto_is_err, if (cfg->username && cfg->username[0] && cfg_uid != (uid_t)-1) { if(chown(ip, cfg_uid, cfg_gid) == -1) - log_err("cannot chown %u.%u %s: %s", + verbose(VERB_QUERY, "cannot chown %u.%u %s: %s", (unsigned)cfg_uid, (unsigned)cfg_gid, ip, strerror(errno)); } @@ -841,7 +793,7 @@ print_stats(SSL* ssl, const char* nm, struct ub_stats_info* s) static int print_thread_stats(SSL* ssl, int i, struct ub_stats_info* s) { - char nm[16]; + char nm[32]; snprintf(nm, sizeof(nm), "thread%d", i); nm[sizeof(nm)-1]=0; return print_stats(ssl, nm, s); @@ -873,6 +825,9 @@ print_mem(SSL* ssl, struct worker* worker, struct daemon* daemon) #ifdef USE_IPSECMOD size_t ipsecmod = 0; #endif /* USE_IPSECMOD */ +#ifdef USE_DNSCRYPT + size_t dnscrypt_shared_secret = 0; +#endif /* USE_DNSCRYPT */ msg = slabhash_get_mem(daemon->env->msg_cache); rrset = slabhash_get_mem(&daemon->env->rrset_cache->table); val = mod_get_mem(&worker->env, "validator"); @@ -884,6 +839,12 @@ print_mem(SSL* ssl, struct worker* worker, struct daemon* daemon) #ifdef USE_IPSECMOD ipsecmod = mod_get_mem(&worker->env, "ipsecmod"); #endif /* USE_IPSECMOD */ +#ifdef USE_DNSCRYPT + if(daemon->dnscenv) { + dnscrypt_shared_secret = slabhash_get_mem( + daemon->dnscenv->shared_secrets_cache); + } +#endif /* USE_DNSCRYPT */ if(!print_longnum(ssl, "mem.cache.rrset"SQ, rrset)) return 0; @@ -903,6 +864,11 @@ print_mem(SSL* ssl, struct worker* worker, struct daemon* daemon) if(!print_longnum(ssl, "mem.mod.ipsecmod"SQ, ipsecmod)) return 0; #endif /* USE_IPSECMOD */ +#ifdef USE_DNSCRYPT + if(!print_longnum(ssl, "mem.cache.dnscrypt_shared_secret"SQ, + dnscrypt_shared_secret)) + return 0; +#endif /* USE_DNSCRYPT */ return 1; } @@ -1065,6 +1031,9 @@ print_ext(SSL* ssl, struct ub_stats_info* s) if(!ssl_printf(ssl, "num.answer.rcode.nodata"SQ"%lu\n", (unsigned long)s->svr.ans_rcode_nodata)) return 0; } + /* iteration */ + if(!ssl_printf(ssl, "num.query.ratelimited"SQ"%lu\n", + (unsigned long)s->svr.queries_ratelimited)) return 0; /* validation */ if(!ssl_printf(ssl, "num.answer.secure"SQ"%lu\n", (unsigned long)s->svr.ans_secure)) return 0; @@ -1086,6 +1055,12 @@ print_ext(SSL* ssl, struct ub_stats_info* s) (unsigned)s->svr.infra_cache_count)) return 0; if(!ssl_printf(ssl, "key.cache.count"SQ"%u\n", (unsigned)s->svr.key_cache_count)) return 0; +#ifdef USE_DNSCRYPT + if(!ssl_printf(ssl, "dnscrypt_shared_secret.cache.count"SQ"%u\n", + (unsigned)s->svr.shared_secret_cache_count)) return 0; + if(!ssl_printf(ssl, "num.query.dnscrypt.shared_secret.cachemiss"SQ"%lu\n", + (unsigned long)s->svr.num_query_dnscrypt_secret_missed_cache)) return 0; +#endif /* USE_DNSCRYPT */ return 1; } @@ -2389,10 +2364,16 @@ dump_infra_host(struct lruhash_entry* e, void* arg) struct infra_data* d = (struct infra_data*)e->data; char ip_str[1024]; char name[257]; + int port; if(a->ssl_failed) return; addr_to_str(&k->addr, k->addrlen, ip_str, sizeof(ip_str)); dname_str(k->zonename, name); + port = (int)ntohs(((struct sockaddr_in*)&k->addr)->sin_port); + if(port != UNBOUND_DNS_PORT) { + snprintf(ip_str+strlen(ip_str), sizeof(ip_str)-strlen(ip_str), + "@%d", port); + } /* skip expired stuff (only backed off) */ if(d->ttl < a->now) { if(d->rtt.rto >= USEFUL_SERVER_TOP_TIMEOUT) { diff --git a/contrib/unbound/daemon/stats.c b/contrib/unbound/daemon/stats.c index 599f39bcddda..1058556be7c2 100644 --- a/contrib/unbound/daemon/stats.c +++ b/contrib/unbound/daemon/stats.c @@ -56,6 +56,7 @@ #include "util/timehist.h" #include "util/net_help.h" #include "validator/validator.h" +#include "iterator/iterator.h" #include "sldns/sbuffer.h" #include "services/cache/rrset.h" #include "services/cache/infra.h" @@ -123,7 +124,7 @@ void server_stats_log(struct ub_server_stats* stats, struct worker* worker, /** get rrsets bogus number from validator */ static size_t -get_rrset_bogus(struct worker* worker) +get_rrset_bogus(struct worker* worker, int reset) { int m = modstack_find(&worker->env.mesh->mods, "validator"); struct val_env* ve; @@ -133,12 +134,48 @@ get_rrset_bogus(struct worker* worker) ve = (struct val_env*)worker->env.modinfo[m]; lock_basic_lock(&ve->bogus_lock); r = ve->num_rrset_bogus; - if(!worker->env.cfg->stat_cumulative) + if(reset && !worker->env.cfg->stat_cumulative) ve->num_rrset_bogus = 0; lock_basic_unlock(&ve->bogus_lock); return r; } +/** get number of ratelimited queries from iterator */ +static size_t +get_queries_ratelimit(struct worker* worker, int reset) +{ + int m = modstack_find(&worker->env.mesh->mods, "iterator"); + struct iter_env* ie; + size_t r; + if(m == -1) + return 0; + ie = (struct iter_env*)worker->env.modinfo[m]; + lock_basic_lock(&ie->queries_ratelimit_lock); + r = ie->num_queries_ratelimited; + if(reset && !worker->env.cfg->stat_cumulative) + ie->num_queries_ratelimited = 0; + lock_basic_unlock(&ie->queries_ratelimit_lock); + return r; +} + +#ifdef USE_DNSCRYPT +/** get the number of shared secret cache miss */ +static size_t +get_dnscrypt_cache_miss(struct worker* worker, int reset) +{ + size_t r; + struct dnsc_env* de = worker->daemon->dnscenv; + if(!de) return 0; + + lock_basic_lock(&de->shared_secrets_cache_lock); + r = de->num_query_dnscrypt_secret_missed_cache; + if(reset && !worker->env.cfg->stat_cumulative) + de->num_query_dnscrypt_secret_missed_cache = 0; + lock_basic_unlock(&de->shared_secrets_cache_lock); + return r; +} +#endif /* USE_DNSCRYPT */ + void server_stats_compile(struct worker* worker, struct ub_stats_info* s, int reset) { @@ -169,7 +206,10 @@ server_stats_compile(struct worker* worker, struct ub_stats_info* s, int reset) s->svr.qtcp_outgoing = (long long)worker->back->num_tcp_outgoing; /* get and reset validator rrset bogus number */ - s->svr.rrset_bogus = (long long)get_rrset_bogus(worker); + s->svr.rrset_bogus = (long long)get_rrset_bogus(worker, reset); + + /* get and reset iterator query ratelimit number */ + s->svr.queries_ratelimited = (long long)get_queries_ratelimit(worker, reset); /* get cache sizes */ s->svr.msg_cache_count = (long long)count_slabhash_entries(worker->env.msg_cache); @@ -179,6 +219,21 @@ server_stats_compile(struct worker* worker, struct ub_stats_info* s, int reset) s->svr.key_cache_count = (long long)count_slabhash_entries(worker->env.key_cache->slab); else s->svr.key_cache_count = 0; +#ifdef USE_DNSCRYPT + if(worker->daemon->dnscenv) { + s->svr.num_query_dnscrypt_secret_missed_cache = + (long long)get_dnscrypt_cache_miss(worker, reset); + s->svr.shared_secret_cache_count = (long long)count_slabhash_entries( + worker->daemon->dnscenv->shared_secrets_cache); + } else { + s->svr.num_query_dnscrypt_secret_missed_cache = 0; + s->svr.shared_secret_cache_count = 0; + } +#else + s->svr.num_query_dnscrypt_secret_missed_cache = 0; + s->svr.shared_secret_cache_count = 0; +#endif /* USE_DNSCRYPT */ + /* get tcp accept usage */ s->svr.tcp_accept_usage = 0; for(lp = worker->front->cps; lp; lp = lp->next) { @@ -240,7 +295,7 @@ void server_stats_add(struct ub_stats_info* total, struct ub_stats_info* a) a->svr.num_query_dnscrypt_cleartext; total->svr.num_query_dnscrypt_crypted_malformed += \ a->svr.num_query_dnscrypt_crypted_malformed; -#endif +#endif /* USE_DNSCRYPT */ /* the max size reached is upped to higher of both */ if(a->svr.max_query_list_size > total->svr.max_query_list_size) total->svr.max_query_list_size = a->svr.max_query_list_size; @@ -266,7 +321,6 @@ void server_stats_add(struct ub_stats_info* total, struct ub_stats_info* a) total->svr.zero_ttl_responses += a->svr.zero_ttl_responses; total->svr.ans_secure += a->svr.ans_secure; total->svr.ans_bogus += a->svr.ans_bogus; - total->svr.rrset_bogus += a->svr.rrset_bogus; total->svr.unwanted_replies += a->svr.unwanted_replies; total->svr.unwanted_queries += a->svr.unwanted_queries; total->svr.tcp_accept_usage += a->svr.tcp_accept_usage; diff --git a/contrib/unbound/daemon/unbound.c b/contrib/unbound/daemon/unbound.c index ba7337d8907a..070a824d6734 100644 --- a/contrib/unbound/daemon/unbound.c +++ b/contrib/unbound/daemon/unbound.c @@ -128,6 +128,9 @@ static void usage(void) for(m = module_list_avail(); *m; m++) printf(" %s", *m); printf("\n"); +#ifdef USE_DNSCRYPT + printf("DNSCrypt feature available\n"); +#endif printf("BSD licensed, see LICENSE in source package for details.\n"); printf("Report bugs to %s\n", PACKAGE_BUGREPORT); ub_event_base_free(base); @@ -400,7 +403,7 @@ detach(void) /** daemonize, drop user priviliges and chroot if needed */ static void perform_setup(struct daemon* daemon, struct config_file* cfg, int debug_mode, - const char** cfgfile) + const char** cfgfile, int need_pidfile) { #ifdef HAVE_KILL int pidinchroot; @@ -444,13 +447,13 @@ perform_setup(struct daemon* daemon, struct config_file* cfg, int debug_mode, #ifdef HAVE_KILL /* true if pidfile is inside chrootdir, or nochroot */ - pidinchroot = !(cfg->chrootdir && cfg->chrootdir[0]) || + pidinchroot = need_pidfile && (!(cfg->chrootdir && cfg->chrootdir[0]) || (cfg->chrootdir && cfg->chrootdir[0] && strncmp(cfg->pidfile, cfg->chrootdir, - strlen(cfg->chrootdir))==0); + strlen(cfg->chrootdir))==0)); /* check old pid file before forking */ - if(cfg->pidfile && cfg->pidfile[0]) { + if(cfg->pidfile && cfg->pidfile[0] && need_pidfile) { /* calculate position of pidfile */ if(cfg->pidfile[0] == '/') daemon->pidfile = strdup(cfg->pidfile); @@ -469,7 +472,7 @@ perform_setup(struct daemon* daemon, struct config_file* cfg, int debug_mode, /* write new pidfile (while still root, so can be outside chroot) */ #ifdef HAVE_KILL - if(cfg->pidfile && cfg->pidfile[0]) { + if(cfg->pidfile && cfg->pidfile[0] && need_pidfile) { writepid(daemon->pidfile, getpid()); if(cfg->username && cfg->username[0] && cfg_uid != (uid_t)-1 && pidinchroot) { @@ -484,6 +487,7 @@ perform_setup(struct daemon* daemon, struct config_file* cfg, int debug_mode, } #else (void)daemon; + (void)need_pidfile; #endif /* HAVE_KILL */ /* Set user context */ @@ -600,9 +604,10 @@ perform_setup(struct daemon* daemon, struct config_file* cfg, int debug_mode, * These increase verbosity as specified in the config file. * @param debug_mode: if set, do not daemonize. * @param log_default_identity: Default identity to report in logs + * @param need_pidfile: if false, no pidfile is checked or created. */ static void -run_daemon(const char* cfgfile, int cmdline_verbose, int debug_mode, const char* log_default_identity) +run_daemon(const char* cfgfile, int cmdline_verbose, int debug_mode, const char* log_default_identity, int need_pidfile) { struct config_file* cfg = NULL; struct daemon* daemon = NULL; @@ -632,7 +637,7 @@ run_daemon(const char* cfgfile, int cmdline_verbose, int debug_mode, const char* if(!daemon_open_shared_ports(daemon)) fatal_exit("could not open ports"); if(!done_setup) { - perform_setup(daemon, cfg, debug_mode, &cfgfile); + perform_setup(daemon, cfg, debug_mode, &cfgfile, need_pidfile); done_setup = 1; } else { /* reopen log after HUP to facilitate log rotation */ @@ -682,6 +687,8 @@ main(int argc, char* argv[]) const char* log_ident_default; int cmdline_verbose = 0; int debug_mode = 0; + int need_pidfile = 1; + #ifdef UB_ON_WINDOWS int cmdline_cfg = 0; #endif @@ -690,7 +697,7 @@ main(int argc, char* argv[]) log_ident_default = strrchr(argv[0],'/')?strrchr(argv[0],'/')+1:argv[0]; log_ident_set(log_ident_default); /* parse the options */ - while( (c=getopt(argc, argv, "c:dhvw:")) != -1) { + while( (c=getopt(argc, argv, "c:dhpvw:")) != -1) { switch(c) { case 'c': cfgfile = optarg; @@ -702,6 +709,9 @@ main(int argc, char* argv[]) cmdline_verbose++; verbosity++; break; + case 'p': + need_pidfile = 0; + break; case 'd': debug_mode++; break; @@ -732,7 +742,7 @@ main(int argc, char* argv[]) return 1; } - run_daemon(cfgfile, cmdline_verbose, debug_mode, log_ident_default); + run_daemon(cfgfile, cmdline_verbose, debug_mode, log_ident_default, need_pidfile); log_init(NULL, 0, NULL); /* close logfile */ return 0; } diff --git a/contrib/unbound/daemon/worker.c b/contrib/unbound/daemon/worker.c index 2c4cf5ba6c0a..683f93169117 100644 --- a/contrib/unbound/daemon/worker.c +++ b/contrib/unbound/daemon/worker.c @@ -1009,6 +1009,7 @@ worker_handle_request(struct comm_point* c, void* arg, int error, struct query_info* lookup_qinfo = &qinfo; struct query_info qinfo_tmp; /* placeholdoer for lookup_qinfo */ struct respip_client_info* cinfo = NULL, cinfo_tmp; + memset(&qinfo, 0, sizeof(qinfo)); if(error != NETEVENT_NOERROR) { /* some bad tcp query DNS formats give these error calls */ @@ -1111,6 +1112,7 @@ worker_handle_request(struct comm_point* c, void* arg, int error, if(!query_info_parse(&qinfo, c->buffer)) { verbose(VERB_ALGO, "worker parse request: formerror."); log_addr(VERB_CLIENT,"from",&repinfo->addr, repinfo->addrlen); + memset(&qinfo, 0, sizeof(qinfo)); /* zero qinfo.qname */ if(worker_err_ratelimit(worker, LDNS_RCODE_FORMERR) == -1) { comm_point_drop_reply(repinfo); return 0; @@ -1355,6 +1357,10 @@ worker_handle_request(struct comm_point* c, void* arg, int error, lock_rw_unlock(&e->lock); regional_free_all(worker->scratchpad); goto send_reply; + } else { + /* Note that we've already released the + * lock if we're here after prefetch. */ + lock_rw_unlock(&e->lock); } /* We've found a partial reply ending with an * alias. Replace the lookup qinfo for the @@ -1362,7 +1368,6 @@ worker_handle_request(struct comm_point* c, void* arg, int error, * (possibly) complete the reply. As we're * passing the "base" reply, there will be no * more alias chasing. */ - lock_rw_unlock(&e->lock); memset(&qinfo_tmp, 0, sizeof(qinfo_tmp)); get_cname_target(alias_rrset, &qinfo_tmp.qname, &qinfo_tmp.qname_len); @@ -1669,7 +1674,17 @@ worker_init(struct worker* worker, struct config_file *cfg, worker->env.send_query = &worker_send_query; worker->env.alloc = &worker->alloc; worker->env.rnd = worker->rndstate; - worker->env.scratch = worker->scratchpad; + /* If case prefetch is triggered, the corresponding mesh will clear + * the scratchpad for the module env in the middle of request handling. + * It would be prone to a use-after-free kind of bug, so we avoid + * sharing it with worker's own scratchpad at the cost of having + * one more pad per worker. */ + worker->env.scratch = regional_create_custom(cfg->msg_buffer_size); + if(!worker->env.scratch) { + log_err("malloc failure"); + worker_delete(worker); + return 0; + } worker->env.mesh = mesh_create(&worker->daemon->mods, &worker->env); worker->env.detach_subs = &mesh_detach_subs; worker->env.attach_sub = &mesh_attach_sub; @@ -1758,6 +1773,7 @@ worker_delete(struct worker* worker) comm_base_delete(worker->base); ub_randfree(worker->rndstate); alloc_clear(&worker->alloc); + regional_destroy(worker->env.scratch); regional_destroy(worker->scratchpad); free(worker); } diff --git a/contrib/unbound/dns64/dns64.c b/contrib/unbound/dns64/dns64.c index b3e3ab852bca..2f2d1255d6ff 100644 --- a/contrib/unbound/dns64/dns64.c +++ b/contrib/unbound/dns64/dns64.c @@ -540,6 +540,7 @@ dns64_operate(struct module_qstate* qstate, enum module_ev event, int id, case module_event_new: /* Tag this query as being new and fall through. */ qstate->minfo[id] = (void*)DNS64_NEW_QUERY; + /* fallthrough */ case module_event_pass: qstate->ext_state[id] = handle_event_pass(qstate, id); break; diff --git a/contrib/unbound/dnscrypt/dnscrypt.c b/contrib/unbound/dnscrypt/dnscrypt.c index 9e858c3fb061..db054df9d680 100644 --- a/contrib/unbound/dnscrypt/dnscrypt.c +++ b/contrib/unbound/dnscrypt/dnscrypt.c @@ -12,6 +12,8 @@ #include "util/net_help.h" #include "util/netevent.h" #include "util/log.h" +#include "util/storage/slabhash.h" +#include "util/storage/lookup3.h" #include "dnscrypt/cert.h" #include "dnscrypt/dnscrypt.h" @@ -19,13 +21,15 @@ #include + /** * \file * dnscrypt functions for encrypting DNS packets. */ #define DNSCRYPT_QUERY_BOX_OFFSET \ - (DNSCRYPT_MAGIC_HEADER_LEN + crypto_box_PUBLICKEYBYTES + crypto_box_HALF_NONCEBYTES) + (DNSCRYPT_MAGIC_HEADER_LEN + crypto_box_PUBLICKEYBYTES + \ + crypto_box_HALF_NONCEBYTES) // 8 bytes: magic header (CERT_MAGIC_HEADER) // 12 bytes: the client's nonce @@ -33,13 +37,110 @@ // 16 bytes: Poly1305 MAC (crypto_box_ZEROBYTES - crypto_box_BOXZEROBYTES) #define DNSCRYPT_REPLY_BOX_OFFSET \ - (DNSCRYPT_MAGIC_HEADER_LEN + crypto_box_HALF_NONCEBYTES + crypto_box_HALF_NONCEBYTES) + (DNSCRYPT_MAGIC_HEADER_LEN + crypto_box_HALF_NONCEBYTES + \ + crypto_box_HALF_NONCEBYTES) + + +/** + * Shared secret cache key length. + * secret key. + * 1 byte: ES_VERSION[1] + * 32 bytes: client crypto_box_PUBLICKEYBYTES + * 32 bytes: server crypto_box_SECRETKEYBYTES + */ +#define DNSCRYPT_SHARED_SECRET_KEY_LENGTH \ + (1 + crypto_box_PUBLICKEYBYTES + crypto_box_SECRETKEYBYTES) + + +struct shared_secret_cache_key { + /** the hash table key */ + uint8_t key[DNSCRYPT_SHARED_SECRET_KEY_LENGTH]; + /** the hash table entry, data is uint8_t pointer of size crypto_box_BEFORENMBYTES which contains the shared secret. */ + struct lruhash_entry entry; +}; + + +/** + * Generate a key suitable to find shared secret in slabhash. + * \param[in] key: a uint8_t pointer of size DNSCRYPT_SHARED_SECRET_KEY_LENGTH + * \param[in] esversion: The es version least significant byte. + * \param[in] pk: The public key of the client. uint8_t pointer of size + * crypto_box_PUBLICKEYBYTES. + * \param[in] sk: The secret key of the server matching the magic query number. + * uint8_t pointer of size crypto_box_SECRETKEYBYTES. + * \return the hash of the key. + */ +static uint32_t +dnsc_shared_secrets_cache_key(uint8_t* key, + uint8_t esversion, + uint8_t* pk, + uint8_t* sk) +{ + key[0] = esversion; + memcpy(key + 1, pk, crypto_box_PUBLICKEYBYTES); + memcpy(key + 1 + crypto_box_PUBLICKEYBYTES, sk, crypto_box_SECRETKEYBYTES); + return hashlittle(key, DNSCRYPT_SHARED_SECRET_KEY_LENGTH, 0); +} + +/** + * Inserts a shared secret into the shared_secrets_cache slabhash. + * The shared secret is copied so the caller can use it freely without caring + * about the cache entry being evicted or not. + * \param[in] cache: the slabhash in which to look for the key. + * \param[in] key: a uint8_t pointer of size DNSCRYPT_SHARED_SECRET_KEY_LENGTH + * which contains the key of the shared secret. + * \param[in] hash: the hash of the key. + * \param[in] nmkey: a uint8_t pointer of size crypto_box_BEFORENMBYTES which + * contains the shared secret. + */ +static void +dnsc_shared_secret_cache_insert(struct slabhash *cache, + uint8_t key[DNSCRYPT_SHARED_SECRET_KEY_LENGTH], + uint32_t hash, + uint8_t nmkey[crypto_box_BEFORENMBYTES]) +{ + struct shared_secret_cache_key* k = + (struct shared_secret_cache_key*)calloc(1, sizeof(*k)); + uint8_t* d = malloc(crypto_box_BEFORENMBYTES); + if(!k || !d) { + free(k); + free(d); + return; + } + memcpy(d, nmkey, crypto_box_BEFORENMBYTES); + lock_rw_init(&k->entry.lock); + memcpy(k->key, key, DNSCRYPT_SHARED_SECRET_KEY_LENGTH); + k->entry.hash = hash; + k->entry.key = k; + k->entry.data = d; + slabhash_insert(cache, + hash, &k->entry, + d, + NULL); +} + +/** + * Lookup a record in shared_secrets_cache. + * \param[in] cache: a pointer to shared_secrets_cache slabhash. + * \param[in] key: a uint8_t pointer of size DNSCRYPT_SHARED_SECRET_KEY_LENGTH + * containing the key to look for. + * \param[in] hash: a hash of the key. + * \return a pointer to the locked cache entry or NULL on failure. + */ +static struct lruhash_entry* +dnsc_shared_secrets_lookup(struct slabhash* cache, + uint8_t key[DNSCRYPT_SHARED_SECRET_KEY_LENGTH], + uint32_t hash) +{ + return slabhash_lookup(cache, hash, key, 0); +} /** * Decrypt a query using the dnsccert that was found using dnsc_find_cert. * The client nonce will be extracted from the encrypted query and stored in * client_nonce, a shared secret will be computed and stored in nmkey and the * buffer will be decrypted inplace. + * \param[in] env the dnscrypt environment. * \param[in] cert the cert that matches this encrypted query. * \param[in] client_nonce where the client nonce will be stored. * \param[in] nmkey where the shared secret key will be written. @@ -47,7 +148,8 @@ * \return 0 on success. */ static int -dnscrypt_server_uncurve(const dnsccert *cert, +dnscrypt_server_uncurve(struct dnsc_env* env, + const dnsccert *cert, uint8_t client_nonce[crypto_box_HALF_NONCEBYTES], uint8_t nmkey[crypto_box_BEFORENMBYTES], struct sldns_buffer* buffer) @@ -56,27 +158,55 @@ dnscrypt_server_uncurve(const dnsccert *cert, uint8_t *const buf = sldns_buffer_begin(buffer); uint8_t nonce[crypto_box_NONCEBYTES]; struct dnscrypt_query_header *query_header; + // shared secret cache + uint8_t key[DNSCRYPT_SHARED_SECRET_KEY_LENGTH]; + struct lruhash_entry* entry; + uint32_t hash; if (len <= DNSCRYPT_QUERY_HEADER_SIZE) { return -1; } query_header = (struct dnscrypt_query_header *)buf; - memcpy(nmkey, query_header->publickey, crypto_box_PUBLICKEYBYTES); - if(cert->es_version[1] == 2) { + hash = dnsc_shared_secrets_cache_key(key, + cert->es_version[1], + query_header->publickey, + cert->keypair->crypt_secretkey); + entry = dnsc_shared_secrets_lookup(env->shared_secrets_cache, + key, + hash); + + if(!entry) { + lock_basic_lock(&env->shared_secrets_cache_lock); + env->num_query_dnscrypt_secret_missed_cache++; + lock_basic_unlock(&env->shared_secrets_cache_lock); + if(cert->es_version[1] == 2) { #ifdef USE_DNSCRYPT_XCHACHA20 - if (crypto_box_curve25519xchacha20poly1305_beforenm( - nmkey, nmkey, cert->keypair->crypt_secretkey) != 0) { - return -1; - } + if (crypto_box_curve25519xchacha20poly1305_beforenm( + nmkey, query_header->publickey, + cert->keypair->crypt_secretkey) != 0) { + return -1; + } #else - return -1; + return -1; #endif } else { - if (crypto_box_beforenm(nmkey, nmkey, cert->keypair->crypt_secretkey) != 0) { + if (crypto_box_beforenm(nmkey, + query_header->publickey, + cert->keypair->crypt_secretkey) != 0) { return -1; } } + // Cache the shared secret we just computed. + dnsc_shared_secret_cache_insert(env->shared_secrets_cache, + key, + hash, + nmkey); + } else { + /* copy shared secret and unlock entry */ + memcpy(nmkey, entry->data, crypto_box_BEFORENMBYTES); + lock_rw_unlock(&entry->lock); + } memcpy(nonce, query_header->nonce, crypto_box_HALF_NONCEBYTES); memset(nonce + crypto_box_HALF_NONCEBYTES, 0, crypto_box_HALF_NONCEBYTES); @@ -106,7 +236,7 @@ dnscrypt_server_uncurve(const dnsccert *cert, len -= DNSCRYPT_QUERY_HEADER_SIZE; while (*sldns_buffer_at(buffer, --len) == 0) - ; + ; if (*sldns_buffer_at(buffer, len) != 0x80) { return -1; @@ -172,7 +302,7 @@ dnscrypt_hrtime(void) if (ret == 0) { ts = (uint64_t)tv.tv_sec * 1000000U + (uint64_t)tv.tv_usec; } else { - log_err("gettimeofday: %s", strerror(errno)); + log_err("gettimeofday: %s", strerror(errno)); } return ts; } @@ -223,7 +353,8 @@ dnscrypt_server_curve(const dnsccert *cert, size_t max_udp_size) { size_t dns_reply_len = sldns_buffer_limit(buffer); - size_t max_len = dns_reply_len + DNSCRYPT_MAX_PADDING + DNSCRYPT_REPLY_HEADER_SIZE; + size_t max_len = dns_reply_len + DNSCRYPT_MAX_PADDING \ + + DNSCRYPT_REPLY_HEADER_SIZE; size_t max_reply_size = max_udp_size - 20U - 8U; uint8_t nonce[crypto_box_NONCEBYTES]; uint8_t *boxed; @@ -268,8 +399,14 @@ dnscrypt_server_curve(const dnsccert *cert, } } - sldns_buffer_write_at(buffer, 0, DNSCRYPT_MAGIC_RESPONSE, DNSCRYPT_MAGIC_HEADER_LEN); - sldns_buffer_write_at(buffer, DNSCRYPT_MAGIC_HEADER_LEN, nonce, crypto_box_NONCEBYTES); + sldns_buffer_write_at(buffer, + 0, + DNSCRYPT_MAGIC_RESPONSE, + DNSCRYPT_MAGIC_HEADER_LEN); + sldns_buffer_write_at(buffer, + DNSCRYPT_MAGIC_HEADER_LEN, + nonce, + crypto_box_NONCEBYTES); sldns_buffer_set_limit(buffer, len + DNSCRYPT_REPLY_HEADER_SIZE); return 0; } @@ -284,17 +421,17 @@ dnscrypt_server_curve(const dnsccert *cert, static int dnsc_read_from_file(char *fname, char *buf, size_t count) { - int fd; - fd = open(fname, O_RDONLY); - if (fd == -1) { - return -1; - } - if (read(fd, buf, count) != (ssize_t)count) { - close(fd); - return -2; - } - close(fd); - return 0; + int fd; + fd = open(fname, O_RDONLY); + if (fd == -1) { + return -1; + } + if (read(fd, buf, count) != (ssize_t)count) { + close(fd); + return -2; + } + close(fd); + return 0; } /** @@ -308,12 +445,12 @@ dnsc_read_from_file(char *fname, char *buf, size_t count) static char * dnsc_chroot_path(struct config_file *cfg, char *path) { - char *nm; - nm = path; - if(cfg->chrootdir && cfg->chrootdir[0] && strncmp(nm, - cfg->chrootdir, strlen(cfg->chrootdir)) == 0) - nm += strlen(cfg->chrootdir); - return nm; + char *nm; + nm = path; + if(cfg->chrootdir && cfg->chrootdir[0] && strncmp(nm, + cfg->chrootdir, strlen(cfg->chrootdir)) == 0) + nm += strlen(cfg->chrootdir); + return nm; } /** @@ -379,7 +516,7 @@ dnsc_key_to_fingerprint(char fingerprint[80U], const uint8_t * const key) /** * Find the cert matching a DNSCrypt query. - * \param[in] dnscenv The DNSCrypt enviroment, which contains the list of certs + * \param[in] dnscenv The DNSCrypt environment, which contains the list of certs * supported by the server. * \param[in] buffer The encrypted DNS query. * \return a dnsccert * if we found a cert matching the magic_number of the @@ -450,6 +587,7 @@ dnsc_load_local_data(struct dnsc_env* dnscenv, struct config_file *cfg) snprintf(rr + strlen(rr), rrlen - 1 - strlen(rr), "\\%03d", c); } } + verbose(VERB_OPS, "DNSCrypt: adding local data to config: %s", rr); snprintf(rr + strlen(rr), rrlen - 1 - strlen(rr), "\""); cfg_strlist_insert(&cfg->local_data, strdup(rr)); free(rr); @@ -502,7 +640,7 @@ dnsc_parse_keys(struct dnsc_env *env, struct config_file *cfg) env->keypairs = sodium_allocarray(env->keypairs_count, sizeof *env->keypairs); - env->certs = sodium_allocarray(env->signed_certs_count, + env->certs = sodium_allocarray(env->signed_certs_count, sizeof *env->certs); cert_id = 0U; @@ -584,7 +722,8 @@ dnsc_handle_curved_request(struct dnsc_env* dnscenv, // to serve the certificate. verbose(VERB_ALGO, "handle request called on DNSCrypt socket"); if ((repinfo->dnsc_cert = dnsc_find_cert(dnscenv, c->buffer)) != NULL) { - if(dnscrypt_server_uncurve(repinfo->dnsc_cert, + if(dnscrypt_server_uncurve(dnscenv, + repinfo->dnsc_cert, repinfo->client_nonce, repinfo->nmkey, c->buffer) != 0){ @@ -629,23 +768,93 @@ dnsc_create(void) fatal_exit("dnsc_create: could not initialize libsodium."); } env = (struct dnsc_env *) calloc(1, sizeof(struct dnsc_env)); + lock_basic_init(&env->shared_secrets_cache_lock); + lock_protect(&env->shared_secrets_cache_lock, + &env->num_query_dnscrypt_secret_missed_cache, + sizeof(env->num_query_dnscrypt_secret_missed_cache)); return env; } int dnsc_apply_cfg(struct dnsc_env *env, struct config_file *cfg) { - if(dnsc_parse_certs(env, cfg) <= 0) { - fatal_exit("dnsc_apply_cfg: no cert file loaded"); - } - if(dnsc_parse_keys(env, cfg) <= 0) { - fatal_exit("dnsc_apply_cfg: no key file loaded"); - } - randombytes_buf(env->hash_key, sizeof env->hash_key); - env->provider_name = cfg->dnscrypt_provider; + if(dnsc_parse_certs(env, cfg) <= 0) { + fatal_exit("dnsc_apply_cfg: no cert file loaded"); + } + if(dnsc_parse_keys(env, cfg) <= 0) { + fatal_exit("dnsc_apply_cfg: no key file loaded"); + } + randombytes_buf(env->hash_key, sizeof env->hash_key); + env->provider_name = cfg->dnscrypt_provider; - if(dnsc_load_local_data(env, cfg) <= 0) { - fatal_exit("dnsc_apply_cfg: could not load local data"); - } - return 0; + if(dnsc_load_local_data(env, cfg) <= 0) { + fatal_exit("dnsc_apply_cfg: could not load local data"); + } + env->shared_secrets_cache = slabhash_create( + cfg->dnscrypt_shared_secret_cache_slabs, + HASH_DEFAULT_STARTARRAY, + cfg->dnscrypt_shared_secret_cache_size, + dnsc_shared_secrets_sizefunc, + dnsc_shared_secrets_compfunc, + dnsc_shared_secrets_delkeyfunc, + dnsc_shared_secrets_deldatafunc, + NULL + ); + if(!env->shared_secrets_cache){ + fatal_exit("dnsc_apply_cfg: could not create shared secrets cache."); + } + return 0; +} + +void +dnsc_delete(struct dnsc_env *env) +{ + if(!env) { + return; + } + verbose(VERB_OPS, "DNSCrypt: Freeing environment."); + sodium_free(env->signed_certs); + sodium_free(env->certs); + sodium_free(env->keypairs); + slabhash_delete(env->shared_secrets_cache); + lock_basic_destroy(&env->shared_secrets_cache_lock); + free(env); +} + +/** + * ######################################################### + * ############# Shared secrets cache functions ############ + * ######################################################### + */ + +size_t +dnsc_shared_secrets_sizefunc(void *k, void* ATTR_UNUSED(d)) +{ + struct shared_secret_cache_key* ssk = (struct shared_secret_cache_key*)k; + size_t key_size = sizeof(struct shared_secret_cache_key) + + lock_get_mem(&ssk->entry.lock); + size_t data_size = crypto_box_BEFORENMBYTES; + (void)ssk; /* otherwise ssk is unused if no threading, or fixed locksize */ + return key_size + data_size; +} + +int +dnsc_shared_secrets_compfunc(void *m1, void *m2) +{ + return sodium_memcmp(m1, m2, DNSCRYPT_SHARED_SECRET_KEY_LENGTH); +} + +void +dnsc_shared_secrets_delkeyfunc(void *k, void* ATTR_UNUSED(arg)) +{ + struct shared_secret_cache_key* ssk = (struct shared_secret_cache_key*)k; + lock_rw_destroy(&ssk->entry.lock); + free(ssk); +} + +void +dnsc_shared_secrets_deldatafunc(void* d, void* ATTR_UNUSED(arg)) +{ + uint8_t* data = (uint8_t*)d; + free(data); } diff --git a/contrib/unbound/dnscrypt/dnscrypt.h b/contrib/unbound/dnscrypt/dnscrypt.h index 26c2bb21d6b6..dde36d6675d1 100644 --- a/contrib/unbound/dnscrypt/dnscrypt.h +++ b/contrib/unbound/dnscrypt/dnscrypt.h @@ -26,6 +26,7 @@ #include "config.h" #include "dnscrypt/cert.h" +#include "util/locks.h" #define DNSCRYPT_QUERY_HEADER_SIZE \ (DNSCRYPT_MAGIC_HEADER_LEN + crypto_box_PUBLICKEYBYTES + crypto_box_HALF_NONCEBYTES + crypto_box_MACBYTES) @@ -38,6 +39,7 @@ struct sldns_buffer; struct config_file; struct comm_reply; +struct slabhash; typedef struct KeyPair_ { uint8_t crypt_publickey[crypto_box_PUBLICKEYBYTES]; @@ -52,7 +54,7 @@ typedef struct cert_ { struct dnsc_env { struct SignedCert *signed_certs; - dnsccert *certs; + dnsccert *certs; size_t signed_certs_count; uint8_t provider_publickey[crypto_sign_ed25519_PUBLICKEYBYTES]; uint8_t provider_secretkey[crypto_sign_ed25519_SECRETKEYBYTES]; @@ -61,6 +63,11 @@ struct dnsc_env { uint64_t nonce_ts_last; unsigned char hash_key[crypto_shorthash_KEYBYTES]; char * provider_name; + struct slabhash *shared_secrets_cache; + /** lock on shared secret cache counters */ + lock_basic_type shared_secrets_cache_lock; + /** number of misses from shared_secrets_cache */ + size_t num_query_dnscrypt_secret_missed_cache; }; struct dnscrypt_query_header { @@ -71,7 +78,7 @@ struct dnscrypt_query_header { }; /** - * Initialize DNSCrypt enviroment. + * Initialize DNSCrypt environment. * Initialize sodium library and allocate the dnsc_env structure. * \return an uninitialized struct dnsc_env. */ @@ -88,6 +95,12 @@ struct dnsc_env * dnsc_create(void); */ int dnsc_apply_cfg(struct dnsc_env *env, struct config_file *cfg); +/** + * Delete DNSCrypt environment + * + */ +void dnsc_delete(struct dnsc_env *env); + /** * handle a crypted dnscrypt request. * Determine wether or not a query is coming over the dnscrypt listener and @@ -105,5 +118,26 @@ int dnsc_handle_curved_request(struct dnsc_env* dnscenv, */ int dnsc_handle_uncurved_request(struct comm_reply *repinfo); + +/** + * Computes the size of the shared secret cache entry. + */ +size_t dnsc_shared_secrets_sizefunc(void *k, void *d); + +/** + * Compares two shared secret cache keys. + */ +int dnsc_shared_secrets_compfunc(void *m1, void *m2); + +/** + * Function to delete a shared secret cache key. + */ +void dnsc_shared_secrets_delkeyfunc(void *k, void* arg); + +/** + * Function to delete a share secret cache value. + */ +void dnsc_shared_secrets_deldatafunc(void* d, void* arg); + #endif /* USE_DNSCRYPT */ #endif diff --git a/contrib/unbound/dnscrypt/dnscrypt_config.h b/contrib/unbound/dnscrypt/dnscrypt_config.h new file mode 100644 index 000000000000..0d77a0c918e7 --- /dev/null +++ b/contrib/unbound/dnscrypt/dnscrypt_config.h @@ -0,0 +1,17 @@ +#ifndef UNBOUND_DNSCRYPT_CONFIG_H +#define UNBOUND_DNSCRYPT_CONFIG_H + +/* + * Process this file (dnscrypt_config.h.in) with AC_CONFIG_FILES to generate + * dnscrypt_config.h. + * + * This file exists so that USE_DNSCRYPT can be used without including config.h. + */ + +#if 0 /* ENABLE_DNSCRYPT */ +# ifndef USE_DNSCRYPT +# define USE_DNSCRYPT 1 +# endif +#endif + +#endif /* UNBOUND_DNSCRYPT_CONFIG_H */ diff --git a/contrib/unbound/doc/Changelog b/contrib/unbound/doc/Changelog index a72f99606e13..39a3a2b7f4aa 100644 --- a/contrib/unbound/doc/Changelog +++ b/contrib/unbound/doc/Changelog @@ -1,8 +1,150 @@ -21 Aug 2017: Wouter +13 September 2017: Wouter + - tag 1.6.6rc2 + +12 September 2017: Wouter + - Add dns64 for client-subnet in unbound-checkconf. + +4 September 2017: Ralph + - Fix #1412: QNAME minimisation strict mode not honored + - Fix #1434: Fix windows openssl 1.1.0 linking. + +4 September 2017: Wouter + - tag 1.6.6rc1 + - makedist fix for windows binaries, with openssl 1.1.0 windres fix, + and expat 2.2.4 install target fix. + +1 September 2017: Wouter + - Recommend 1472 buffer size in unbound.conf + +31 August 2017: Wouter + - Fix #1424: cachedb:testframe is not thread safe. + - For #1417: escape ; in dnscrypt tests. + - but reverted that, tests fails with that escape. + - Fix #1417: [dnscrypt] shared secret cache counters, and works when + dnscrypt is not enabled. And cache size configuration option. + - make depend + - Fix #1418: [ip ratelimit] initialize slabhash using + ip-ratelimit-slabs. + +30 August 2017: Wouter + - updated contrib/fastrpz.patch to apply with configparser changes. + - Fix 1416: qname-minimisation breaks TLSA lookups with CNAMEs. + +29 August 2017: Wouter + - Fix #1414: fix segfault on parse failure and log_replies. + - zero qinfo in handle_request, this zeroes local_alias and also the + qname member. + - new keys and certs for dnscrypt tests. + - fixup WKS test on buildhost without servicebyname. + +28 August 2017: Wouter + - Fix #1415: patch to free dnscrypt environment on reload. + - iana portlist update + - Fix #1415: [dnscrypt] shared secret cache, patch from + Manu Bretelle. + - Small fixes for the shared secret cache patch. + - Fix WKS records on kvm autobuild host, with default protobyname + entries for udp and tcp. + +23 August 2017: Wouter + - Fix #1407: Add ECS options check to unbound-checkconf. + - make depend + - Fix to reclaim tcp handler when it is closed due to dnscrypt buffer + allocation failure. + +22 August 2017: Wouter - Fix install of trust anchor when two anchors are present, makes both - valid. Checks hash of DS but not signature of new key. This fixes - installs between sep11 and oct11 2017. - - Tag 1.6.5 + valid. Checks hash of DS but not signature of new key. This fixes + the root.key file if created when unbound is installed between + sep11 and oct11 2017. + - tag 1.6.5 with pointrelease 1.6.5 (1.6.4 plus 5011 fix). + - trunk version 1.6.6 in development. + - Fix issue on macOX 10.10 where TCP fast open is detected but not + implemented causing TCP to fail. The fix allows fallback to regular + TCP in this case and is also more robust for cases where connectx() + fails for some reason. + - Fix #1402: squelch invalid argument error for fd_set_block on windows. + +10 August 2017: Wouter + - Patch to show DNSCrypt status in help output, from Carsten + Strotmann. + +8 August 2017: Wouter + - Fix #1398: make cachedb secret configurable. + - Remove spaces from Makefile. + +7 August 2017: Wouter + - Fix #1397: Recursive DS lookups for AS112 zones names should recurse. + +3 August 2017: Ralph + - Remove unused iter_env member (ip6arpa_dname) + - Do not reset rrset.bogus stats when called using stats_noreset. + - Added stats for queries that have been ratelimited by domain + recursion. + - Do not add rrset_bogus and query ratelimiting stats per thread, these + module stats are global. + +3 August 2017: Wouter + - Fix #1394: mix of serve-expired and response-ip could cause a crash. + +24 July 2017: Wouter + - upgrade aclocal(pkg.m4 0.29.1), config.guess(2016-10-02), + config.sub(2016-09-05). + - annotate case statement fallthrough for gcc 7.1.1. + - flex output from flex 2.6.1. + - snprintf of thread number does not warn about truncated string. + - squelch TCP fast open error on FreeBSD when kernel has it disabled, + unless verbosity is high. + - remove warning from windows compile. + - Fix compile with libnettle + - Fix DSA configure switch (--disable dsa) for libnettle and libnss. + - Fix #1365: Add Ed25519 support using libnettle. + - iana portlist update + +17 July 2017: Wouter + - Fix #1350: make cachedb backend configurable (from JINMEI Tatuya). + - Fix #1349: allow suppression of pidfiles (from Daniel Kahn Gillmor). + With the -p option unbound does not create a pidfile. + +11 July 2017: Wouter + - Fix #1344: RFC6761-reserved domains: test. and invalid. + - Redirect all localhost names to localhost address for RFC6761. + +6 July 2017: Wouter + - Fix tests to use .tdir (from Manu Bretelle) instead of .tpkg. + - Fix svn hooks for tdir (selected if testcode/mini_tdir.sh exists).. + +4 July 2017: Wouter + - Fix 1332: Bump verbosity of failed chown'ing of the control socket. + +3 July 2017: Wouter + - Fix for unbound-checkconf, check ipsecmod-hook if ipsecmod is turned + on. + - Fix #1331: libunbound segfault in threaded mode when context is + deleted. + - Fix pythonmod link line option flag. + - Fix openssl 1.1.0 load of ssl error strings from ssl init. + +29 June 2017: Wouter + - Fix python example0 return module wait instead of error for pass. + - iana portlist update + - enhancement for hardened-tls for DNS over TLS. Removed duplicated + security settings. + +27 June 2017: Wouter + - Tag 1.6.4 is created with the 1.6.4rc2 contents. + - Trunk contains 1.6.5, with changes from 26, 27 june. + - Remove signed unsigned warning from authzone. + - Fix that infra cache host hash does not change after reconfig. + +26 June 2017: Wouter + - (for 1.6.5) + Better fixup of dnscrypt_cert_chacha test for different escapes. + - First fix for zero b64 and hex text zone format in sldns. + - unbound-control dump_infra prints port number for address if not 53. + +23 June 2017: Wouter + - (for 1.6.5): fixup of dnscrypt_cert_chacha test (from Manu Bretelle). 22 June 2017: Wouter - Tag 1.6.4rc2 diff --git a/contrib/unbound/doc/README b/contrib/unbound/doc/README index 6c4b28537703..d0c0bf34f3fb 100644 --- a/contrib/unbound/doc/README +++ b/contrib/unbound/doc/README @@ -1,4 +1,4 @@ -README for Unbound 1.6.5 +README for Unbound 1.6.6 Copyright 2007 NLnet Labs http://unbound.net diff --git a/contrib/unbound/doc/example.conf b/contrib/unbound/doc/example.conf index c5a3c585bbc1..175589e881c0 100644 --- a/contrib/unbound/doc/example.conf +++ b/contrib/unbound/doc/example.conf @@ -1,7 +1,7 @@ # # Example configuration file. # -# See unbound.conf(5) man page, version 1.6.4. +# See unbound.conf(5) man page, version 1.6.6. # # this is a comment. @@ -116,7 +116,7 @@ server: # ip-freebind: no # EDNS reassembly buffer to advertise to UDP peers (the actual buffer - # is set with msg-buffer-size). 1480 can solve fragmentation (timeouts). + # is set with msg-buffer-size). 1472 can solve fragmentation (timeouts) # edns-buffer-size: 4096 # Maximum UDP response size (not applied to TCP response). @@ -563,6 +563,8 @@ server: # local-zone: "127.in-addr.arpa." nodefault # local-zone: "1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa." nodefault # local-zone: "onion." nodefault + # local-zone: "test." nodefault + # local-zone: "invalid." nodefault # local-zone: "10.in-addr.arpa." nodefault # local-zone: "16.172.in-addr.arpa." nodefault # local-zone: "17.172.in-addr.arpa." nodefault @@ -838,3 +840,13 @@ remote-control: # dnscrypt-secret-key: /path/unbound-conf/keys2/1.key # dnscrypt-provider-cert: /path/unbound-conf/keys1/1.cert # dnscrypt-provider-cert: /path/unbound-conf/keys2/1.cert + +# CacheDB +# Enable external backend DB as auxiliary cache. Specify the backend name +# (default is "testframe", which has no use other than for debugging and +# testing) and backend-specific options. The 'cachedb' module must be +# included in module-config. +# cachedb: +# backend: "testframe" +# # secret seed string to calculate hashed keys +# secret-seed: "default" diff --git a/contrib/unbound/doc/example.conf.in b/contrib/unbound/doc/example.conf.in index 481f2e0c214b..e7978b79c898 100644 --- a/contrib/unbound/doc/example.conf.in +++ b/contrib/unbound/doc/example.conf.in @@ -1,7 +1,7 @@ # # Example configuration file. # -# See unbound.conf(5) man page, version 1.6.5. +# See unbound.conf(5) man page, version 1.6.6. # # this is a comment. @@ -116,7 +116,7 @@ server: # ip-freebind: no # EDNS reassembly buffer to advertise to UDP peers (the actual buffer - # is set with msg-buffer-size). 1480 can solve fragmentation (timeouts). + # is set with msg-buffer-size). 1472 can solve fragmentation (timeouts) # edns-buffer-size: 4096 # Maximum UDP response size (not applied to TCP response). @@ -563,6 +563,8 @@ server: # local-zone: "127.in-addr.arpa." nodefault # local-zone: "1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa." nodefault # local-zone: "onion." nodefault + # local-zone: "test." nodefault + # local-zone: "invalid." nodefault # local-zone: "10.in-addr.arpa." nodefault # local-zone: "16.172.in-addr.arpa." nodefault # local-zone: "17.172.in-addr.arpa." nodefault @@ -838,3 +840,13 @@ remote-control: # dnscrypt-secret-key: /path/unbound-conf/keys2/1.key # dnscrypt-provider-cert: /path/unbound-conf/keys1/1.cert # dnscrypt-provider-cert: /path/unbound-conf/keys2/1.cert + +# CacheDB +# Enable external backend DB as auxiliary cache. Specify the backend name +# (default is "testframe", which has no use other than for debugging and +# testing) and backend-specific options. The 'cachedb' module must be +# included in module-config. +# cachedb: +# backend: "testframe" +# # secret seed string to calculate hashed keys +# secret-seed: "default" diff --git a/contrib/unbound/doc/libunbound.3 b/contrib/unbound/doc/libunbound.3 index bcd79ffcaff4..fbf3cd832af6 100644 --- a/contrib/unbound/doc/libunbound.3 +++ b/contrib/unbound/doc/libunbound.3 @@ -1,4 +1,4 @@ -.TH "libunbound" "3" "Jun 27, 2017" "NLnet Labs" "unbound 1.6.4" +.TH "libunbound" "3" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" libunbound.3 -- unbound library functions manual .\" @@ -43,7 +43,7 @@ .B ub_ctx_zone_remove, .B ub_ctx_data_add, .B ub_ctx_data_remove -\- Unbound DNS validating resolver 1.6.4 functions. +\- Unbound DNS validating resolver 1.6.6 functions. .SH "SYNOPSIS" .B #include .LP diff --git a/contrib/unbound/doc/libunbound.3.in b/contrib/unbound/doc/libunbound.3.in index 40f3ba20def5..fbf3cd832af6 100644 --- a/contrib/unbound/doc/libunbound.3.in +++ b/contrib/unbound/doc/libunbound.3.in @@ -1,4 +1,4 @@ -.TH "libunbound" "3" "Aug 21, 2017" "NLnet Labs" "unbound 1.6.5" +.TH "libunbound" "3" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" libunbound.3 -- unbound library functions manual .\" @@ -43,7 +43,7 @@ .B ub_ctx_zone_remove, .B ub_ctx_data_add, .B ub_ctx_data_remove -\- Unbound DNS validating resolver 1.6.5 functions. +\- Unbound DNS validating resolver 1.6.6 functions. .SH "SYNOPSIS" .B #include .LP diff --git a/contrib/unbound/doc/unbound-anchor.8 b/contrib/unbound/doc/unbound-anchor.8 index 6e5e16a8a72f..c8ee77e2c074 100644 --- a/contrib/unbound/doc/unbound-anchor.8 +++ b/contrib/unbound/doc/unbound-anchor.8 @@ -1,4 +1,4 @@ -.TH "unbound-anchor" "8" "Jun 27, 2017" "NLnet Labs" "unbound 1.6.4" +.TH "unbound-anchor" "8" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound-anchor.8 -- unbound anchor maintenance utility manual .\" diff --git a/contrib/unbound/doc/unbound-anchor.8.in b/contrib/unbound/doc/unbound-anchor.8.in index 8436c3cd5f5e..a008e0c0e262 100644 --- a/contrib/unbound/doc/unbound-anchor.8.in +++ b/contrib/unbound/doc/unbound-anchor.8.in @@ -1,4 +1,4 @@ -.TH "unbound-anchor" "8" "Aug 21, 2017" "NLnet Labs" "unbound 1.6.5" +.TH "unbound-anchor" "8" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound-anchor.8 -- unbound anchor maintenance utility manual .\" diff --git a/contrib/unbound/doc/unbound-checkconf.8 b/contrib/unbound/doc/unbound-checkconf.8 index 6635f7a13119..2c0278ea1b27 100644 --- a/contrib/unbound/doc/unbound-checkconf.8 +++ b/contrib/unbound/doc/unbound-checkconf.8 @@ -1,4 +1,4 @@ -.TH "unbound-checkconf" "8" "Jun 27, 2017" "NLnet Labs" "unbound 1.6.4" +.TH "unbound-checkconf" "8" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound-checkconf.8 -- unbound configuration checker manual .\" diff --git a/contrib/unbound/doc/unbound-checkconf.8.in b/contrib/unbound/doc/unbound-checkconf.8.in index 9778ebddee16..2e38e76b9979 100644 --- a/contrib/unbound/doc/unbound-checkconf.8.in +++ b/contrib/unbound/doc/unbound-checkconf.8.in @@ -1,4 +1,4 @@ -.TH "unbound-checkconf" "8" "Aug 21, 2017" "NLnet Labs" "unbound 1.6.5" +.TH "unbound-checkconf" "8" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound-checkconf.8 -- unbound configuration checker manual .\" diff --git a/contrib/unbound/doc/unbound-control.8 b/contrib/unbound/doc/unbound-control.8 index 453259f5504a..c30f32f64eae 100644 --- a/contrib/unbound/doc/unbound-control.8 +++ b/contrib/unbound/doc/unbound-control.8 @@ -1,4 +1,4 @@ -.TH "unbound-control" "8" "Jun 27, 2017" "NLnet Labs" "unbound 1.6.4" +.TH "unbound-control" "8" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound-control.8 -- unbound remote control manual .\" @@ -493,6 +493,10 @@ number of queries that had an EDNS OPT record present. number of queries that had an EDNS OPT record with the DO (DNSSEC OK) bit set. These queries are also included in the num.query.edns.present number. .TP +.I num.query.ratelimited +The number of queries that are turned away from being send to nameserver due to +ratelimiting. +.TP .I num.answer.rcode.NXDOMAIN The number of answers to queries, from cache or from recursion, that had the return code NXDOMAIN. Also printed for the other return codes. diff --git a/contrib/unbound/doc/unbound-control.8.in b/contrib/unbound/doc/unbound-control.8.in index 5b220d664dd0..66ea690390a0 100644 --- a/contrib/unbound/doc/unbound-control.8.in +++ b/contrib/unbound/doc/unbound-control.8.in @@ -1,4 +1,4 @@ -.TH "unbound-control" "8" "Aug 21, 2017" "NLnet Labs" "unbound 1.6.5" +.TH "unbound-control" "8" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound-control.8 -- unbound remote control manual .\" @@ -493,6 +493,10 @@ number of queries that had an EDNS OPT record present. number of queries that had an EDNS OPT record with the DO (DNSSEC OK) bit set. These queries are also included in the num.query.edns.present number. .TP +.I num.query.ratelimited +The number of queries that are turned away from being send to nameserver due to +ratelimiting. +.TP .I num.answer.rcode.NXDOMAIN The number of answers to queries, from cache or from recursion, that had the return code NXDOMAIN. Also printed for the other return codes. diff --git a/contrib/unbound/doc/unbound-host.1 b/contrib/unbound/doc/unbound-host.1 index 6f07d2e69b9d..283b73e3c0e9 100644 --- a/contrib/unbound/doc/unbound-host.1 +++ b/contrib/unbound/doc/unbound-host.1 @@ -1,4 +1,4 @@ -.TH "unbound\-host" "1" "Jun 27, 2017" "NLnet Labs" "unbound 1.6.4" +.TH "unbound\-host" "1" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound-host.1 -- unbound DNS lookup utility .\" diff --git a/contrib/unbound/doc/unbound-host.1.in b/contrib/unbound/doc/unbound-host.1.in index 5a088b606f78..de8f0bdd052c 100644 --- a/contrib/unbound/doc/unbound-host.1.in +++ b/contrib/unbound/doc/unbound-host.1.in @@ -1,4 +1,4 @@ -.TH "unbound\-host" "1" "Aug 21, 2017" "NLnet Labs" "unbound 1.6.5" +.TH "unbound\-host" "1" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound-host.1 -- unbound DNS lookup utility .\" diff --git a/contrib/unbound/doc/unbound.8 b/contrib/unbound/doc/unbound.8 index 3b66f41d8967..51fd99eb157f 100644 --- a/contrib/unbound/doc/unbound.8 +++ b/contrib/unbound/doc/unbound.8 @@ -1,4 +1,4 @@ -.TH "unbound" "8" "Jun 27, 2017" "NLnet Labs" "unbound 1.6.4" +.TH "unbound" "8" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound.8 -- unbound manual .\" @@ -9,11 +9,12 @@ .\" .SH "NAME" .B unbound -\- Unbound DNS validating resolver 1.6.4. +\- Unbound DNS validating resolver 1.6.6. .SH "SYNOPSIS" .B unbound .RB [ \-h ] .RB [ \-d ] +.RB [ \-p ] .RB [ \-v ] .RB [ \-c .IR cfgfile ] @@ -67,6 +68,11 @@ the thread\-spawn time, so that most config and setup errors appear on stderr. If given twice or more, logging does not switch to the log file or to syslog, but the log messages are printed to stderr all the time. .TP +.B \-p +Don't use a pidfile. This argument should only be used by supervision +systems which can ensure that only one instance of unbound will run +concurrently. +.TP .B \-v Increase verbosity. If given multiple times, more information is logged. This is in addition to the verbosity (if any) from the config file. diff --git a/contrib/unbound/doc/unbound.8.in b/contrib/unbound/doc/unbound.8.in index 87f1b6ef0123..24959ba26cec 100644 --- a/contrib/unbound/doc/unbound.8.in +++ b/contrib/unbound/doc/unbound.8.in @@ -1,4 +1,4 @@ -.TH "unbound" "8" "Aug 21, 2017" "NLnet Labs" "unbound 1.6.5" +.TH "unbound" "8" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound.8 -- unbound manual .\" @@ -9,11 +9,12 @@ .\" .SH "NAME" .B unbound -\- Unbound DNS validating resolver 1.6.5. +\- Unbound DNS validating resolver 1.6.6. .SH "SYNOPSIS" .B unbound .RB [ \-h ] .RB [ \-d ] +.RB [ \-p ] .RB [ \-v ] .RB [ \-c .IR cfgfile ] @@ -67,6 +68,11 @@ the thread\-spawn time, so that most config and setup errors appear on stderr. If given twice or more, logging does not switch to the log file or to syslog, but the log messages are printed to stderr all the time. .TP +.B \-p +Don't use a pidfile. This argument should only be used by supervision +systems which can ensure that only one instance of unbound will run +concurrently. +.TP .B \-v Increase verbosity. If given multiple times, more information is logged. This is in addition to the verbosity (if any) from the config file. diff --git a/contrib/unbound/doc/unbound.conf.5 b/contrib/unbound/doc/unbound.conf.5 index 7cca54162f53..b489ccc53b26 100644 --- a/contrib/unbound/doc/unbound.conf.5 +++ b/contrib/unbound/doc/unbound.conf.5 @@ -1,4 +1,4 @@ -.TH "unbound.conf" "5" "Jun 27, 2017" "NLnet Labs" "unbound 1.6.4" +.TH "unbound.conf" "5" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound.conf.5 -- unbound.conf manual .\" @@ -197,7 +197,7 @@ This is the value put into datagrams over UDP towards peers. The actual buffer size is determined by msg\-buffer\-size (both for TCP and UDP). Do not set higher than that value. Default is 4096 which is RFC recommended. If you have fragmentation reassembly problems, usually seen as timeouts, -then a value of 1480 can fix it. Setting to 512 bypasses even the most +then a value of 1472 can fix it. Setting to 512 bypasses even the most stringent path MTU problems, but is seen as extreme, since the amount of TCP fallback generated is excessive (probably also for this resolver, consider tuning the outgoing tcp number). @@ -1048,19 +1048,19 @@ has no other effect than turning off default contents for the given zone. Use \fInodefault\fR if you use exactly that zone, if you want to use a subzone, use \fItransparent\fR. .P -The default zones are localhost, reverse 127.0.0.1 and ::1, the onion and -the AS112 zones. The AS112 zones are reverse DNS zones for private use and -reserved IP addresses for which the servers on the internet cannot provide -correct answers. They are configured by default to give nxdomain (no reverse -information) answers. The defaults can be turned off by specifying your -own local\-zone of that name, or using the 'nodefault' type. Below is a -list of the default zone contents. +The default zones are localhost, reverse 127.0.0.1 and ::1, the onion, test, +invalid and the AS112 zones. The AS112 zones are reverse DNS zones for +private use and reserved IP addresses for which the servers on the internet +cannot provide correct answers. They are configured by default to give +nxdomain (no reverse information) answers. The defaults can be turned off +by specifying your own local\-zone of that name, or using the 'nodefault' +type. Below is a list of the default zone contents. .TP 10 \h'5'\fIlocalhost\fR The IP4 and IP6 localhost information is given. NS and SOA records are provided for completeness and to satisfy some DNS update tools. Default content: .nf -local\-zone: "localhost." static +local\-zone: "localhost." redirect local\-data: "localhost. 10800 IN NS localhost." local\-data: "localhost. 10800 IN SOA localhost. nobody.invalid. 1 3600 1200 604800 10800" @@ -1104,6 +1104,24 @@ local\-data: "onion. 10800 IN SOA localhost. nobody.invalid. 1 3600 1200 604800 10800" .fi .TP 10 +\h'5'\fItest (RFC 7686)\fR +Default content: +.nf +local\-zone: "test." static +local\-data: "test. 10800 IN NS localhost." +local\-data: "test. 10800 IN + SOA localhost. nobody.invalid. 1 3600 1200 604800 10800" +.fi +.TP 10 +\h'5'\fIinvalid (RFC 7686)\fR +Default content: +.nf +local\-zone: "invalid." static +local\-data: "invalid. 10800 IN NS localhost." +local\-data: "invalid. 10800 IN + SOA localhost. nobody.invalid. 1 3600 1200 604800 10800" +.fi +.TP 10 \h'5'\fIreverse RFC1918 local use zones\fR Reverse data for zones 10.in\-addr.arpa, 16.172.in\-addr.arpa to 31.172.in\-addr.arpa, 168.192.in\-addr.arpa. @@ -1461,7 +1479,7 @@ despite the presence of actual AAAA records. .LP The .B dnscrypt: -clause give the settings of the dnscrypt channel. While those options are +clause gives the settings of the dnscrypt channel. While those options are available, they are only meaningful if unbound was compiled with \fB\-\-enable\-dnscrypt\fR. Currently certificate and secret/public keys cannot be generated by unbound. @@ -1489,6 +1507,17 @@ times. .B dnscrypt\-provider\-cert: \fI\fR Path to the certificate related to the \fBdnscrypt\-secret\-key\fRs. This option may be specified multiple times. +.TP +.B dnscrypt\-shared\-secret\-cache\-size: \fI +Give the size of the data structure in which the shared secret keys are kept +in. Default 4m. In bytes or use m(mega), k(kilo), g(giga). +The shared secret cache is used when a same client is making multiple queries +using the same public key. It saves a substantial amount of CPU. +.TP +.B dnscrypt\-shared\-secret\-cache\-slabs: \fI +Give power of 2 number of slabs, this is used to reduce lock contention +in the dnscrypt shared secrets cache. Close to the number of cpus is +a fairly good setting. .SS "EDNS Client Subnet Module Options" .LP The ECS module must be configured in the \fBmodule\-config:\fR "subnetcache @@ -1603,6 +1632,37 @@ A/AAAA query will be SERVFAIL. Mainly used for testing. Defaults to no. Whitelist the domain so that the module logic will be executed. Can be given multiple times, for different domains. If the option is not specified, all domains are treated as being whitelisted (default). +.SS "Cache DB Module Options" +.LP +The Cache DB module must be configured in the \fBmodule\-config:\fR +"validator cachedb iterator" directive and be compiled into the daemon +with \fB\-\-enable\-cachedb\fR. +If this module is enabled and configured, the specified backend database +works as a second level cache: +When Unbound cannot find an answer to a query in its built-in in-memory +cache, it consults the specified backend. +If it finds a valid answer in the backend, Unbound uses it to respond +to the query without performing iterative DNS resolution. +If Unbound cannot even find an answer in the backend, it resolves the +query as usual, and stores the answer in the backend. +The +.B cachedb: +clause gives custom settings of the cache DB module. +.TP +.B backend: \fI\fR +Specify the backend database name. +Currently, only the in-memory "testframe" backend is supported. +As the name suggests this backend is not of any practical use. +This option defaults to "testframe". +.TP +.B secret-seed: \fI<"secret string">\fR +Specify a seed to calculate a hash value from query information. +This value will be used as the key of the corresponding answer for the +backend database and can be customized if the hash should not be predictable +operationally. +If the backend database is shared by multiple Unbound instances, +all instances must use the same secret seed. +This option defaults to "default". .SH "MEMORY CONTROL EXAMPLE" In the example config settings below memory usage is reduced. Some service levels are lower, notable very large data and a high TCP load are no longer diff --git a/contrib/unbound/doc/unbound.conf.5.in b/contrib/unbound/doc/unbound.conf.5.in index 2acf2622c5da..f48ef9214afa 100644 --- a/contrib/unbound/doc/unbound.conf.5.in +++ b/contrib/unbound/doc/unbound.conf.5.in @@ -1,4 +1,4 @@ -.TH "unbound.conf" "5" "Aug 21, 2017" "NLnet Labs" "unbound 1.6.5" +.TH "unbound.conf" "5" "Sep 18, 2017" "NLnet Labs" "unbound 1.6.6" .\" .\" unbound.conf.5 -- unbound.conf manual .\" @@ -197,7 +197,7 @@ This is the value put into datagrams over UDP towards peers. The actual buffer size is determined by msg\-buffer\-size (both for TCP and UDP). Do not set higher than that value. Default is 4096 which is RFC recommended. If you have fragmentation reassembly problems, usually seen as timeouts, -then a value of 1480 can fix it. Setting to 512 bypasses even the most +then a value of 1472 can fix it. Setting to 512 bypasses even the most stringent path MTU problems, but is seen as extreme, since the amount of TCP fallback generated is excessive (probably also for this resolver, consider tuning the outgoing tcp number). @@ -1048,19 +1048,19 @@ has no other effect than turning off default contents for the given zone. Use \fInodefault\fR if you use exactly that zone, if you want to use a subzone, use \fItransparent\fR. .P -The default zones are localhost, reverse 127.0.0.1 and ::1, the onion and -the AS112 zones. The AS112 zones are reverse DNS zones for private use and -reserved IP addresses for which the servers on the internet cannot provide -correct answers. They are configured by default to give nxdomain (no reverse -information) answers. The defaults can be turned off by specifying your -own local\-zone of that name, or using the 'nodefault' type. Below is a -list of the default zone contents. +The default zones are localhost, reverse 127.0.0.1 and ::1, the onion, test, +invalid and the AS112 zones. The AS112 zones are reverse DNS zones for +private use and reserved IP addresses for which the servers on the internet +cannot provide correct answers. They are configured by default to give +nxdomain (no reverse information) answers. The defaults can be turned off +by specifying your own local\-zone of that name, or using the 'nodefault' +type. Below is a list of the default zone contents. .TP 10 \h'5'\fIlocalhost\fR The IP4 and IP6 localhost information is given. NS and SOA records are provided for completeness and to satisfy some DNS update tools. Default content: .nf -local\-zone: "localhost." static +local\-zone: "localhost." redirect local\-data: "localhost. 10800 IN NS localhost." local\-data: "localhost. 10800 IN SOA localhost. nobody.invalid. 1 3600 1200 604800 10800" @@ -1104,6 +1104,24 @@ local\-data: "onion. 10800 IN SOA localhost. nobody.invalid. 1 3600 1200 604800 10800" .fi .TP 10 +\h'5'\fItest (RFC 7686)\fR +Default content: +.nf +local\-zone: "test." static +local\-data: "test. 10800 IN NS localhost." +local\-data: "test. 10800 IN + SOA localhost. nobody.invalid. 1 3600 1200 604800 10800" +.fi +.TP 10 +\h'5'\fIinvalid (RFC 7686)\fR +Default content: +.nf +local\-zone: "invalid." static +local\-data: "invalid. 10800 IN NS localhost." +local\-data: "invalid. 10800 IN + SOA localhost. nobody.invalid. 1 3600 1200 604800 10800" +.fi +.TP 10 \h'5'\fIreverse RFC1918 local use zones\fR Reverse data for zones 10.in\-addr.arpa, 16.172.in\-addr.arpa to 31.172.in\-addr.arpa, 168.192.in\-addr.arpa. @@ -1461,7 +1479,7 @@ despite the presence of actual AAAA records. .LP The .B dnscrypt: -clause give the settings of the dnscrypt channel. While those options are +clause gives the settings of the dnscrypt channel. While those options are available, they are only meaningful if unbound was compiled with \fB\-\-enable\-dnscrypt\fR. Currently certificate and secret/public keys cannot be generated by unbound. @@ -1489,6 +1507,17 @@ times. .B dnscrypt\-provider\-cert: \fI\fR Path to the certificate related to the \fBdnscrypt\-secret\-key\fRs. This option may be specified multiple times. +.TP +.B dnscrypt\-shared\-secret\-cache\-size: \fI +Give the size of the data structure in which the shared secret keys are kept +in. Default 4m. In bytes or use m(mega), k(kilo), g(giga). +The shared secret cache is used when a same client is making multiple queries +using the same public key. It saves a substantial amount of CPU. +.TP +.B dnscrypt\-shared\-secret\-cache\-slabs: \fI +Give power of 2 number of slabs, this is used to reduce lock contention +in the dnscrypt shared secrets cache. Close to the number of cpus is +a fairly good setting. .SS "EDNS Client Subnet Module Options" .LP The ECS module must be configured in the \fBmodule\-config:\fR "subnetcache @@ -1603,6 +1632,37 @@ A/AAAA query will be SERVFAIL. Mainly used for testing. Defaults to no. Whitelist the domain so that the module logic will be executed. Can be given multiple times, for different domains. If the option is not specified, all domains are treated as being whitelisted (default). +.SS "Cache DB Module Options" +.LP +The Cache DB module must be configured in the \fBmodule\-config:\fR +"validator cachedb iterator" directive and be compiled into the daemon +with \fB\-\-enable\-cachedb\fR. +If this module is enabled and configured, the specified backend database +works as a second level cache: +When Unbound cannot find an answer to a query in its built-in in-memory +cache, it consults the specified backend. +If it finds a valid answer in the backend, Unbound uses it to respond +to the query without performing iterative DNS resolution. +If Unbound cannot even find an answer in the backend, it resolves the +query as usual, and stores the answer in the backend. +The +.B cachedb: +clause gives custom settings of the cache DB module. +.TP +.B backend: \fI\fR +Specify the backend database name. +Currently, only the in-memory "testframe" backend is supported. +As the name suggests this backend is not of any practical use. +This option defaults to "testframe". +.TP +.B secret-seed: \fI<"secret string">\fR +Specify a seed to calculate a hash value from query information. +This value will be used as the key of the corresponding answer for the +backend database and can be customized if the hash should not be predictable +operationally. +If the backend database is shared by multiple Unbound instances, +all instances must use the same secret seed. +This option defaults to "default". .SH "MEMORY CONTROL EXAMPLE" In the example config settings below memory usage is reduced. Some service levels are lower, notable very large data and a high TCP load are no longer diff --git a/contrib/unbound/iterator/iterator.c b/contrib/unbound/iterator/iterator.c index 205ab0d15407..01ac883e81e8 100644 --- a/contrib/unbound/iterator/iterator.c +++ b/contrib/unbound/iterator/iterator.c @@ -78,6 +78,12 @@ iter_init(struct module_env* env, int id) return 0; } env->modinfo[id] = (void*)iter_env; + + lock_basic_init(&iter_env->queries_ratelimit_lock); + lock_protect(&iter_env->queries_ratelimit_lock, + &iter_env->num_queries_ratelimited, + sizeof(iter_env->num_queries_ratelimited)); + if(!iter_apply_cfg(iter_env, env->cfg)) { log_err("iterator: could not apply configuration settings."); return 0; @@ -103,6 +109,7 @@ iter_deinit(struct module_env* env, int id) if(!env || !env->modinfo[id]) return; iter_env = (struct iter_env*)env->modinfo[id]; + lock_basic_destroy(&iter_env->queries_ratelimit_lock); free(iter_env->target_fetch_policy); priv_delete(iter_env->priv); donotq_delete(iter_env->donotq); @@ -1276,6 +1283,9 @@ processInitRequest(struct module_qstate* qstate, struct iter_qstate* iq, "delegation point", iq->dp->name, LDNS_RR_TYPE_NS, LDNS_RR_CLASS_IN); } else { + lock_basic_lock(&ie->queries_ratelimit_lock); + ie->num_queries_ratelimited++; + lock_basic_unlock(&ie->queries_ratelimit_lock); log_nametypeclass(VERB_ALGO, "ratelimit exceeded with " "delegation point", iq->dp->name, LDNS_RR_TYPE_NS, LDNS_RR_CLASS_IN); @@ -2064,6 +2074,9 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq, if(!(iq->chase_flags & BIT_RD) && !iq->ratelimit_ok) { if(!infra_ratelimit_inc(qstate->env->infra_cache, iq->dp->name, iq->dp->namelen, *qstate->env->now)) { + lock_basic_lock(&ie->queries_ratelimit_lock); + ie->num_queries_ratelimited++; + lock_basic_unlock(&ie->queries_ratelimit_lock); verbose(VERB_ALGO, "query exceeded ratelimits"); return error_response(qstate, id, LDNS_RCODE_SERVFAIL); } @@ -2156,7 +2169,6 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq, } } if(iq->minimisation_state == SKIP_MINIMISE_STATE) { - iq->minimise_timeout_count++; if(iq->minimise_timeout_count < MAX_MINIMISE_TIMEOUT_COUNT) /* Do not increment qname, continue incrementing next * iteration */ @@ -2197,6 +2209,8 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq, if(!(iq->chase_flags & BIT_RD) && !iq->ratelimit_ok) infra_ratelimit_dec(qstate->env->infra_cache, iq->dp->name, iq->dp->namelen, *qstate->env->now); + if(qstate->env->cfg->qname_minimisation) + iq->minimisation_state = SKIP_MINIMISE_STATE; return next_state(iq, QUERYTARGETS_STATE); } outbound_list_insert(&iq->outlist, outq); @@ -2246,8 +2260,10 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq, if(iq->response == NULL) { /* Don't increment qname when QNAME minimisation is enabled */ - if(qstate->env->cfg->qname_minimisation) + if(qstate->env->cfg->qname_minimisation) { + iq->minimise_timeout_count++; iq->minimisation_state = SKIP_MINIMISE_STATE; + } iq->chase_to_rd = 0; iq->dnssec_lame_query = 0; verbose(VERB_ALGO, "query response was timeout"); diff --git a/contrib/unbound/iterator/iterator.h b/contrib/unbound/iterator/iterator.h index 37b0ab0dc24a..75aafee475e2 100644 --- a/contrib/unbound/iterator/iterator.h +++ b/contrib/unbound/iterator/iterator.h @@ -130,8 +130,10 @@ struct iter_env { */ int* target_fetch_policy; - /** ip6.arpa dname in wireformat, used for qname-minimisation */ - uint8_t* ip6arpa_dname; + /** lock on ratelimit counter */ + lock_basic_type queries_ratelimit_lock; + /** number of queries that have been ratelimited */ + size_t num_queries_ratelimited; }; /** diff --git a/contrib/unbound/libunbound/libworker.c b/contrib/unbound/libunbound/libworker.c index b42ba0bd8e78..f6a1d1d1c47b 100644 --- a/contrib/unbound/libunbound/libworker.c +++ b/contrib/unbound/libunbound/libworker.c @@ -294,6 +294,7 @@ libworker_do_cmd(struct libworker* w, uint8_t* msg, uint32_t len) log_err("unknown command for bg worker %d", (int)context_serial_getcmd(msg, len)); /* and fall through to quit */ + /* fallthrough */ case UB_LIBCMD_QUIT: free(msg); comm_base_exit(w->base); @@ -749,7 +750,7 @@ libworker_bg_done_cb(void* arg, int rcode, sldns_buffer* buf, enum sec_status s, { struct ctx_query* q = (struct ctx_query*)arg; - if(q->cancelled) { + if(q->cancelled || q->w->back->want_to_quit) { if(q->w->is_bg_thread) { /* delete it now */ struct ub_ctx* ctx = q->w->ctx; diff --git a/contrib/unbound/libunbound/unbound.h b/contrib/unbound/libunbound/unbound.h index d7667d104a0e..ac747a7cc6cc 100644 --- a/contrib/unbound/libunbound/unbound.h +++ b/contrib/unbound/libunbound/unbound.h @@ -622,6 +622,7 @@ struct ub_shm_stat_info { long long subnet; long long ipsecmod; long long respip; + long long dnscrypt_shared_secret; } mem; }; @@ -704,6 +705,8 @@ struct ub_server_stats { long long ans_bogus; /** rrsets marked bogus by validator */ long long rrset_bogus; + /** number of queries that have been ratelimited by domain recursion. */ + long long queries_ratelimited; /** unwanted traffic received on server-facing ports */ long long unwanted_replies; /** unwanted traffic received on client-facing ports */ @@ -735,6 +738,10 @@ struct ub_server_stats { long long num_query_dnscrypt_cleartext; /** number of malformed encrypted queries */ long long num_query_dnscrypt_crypted_malformed; + /** number of queries which did not have a shared secret in cache */ + long long num_query_dnscrypt_secret_missed_cache; + /** number of dnscrypt shared secret cache entries */ + long long shared_secret_cache_count; }; /** diff --git a/contrib/unbound/services/authzone.c b/contrib/unbound/services/authzone.c index da77db6b8184..7fe3a6861f7d 100644 --- a/contrib/unbound/services/authzone.c +++ b/contrib/unbound/services/authzone.c @@ -628,7 +628,7 @@ rrset_add_rr(struct auth_rrset* rrset, uint32_t rr_ttl, uint8_t* rdata, d->rr_len[d->count-1] = rdatalen; else d->rr_len[total-1] = rdatalen; packed_rrset_ptr_fixup(d); - if(rr_ttl < d->ttl) + if((time_t)rr_ttl < d->ttl) d->ttl = rr_ttl; /* copy old values into new array */ diff --git a/contrib/unbound/services/cache/dns.c b/contrib/unbound/services/cache/dns.c index 764205e53cbe..da43c504dfa3 100644 --- a/contrib/unbound/services/cache/dns.c +++ b/contrib/unbound/services/cache/dns.c @@ -99,6 +99,9 @@ store_rrsets(struct module_env* env, struct reply_info* rep, time_t now, } } /* no break: also copy key item */ + /* the line below is matched by gcc regex and silences + * the fallthrough warning */ + /* fallthrough */ case 1: /* ref updated, item inserted */ rep->rrsets[i] = rep->ref[i].key; } diff --git a/contrib/unbound/services/cache/infra.c b/contrib/unbound/services/cache/infra.c index 9673259d889a..ff95b4d1d582 100644 --- a/contrib/unbound/services/cache/infra.c +++ b/contrib/unbound/services/cache/infra.c @@ -249,7 +249,7 @@ infra_create(struct config_file* cfg) name_tree_init_parents(&infra->domain_limits); } infra_ip_ratelimit = cfg->ip_ratelimit; - infra->client_ip_rates = slabhash_create(cfg->ratelimit_slabs, + infra->client_ip_rates = slabhash_create(cfg->ip_ratelimit_slabs, INFRA_HOST_STARTSIZE, cfg->ip_ratelimit_size, &ip_rate_sizefunc, &ip_rate_compfunc, &ip_rate_delkeyfunc, &ip_rate_deldatafunc, NULL); if(!infra->client_ip_rates) { diff --git a/contrib/unbound/services/listen_dnsport.c b/contrib/unbound/services/listen_dnsport.c index 0341f3067489..3b53676d0e06 100644 --- a/contrib/unbound/services/listen_dnsport.c +++ b/contrib/unbound/services/listen_dnsport.c @@ -792,7 +792,12 @@ create_tcp_accept_sock(struct addrinfo *addr, int v6only, int* noproto, #endif if ((setsockopt(s, IPPROTO_TCP, TCP_FASTOPEN, &qlen, sizeof(qlen))) == -1 ) { - log_err("Setting TCP Fast Open as server failed: %s", strerror(errno)); +#ifdef ENOPROTOOPT + /* squelch ENOPROTOOPT: freebsd server mode with kernel support + disabled, except when verbosity enabled for debugging */ + if(errno != ENOPROTOOPT || verbosity >= 3) +#endif + log_err("Setting TCP Fast Open as server failed: %s", strerror(errno)); } #endif return s; diff --git a/contrib/unbound/services/localzone.c b/contrib/unbound/services/localzone.c index a19b5252643f..6bde432e8d09 100644 --- a/contrib/unbound/services/localzone.c +++ b/contrib/unbound/services/localzone.c @@ -260,7 +260,8 @@ rrstr_get_rr_content(const char* str, uint8_t** nm, uint16_t* type, /** return name and class of rr; parses string */ static int -get_rr_nameclass(const char* str, uint8_t** nm, uint16_t* dclass) +get_rr_nameclass(const char* str, uint8_t** nm, uint16_t* dclass, + uint16_t* dtype) { uint8_t rr[LDNS_RR_BUF_SIZE]; size_t len = sizeof(rr), dname_len = 0; @@ -274,6 +275,7 @@ get_rr_nameclass(const char* str, uint8_t** nm, uint16_t* dclass) } *nm = memdup(rr, dname_len); *dclass = sldns_wirerr_get_class(rr, len, dname_len); + *dtype = sldns_wirerr_get_type(rr, len, dname_len); if(!*nm) { log_err("out of memory"); return 0; @@ -522,18 +524,18 @@ static int lz_enter_rr_str(struct local_zones* zones, const char* rr) { uint8_t* rr_name; - uint16_t rr_class; + uint16_t rr_class, rr_type; size_t len; int labs; struct local_zone* z; int r; - if(!get_rr_nameclass(rr, &rr_name, &rr_class)) { + if(!get_rr_nameclass(rr, &rr_name, &rr_class, &rr_type)) { log_err("bad rr %s", rr); return 0; } labs = dname_count_size_labels(rr_name, &len); lock_rw_rdlock(&zones->lock); - z = local_zones_lookup(zones, rr_name, len, labs, rr_class); + z = local_zones_lookup(zones, rr_name, len, labs, rr_class, rr_type); if(!z) { lock_rw_unlock(&zones->lock); fatal_exit("internal error: no zone for rr %s", rr); @@ -719,9 +721,9 @@ lz_nodefault(struct config_file* cfg, const char* name) return 0; } -/** enter AS112 default zone */ +/** enter (AS112) empty default zone */ static int -add_as112_default(struct local_zones* zones, struct config_file* cfg, +add_empty_default(struct local_zones* zones, struct config_file* cfg, const char* name) { struct local_zone* z; @@ -762,7 +764,7 @@ int local_zone_enter_defaults(struct local_zones* zones, struct config_file* cfg /* localhost. zone */ if(!lz_exists(zones, "localhost.") && !lz_nodefault(cfg, "localhost.")) { - if(!(z=lz_enter_zone(zones, "localhost.", "static", + if(!(z=lz_enter_zone(zones, "localhost.", "redirect", LDNS_RR_CLASS_IN)) || !lz_enter_rr_into_zone(z, "localhost. 10800 IN NS localhost.") || @@ -816,26 +818,24 @@ int local_zone_enter_defaults(struct local_zones* zones, struct config_file* cfg lock_rw_unlock(&z->lock); } /* onion. zone (RFC 7686) */ - if(!lz_exists(zones, "onion.") && - !lz_nodefault(cfg, "onion.")) { - if(!(z=lz_enter_zone(zones, "onion.", "static", - LDNS_RR_CLASS_IN)) || - !lz_enter_rr_into_zone(z, - "onion. 10800 IN NS localhost.") || - !lz_enter_rr_into_zone(z, - "onion. 10800 IN SOA localhost. nobody.invalid. " - "1 3600 1200 604800 10800")) { - log_err("out of memory adding default zone"); - if(z) { lock_rw_unlock(&z->lock); } - return 0; - } - lock_rw_unlock(&z->lock); + if(!add_empty_default(zones, cfg, "onion.")) { + log_err("out of memory adding default zone"); + return 0; + } + /* test. zone (RFC 7686) */ + if(!add_empty_default(zones, cfg, "test.")) { + log_err("out of memory adding default zone"); + return 0; + } + /* invalid. zone (RFC 7686) */ + if(!add_empty_default(zones, cfg, "invalid.")) { + log_err("out of memory adding default zone"); + return 0; } - /* block AS112 zones, unless asked not to */ if(!cfg->unblock_lan_zones) { for(zstr = as112_zones; *zstr; zstr++) { - if(!add_as112_default(zones, cfg, *zstr)) { + if(!add_empty_default(zones, cfg, *zstr)) { log_err("out of memory adding default zone"); return 0; } @@ -913,16 +913,17 @@ lz_setup_implicit(struct local_zones* zones, struct config_file* cfg) init_parents(zones); /* to enable local_zones_lookup() */ for(p = cfg->local_data; p; p = p->next) { uint8_t* rr_name; - uint16_t rr_class; + uint16_t rr_class, rr_type; size_t len; int labs; - if(!get_rr_nameclass(p->str, &rr_name, &rr_class)) { + if(!get_rr_nameclass(p->str, &rr_name, &rr_class, &rr_type)) { log_err("Bad local-data RR %s", p->str); return 0; } labs = dname_count_size_labels(rr_name, &len); lock_rw_rdlock(&zones->lock); - if(!local_zones_lookup(zones, rr_name, len, labs, rr_class)) { + if(!local_zones_lookup(zones, rr_name, len, labs, rr_class, + rr_type)) { if(!have_name) { dclass = rr_class; nm = rr_name; @@ -1053,21 +1054,26 @@ local_zones_apply_cfg(struct local_zones* zones, struct config_file* cfg) struct local_zone* local_zones_lookup(struct local_zones* zones, - uint8_t* name, size_t len, int labs, uint16_t dclass) + uint8_t* name, size_t len, int labs, uint16_t dclass, uint16_t dtype) { return local_zones_tags_lookup(zones, name, len, labs, - dclass, NULL, 0, 1); + dclass, dtype, NULL, 0, 1); } struct local_zone* local_zones_tags_lookup(struct local_zones* zones, - uint8_t* name, size_t len, int labs, uint16_t dclass, + uint8_t* name, size_t len, int labs, uint16_t dclass, uint16_t dtype, uint8_t* taglist, size_t taglen, int ignoretags) { rbnode_type* res = NULL; struct local_zone *result; struct local_zone key; int m; + /* for type DS use a zone higher when on a zonecut */ + if(dtype == LDNS_RR_TYPE_DS && !dname_is_root(name)) { + dname_remove_label(&name, &len); + labs--; + } key.node.key = &key; key.dclass = dclass; key.name = name; @@ -1583,7 +1589,7 @@ local_zones_answer(struct local_zones* zones, struct module_env* env, if(view->local_zones && (z = local_zones_lookup(view->local_zones, qinfo->qname, qinfo->qname_len, labs, - qinfo->qclass))) { + qinfo->qclass, qinfo->qtype))) { verbose(VERB_ALGO, "using localzone from view: %s", view->name); @@ -1600,8 +1606,8 @@ local_zones_answer(struct local_zones* zones, struct module_env* env, /* try global local_zones tree */ lock_rw_rdlock(&zones->lock); if(!(z = local_zones_tags_lookup(zones, qinfo->qname, - qinfo->qname_len, labs, qinfo->qclass, taglist, - taglen, 0))) { + qinfo->qname_len, labs, qinfo->qclass, qinfo->qtype, + taglist, taglen, 0))) { lock_rw_unlock(&zones->lock); return 0; } @@ -1756,19 +1762,19 @@ int local_zones_add_RR(struct local_zones* zones, const char* rr) { uint8_t* rr_name; - uint16_t rr_class; + uint16_t rr_class, rr_type; size_t len; int labs; struct local_zone* z; int r; - if(!get_rr_nameclass(rr, &rr_name, &rr_class)) { + if(!get_rr_nameclass(rr, &rr_name, &rr_class, &rr_type)) { return 0; } labs = dname_count_size_labels(rr_name, &len); /* could first try readlock then get writelock if zone does not exist, * but we do not add enough RRs (from multiple threads) to optimize */ lock_rw_wrlock(&zones->lock); - z = local_zones_lookup(zones, rr_name, len, labs, rr_class); + z = local_zones_lookup(zones, rr_name, len, labs, rr_class, rr_type); if(!z) { z = local_zones_add_zone(zones, rr_name, len, labs, rr_class, local_zone_transparent); @@ -1820,14 +1826,47 @@ del_empty_term(struct local_zone* z, struct local_data* d, } } +/** find and remove type from list in domain struct */ +static void +del_local_rrset(struct local_data* d, uint16_t dtype) +{ + struct local_rrset* prev=NULL, *p=d->rrsets; + while(p && ntohs(p->rrset->rk.type) != dtype) { + prev = p; + p = p->next; + } + if(!p) + return; /* rrset type not found */ + /* unlink it */ + if(prev) prev->next = p->next; + else d->rrsets = p->next; + /* no memory recycling for zone deletions ... */ +} + void local_zones_del_data(struct local_zones* zones, uint8_t* name, size_t len, int labs, uint16_t dclass) { /* find zone */ struct local_zone* z; struct local_data* d; + + /* remove DS */ lock_rw_rdlock(&zones->lock); - z = local_zones_lookup(zones, name, len, labs, dclass); + z = local_zones_lookup(zones, name, len, labs, dclass, LDNS_RR_TYPE_DS); + if(z) { + lock_rw_wrlock(&z->lock); + d = lz_find_node(z, name, len, labs); + if(d) { + del_local_rrset(d, LDNS_RR_TYPE_DS); + del_empty_term(z, d, name, len, labs); + } + lock_rw_unlock(&z->lock); + } + lock_rw_unlock(&zones->lock); + + /* remove other types */ + lock_rw_rdlock(&zones->lock); + z = local_zones_lookup(zones, name, len, labs, dclass, 0); if(!z) { /* no such zone, we're done */ lock_rw_unlock(&zones->lock); diff --git a/contrib/unbound/services/localzone.h b/contrib/unbound/services/localzone.h index fcdad41666d2..0a8759268bb2 100644 --- a/contrib/unbound/services/localzone.h +++ b/contrib/unbound/services/localzone.h @@ -235,6 +235,7 @@ void local_zone_delete(struct local_zone* z); * @param len: length of name. * @param labs: labelcount of name. * @param dclass: class to lookup. + * @param dtype: type to lookup, if type DS a zone higher is used for zonecuts. * @param taglist: taglist to lookup. * @param taglen: lenth of taglist. * @param ignoretags: lookup zone by name and class, regardless the @@ -242,7 +243,7 @@ void local_zone_delete(struct local_zone* z); * @return closest local_zone or NULL if no covering zone is found. */ struct local_zone* local_zones_tags_lookup(struct local_zones* zones, - uint8_t* name, size_t len, int labs, uint16_t dclass, + uint8_t* name, size_t len, int labs, uint16_t dclass, uint16_t dtype, uint8_t* taglist, size_t taglen, int ignoretags); /** @@ -253,10 +254,12 @@ struct local_zone* local_zones_tags_lookup(struct local_zones* zones, * @param len: length of name. * @param labs: labelcount of name. * @param dclass: class to lookup. + * @param dtype: type of the record, if type DS then a zone higher up is found + * pass 0 to just plain find a zone for a name. * @return closest local_zone or NULL if no covering zone is found. */ struct local_zone* local_zones_lookup(struct local_zones* zones, - uint8_t* name, size_t len, int labs, uint16_t dclass); + uint8_t* name, size_t len, int labs, uint16_t dclass, uint16_t dtype); /** * Debug helper. Print all zones diff --git a/contrib/unbound/services/outside_network.c b/contrib/unbound/services/outside_network.c index 9b1490e643f8..fe2b55b1ac17 100644 --- a/contrib/unbound/services/outside_network.c +++ b/contrib/unbound/services/outside_network.c @@ -268,6 +268,13 @@ outnet_tcp_take_into_use(struct waiting_tcp* w, uint8_t* pkt, size_t pkt_len) if (connectx(s, &endpoints, SAE_ASSOCID_ANY, CONNECT_DATA_IDEMPOTENT | CONNECT_RESUME_ON_READ_WRITE, NULL, 0, NULL, NULL) == -1) { + /* if fails, failover to connect for OSX 10.10 */ +#ifdef EINPROGRESS + if(errno != EINPROGRESS) { +#else + if(1) { +#endif + if(connect(s, (struct sockaddr*)&w->addr, w->addrlen) == -1) { #else /* USE_OSX_MSG_FASTOPEN*/ #ifdef USE_MSG_FASTOPEN pend->c->tcp_do_fastopen = 1; @@ -302,6 +309,10 @@ outnet_tcp_take_into_use(struct waiting_tcp* w, uint8_t* pkt, size_t pkt_len) #ifdef USE_MSG_FASTOPEN } #endif /* USE_MSG_FASTOPEN */ +#ifdef USE_OSX_MSG_FASTOPEN + } + } +#endif /* USE_OSX_MSG_FASTOPEN */ if(w->outnet->sslctx && w->ssl_upstream) { pend->c->ssl = outgoing_ssl_fd(w->outnet->sslctx, s); if(!pend->c->ssl) { diff --git a/contrib/unbound/sldns/parseutil.c b/contrib/unbound/sldns/parseutil.c index 32717616aa4a..769987c64777 100644 --- a/contrib/unbound/sldns/parseutil.c +++ b/contrib/unbound/sldns/parseutil.c @@ -402,10 +402,12 @@ sldns_b32_ntop_base(const uint8_t* src, size_t src_sz, char* dst, size_t dst_sz, /* ........ ........ ....4444 4....... ........ */ c = src[3] >> 7 ; + /* fallthrough */ case 3: dst[4] = b32[(src[2] & 0x0f) << 1 | c]; /* ........ .......3 3333.... ........ ........ */ c = src[2] >> 4 ; + /* fallthrough */ case 2: dst[3] = b32[(src[1] & 0x01) << 4 | c]; /* ........ ..22222. ........ ........ ........ */ @@ -413,6 +415,7 @@ sldns_b32_ntop_base(const uint8_t* src, size_t src_sz, char* dst, size_t dst_sz, /* .....111 11...... ........ ........ ........ */ c = src[1] >> 6 ; + /* fallthrough */ case 1: dst[1] = b32[(src[0] & 0x07) << 2 | c]; /* 00000... ........ ........ ........ ........ */ @@ -423,9 +426,12 @@ sldns_b32_ntop_base(const uint8_t* src, size_t src_sz, char* dst, size_t dst_sz, switch (src_sz) { case 1: dst[2] = '='; dst[3] = '='; + /* fallthrough */ case 2: dst[4] = '='; + /* fallthrough */ case 3: dst[5] = '='; dst[6] = '='; + /* fallthrough */ case 4: dst[7] = '='; } } @@ -537,15 +543,18 @@ sldns_b32_pton_base(const char* src, size_t src_sz, uint8_t* dst, size_t dst_sz, /* ........ ........ ........ .55555.. ........ */ /* ........ ........ ....4444 4....... ........ */ dst[3] = buf[4] << 7 | buf[5] << 2 | buf[6] >> 3; + /* fallthrough */ case 5: /* ........ ........ ....4444 4....... ........ */ /* ........ .......3 3333.... ........ ........ */ dst[2] = buf[3] << 4 | buf[4] >> 1; + /* fallthrough */ case 4: /* ........ .......3 3333.... ........ ........ */ /* ........ ..22222. ........ ........ ........ */ /* .....111 11...... ........ ........ ........ */ dst[1] = buf[1] << 6 | buf[2] << 1 | buf[3] >> 4; + /* fallthrough */ case 2: /* .....111 11...... ........ ........ ........ */ /* 00000... ........ ........ ........ ........ */ diff --git a/contrib/unbound/sldns/str2wire.c b/contrib/unbound/sldns/str2wire.c index b4f84faf9b3b..f84d7d6b823b 100644 --- a/contrib/unbound/sldns/str2wire.c +++ b/contrib/unbound/sldns/str2wire.c @@ -1190,6 +1190,10 @@ int sldns_str2wire_b64_buf(const char* str, uint8_t* rd, size_t* len) { size_t sz = sldns_b64_pton_calculate_size(strlen(str)); int n; + if(strcmp(str, "0") == 0) { + *len = 0; + return LDNS_WIREPARSE_ERR_OK; + } if(*len < sz) return LDNS_WIREPARSE_ERR_BUFFER_TOO_SMALL; n = sldns_b64_pton(str, rd, *len); @@ -1223,6 +1227,10 @@ int sldns_str2wire_hex_buf(const char* str, uint8_t* rd, size_t* len) s++; continue; } + if(dlen == 0 && *s == '0' && *(s+1) == 0) { + *len = 0; + return LDNS_WIREPARSE_ERR_OK; + } if(!isxdigit((unsigned char)*s)) return RET_ERR(LDNS_WIREPARSE_ERR_SYNTAX_HEX, s-str); if(*len < dlen/2 + 1) @@ -1685,12 +1693,15 @@ int sldns_str2wire_wks_buf(const char* str, uint8_t* rd, size_t* len) struct protoent *p = getprotobyname(token); have_proto = 1; if(p) rd[0] = (uint8_t)p->p_proto; + else if(strcasecmp(token, "tcp")==0) rd[0]=6; + else if(strcasecmp(token, "udp")==0) rd[0]=17; else rd[0] = (uint8_t)atoi(token); (void)strlcpy(proto_str, token, sizeof(proto_str)); } else { int serv_port; struct servent *serv = getservbyname(token, proto_str); if(serv) serv_port=(int)ntohs((uint16_t)serv->s_port); + else if(strcasecmp(token, "domain")==0) serv_port=53; else { serv_port = atoi(token); if(serv_port == 0 && strcmp(token, "0") != 0) { diff --git a/contrib/unbound/sldns/wire2str.c b/contrib/unbound/sldns/wire2str.c index 78d2b94c0fd3..781482cd4455 100644 --- a/contrib/unbound/sldns/wire2str.c +++ b/contrib/unbound/sldns/wire2str.c @@ -1220,11 +1220,17 @@ static int sldns_wire2str_b64_scan_num(uint8_t** d, size_t* dl, char** s, int sldns_wire2str_b64_scan(uint8_t** d, size_t* dl, char** s, size_t* sl) { + if(*dl == 0) { + return sldns_str_print(s, sl, "0"); + } return sldns_wire2str_b64_scan_num(d, dl, s, sl, *dl); } int sldns_wire2str_hex_scan(uint8_t** d, size_t* dl, char** s, size_t* sl) { + if(*dl == 0) { + return sldns_str_print(s, sl, "0"); + } return print_remainder_hex("", d, dl, s, sl); } @@ -1465,6 +1471,10 @@ int sldns_wire2str_wks_scan(uint8_t** d, size_t* dl, char** s, size_t* sl) if(protocol && (protocol->p_name != NULL)) { w += sldns_str_print(s, sl, "%s", protocol->p_name); proto_name = protocol->p_name; + } else if(protocol_nr == 6) { + w += sldns_str_print(s, sl, "tcp"); + } else if(protocol_nr == 17) { + w += sldns_str_print(s, sl, "udp"); } else { w += sldns_str_print(s, sl, "%u", (unsigned)protocol_nr); } diff --git a/contrib/unbound/smallapp/unbound-anchor.c b/contrib/unbound/smallapp/unbound-anchor.c index bdebe7192a84..437f185373ed 100644 --- a/contrib/unbound/smallapp/unbound-anchor.c +++ b/contrib/unbound/smallapp/unbound-anchor.c @@ -2319,7 +2319,9 @@ int main(int argc, char* argv[]) #ifdef HAVE_ERR_LOAD_CRYPTO_STRINGS ERR_load_crypto_strings(); #endif +#if OPENSSL_VERSION_NUMBER < 0x10100000 || !defined(HAVE_OPENSSL_INIT_SSL) ERR_load_SSL_strings(); +#endif #if OPENSSL_VERSION_NUMBER < 0x10100000 || !defined(HAVE_OPENSSL_INIT_CRYPTO) OpenSSL_add_all_algorithms(); #else @@ -2330,7 +2332,7 @@ int main(int argc, char* argv[]) #if OPENSSL_VERSION_NUMBER < 0x10100000 || !defined(HAVE_OPENSSL_INIT_SSL) (void)SSL_library_init(); #else - (void)OPENSSL_init_ssl(0, NULL); + (void)OPENSSL_init_ssl(OPENSSL_INIT_LOAD_SSL_STRINGS, NULL); #endif if(dolist) do_list_builtin(); diff --git a/contrib/unbound/smallapp/unbound-checkconf.c b/contrib/unbound/smallapp/unbound-checkconf.c index 11df4415c5c5..7e9cb4740ae3 100644 --- a/contrib/unbound/smallapp/unbound-checkconf.c +++ b/contrib/unbound/smallapp/unbound-checkconf.c @@ -71,6 +71,9 @@ #ifdef WITH_PYTHONMODULE #include "pythonmod/pythonmod.h" #endif +#ifdef CLIENT_SUBNET +#include "edns-subnet/subnet-whitelist.h" +#endif /** Give checkconf usage, and exit (1). */ static void @@ -345,6 +348,20 @@ check_chroot_filelist_wild(const char* desc, struct config_strlist* list, } } +#ifdef CLIENT_SUBNET +/** check ECS configuration */ +static void +ecs_conf_checks(struct config_file* cfg) +{ + struct ecs_whitelist* whitelist = NULL; + if(!(whitelist = ecs_whitelist_create())) + fatal_exit("Could not create ednssubnet whitelist: out of memory"); + if(!ecs_whitelist_apply_cfg(whitelist, cfg)) + fatal_exit("Could not setup ednssubnet whitelist"); + ecs_whitelist_delete(whitelist); +} +#endif /* CLIENT_SUBNET */ + /** check configuration for errors */ static void morechecks(struct config_file* cfg, const char* fname) @@ -427,8 +444,11 @@ morechecks(struct config_file* cfg, const char* fname) check_chroot_string("dlv-anchor-file", &cfg->dlv_anchor_file, cfg->chrootdir, cfg); #ifdef USE_IPSECMOD - check_chroot_string("ipsecmod-hook", &cfg->ipsecmod_hook, cfg->chrootdir, - cfg); + if(cfg->ipsecmod_enabled && strstr(cfg->module_conf, "ipsecmod")) { + /* only check hook if enabled */ + check_chroot_string("ipsecmod-hook", &cfg->ipsecmod_hook, + cfg->chrootdir, cfg); + } #endif /* remove chroot setting so that modules are not stripping pathnames*/ free(cfg->chrootdir); @@ -474,6 +494,8 @@ morechecks(struct config_file* cfg, const char* fname) #ifdef CLIENT_SUBNET && strcmp(cfg->module_conf, "subnetcache iterator") != 0 && strcmp(cfg->module_conf, "subnetcache validator iterator") != 0 + && strcmp(cfg->module_conf, "dns64 subnetcache iterator") != 0 + && strcmp(cfg->module_conf, "dns64 subnetcache validator iterator") != 0 #endif #if defined(WITH_PYTHONMODULE) && defined(CLIENT_SUBNET) && strcmp(cfg->module_conf, "python subnetcache iterator") != 0 @@ -524,6 +546,9 @@ morechecks(struct config_file* cfg, const char* fname) localzonechecks(cfg); view_and_respipchecks(cfg); +#ifdef CLIENT_SUBNET + ecs_conf_checks(cfg); +#endif } /** check forwards */ diff --git a/contrib/unbound/smallapp/unbound-control.c b/contrib/unbound/smallapp/unbound-control.c index aa2db4a61dfb..4b3efc134dc0 100644 --- a/contrib/unbound/smallapp/unbound-control.c +++ b/contrib/unbound/smallapp/unbound-control.c @@ -207,7 +207,7 @@ static void pr_stats(const char* nm, struct ub_stats_info* s) PR_UL_NM("num.dnscrypt.cleartext", s->svr.num_query_dnscrypt_cleartext); PR_UL_NM("num.dnscrypt.malformed", s->svr.num_query_dnscrypt_crypted_malformed); -#endif +#endif /* USE_DNSCRYPT */ printf("%s.requestlist.avg"SQ"%g\n", nm, (s->svr.num_queries_missed_cache+s->svr.num_queries_prefetch)? (double)s->svr.sum_query_list_size/ @@ -251,6 +251,10 @@ static void print_mem(struct ub_shm_stat_info* shm_stat) #ifdef USE_IPSECMOD PR_LL("mem.mod.ipsecmod", shm_stat->mem.ipsecmod); #endif +#ifdef USE_DNSCRYPT + PR_LL("mem.cache.dnscrypt_shared_secret", + shm_stat->mem.dnscrypt_shared_secret); +#endif } /** print histogram */ @@ -337,6 +341,8 @@ static void print_extended(struct ub_stats_info* s) if(!inhibit_zero || s->svr.ans_rcode_nodata) { PR_UL("num.answer.rcode.nodata", s->svr.ans_rcode_nodata); } + /* iteration */ + PR_UL("num.query.ratelimited", s->svr.queries_ratelimited); /* validation */ PR_UL("num.answer.secure", s->svr.ans_secure); PR_UL("num.answer.bogus", s->svr.ans_bogus); @@ -349,6 +355,12 @@ static void print_extended(struct ub_stats_info* s) PR_UL("rrset.cache.count", s->svr.rrset_cache_count); PR_UL("infra.cache.count", s->svr.infra_cache_count); PR_UL("key.cache.count", s->svr.key_cache_count); +#ifdef USE_DNSCRYPT + PR_UL("dnscrypt_shared_secret.cache.count", + s->svr.shared_secret_cache_count); + PR_UL("num.query.dnscrypt.shared_secret.cachemiss", + s->svr.num_query_dnscrypt_secret_missed_cache); +#endif /* USE_DNSCRYPT */ } /** print statistics out of memory structures */ @@ -356,7 +368,7 @@ static void do_stats_shm(struct config_file* cfg, struct ub_stats_info* stats, struct ub_shm_stat_info* shm_stat) { int i; - char nm[16]; + char nm[32]; for(i=0; inum_threads; i++) { snprintf(nm, sizeof(nm), "thread%d", i); pr_stats(nm, &stats[i+1]); @@ -763,7 +775,9 @@ int main(int argc, char* argv[]) #ifdef HAVE_ERR_LOAD_CRYPTO_STRINGS ERR_load_crypto_strings(); #endif +#if OPENSSL_VERSION_NUMBER < 0x10100000 || !defined(HAVE_OPENSSL_INIT_SSL) ERR_load_SSL_strings(); +#endif #if OPENSSL_VERSION_NUMBER < 0x10100000 || !defined(HAVE_OPENSSL_INIT_CRYPTO) OpenSSL_add_all_algorithms(); #else @@ -774,7 +788,7 @@ int main(int argc, char* argv[]) #if OPENSSL_VERSION_NUMBER < 0x10100000 || !defined(HAVE_OPENSSL_INIT_SSL) (void)SSL_library_init(); #else - (void)OPENSSL_init_ssl(0, NULL); + (void)OPENSSL_init_ssl(OPENSSL_INIT_LOAD_SSL_STRINGS, NULL); #endif if(!RAND_status()) { diff --git a/contrib/unbound/util/config_file.c b/contrib/unbound/util/config_file.c index f7a62fbd7e0e..f40993c89272 100644 --- a/contrib/unbound/util/config_file.c +++ b/contrib/unbound/util/config_file.c @@ -282,6 +282,8 @@ config_create(void) cfg->dnscrypt_provider = NULL; cfg->dnscrypt_provider_cert = NULL; cfg->dnscrypt_secret_key = NULL; + cfg->dnscrypt_shared_secret_cache_size = 4*1024*1024; + cfg->dnscrypt_shared_secret_cache_slabs = 4; #ifdef USE_IPSECMOD cfg->ipsecmod_enabled = 1; cfg->ipsecmod_ignore_bogus = 0; @@ -289,6 +291,10 @@ config_create(void) cfg->ipsecmod_max_ttl = 3600; cfg->ipsecmod_whitelist = NULL; cfg->ipsecmod_strict = 0; +#endif +#ifdef USE_CACHEDB + cfg->cachedb_backend = NULL; + cfg->cachedb_secret = NULL; #endif return cfg; error_exit: @@ -561,6 +567,10 @@ int config_set_option(struct config_file* cfg, const char* opt, else S_STR("dnscrypt-provider:", dnscrypt_provider) else S_STRLIST("dnscrypt-provider-cert:", dnscrypt_provider_cert) else S_STRLIST("dnscrypt-secret-key:", dnscrypt_secret_key) + else S_MEMSIZE("dnscrypt-shared-secret-cache-size:", + dnscrypt_shared_secret_cache_size) + else S_POW2("dnscrypt-shared-secret-cache-slabs:", + dnscrypt_shared_secret_cache_slabs) #endif else if(strcmp(opt, "ip-ratelimit:") == 0) { IS_NUMBER_OR_ZERO; cfg->ip_ratelimit = atoi(val); @@ -922,6 +932,10 @@ config_get_option(struct config_file* cfg, const char* opt, else O_STR(opt, "dnscrypt-provider", dnscrypt_provider) else O_LST(opt, "dnscrypt-provider-cert", dnscrypt_provider_cert) else O_LST(opt, "dnscrypt-secret-key", dnscrypt_secret_key) + else O_MEM(opt, "dnscrypt-shared-secret-cache-size", + dnscrypt_shared_secret_cache_size) + else O_DEC(opt, "dnscrypt-shared-secret-cache-slabs", + dnscrypt_shared_secret_cache_slabs) #endif else O_YNO(opt, "unblock-lan-zones", unblock_lan_zones) else O_YNO(opt, "insecure-lan-zones", insecure_lan_zones) @@ -957,6 +971,10 @@ config_get_option(struct config_file* cfg, const char* opt, else O_DEC(opt, "ipsecmod-max-ttl", ipsecmod_max_ttl) else O_LST(opt, "ipsecmod-whitelist", ipsecmod_whitelist) else O_YNO(opt, "ipsecmod-strict", ipsecmod_strict) +#endif +#ifdef USE_CACHEDB + else O_STR(opt, "backend", cachedb_backend) + else O_STR(opt, "secret-seed", cachedb_secret) #endif /* not here: * outgoing-permit, outgoing-avoid - have list of ports @@ -1258,6 +1276,10 @@ config_delete(struct config_file* cfg) #ifdef USE_IPSECMOD free(cfg->ipsecmod_hook); config_delstrlist(cfg->ipsecmod_whitelist); +#endif +#ifdef USE_CACHEDB + free(cfg->cachedb_backend); + free(cfg->cachedb_secret); #endif free(cfg); } diff --git a/contrib/unbound/util/config_file.h b/contrib/unbound/util/config_file.h index bb7a292050b4..fdc48111e30a 100644 --- a/contrib/unbound/util/config_file.h +++ b/contrib/unbound/util/config_file.h @@ -464,6 +464,10 @@ struct config_file { struct config_strlist* dnscrypt_secret_key; /** dnscrypt provider certs 1.cert */ struct config_strlist* dnscrypt_provider_cert; + /** memory size in bytes for dnscrypt shared secrets cache */ + size_t dnscrypt_shared_secret_cache_size; + /** number of slabs for dnscrypt shared secrets cache */ + size_t dnscrypt_shared_secret_cache_slabs; /** IPsec module */ #ifdef USE_IPSECMOD @@ -480,6 +484,14 @@ struct config_file { /** false to proceed even when ipsecmod_hook fails */ int ipsecmod_strict; #endif + + /* cachedb module */ +#ifdef USE_CACHEDB + /** backend DB name */ + char* cachedb_backend; + /** secret seed for hash key calculation */ + char* cachedb_secret; +#endif }; /** from cfg username, after daemonise setup performed */ diff --git a/contrib/unbound/util/configlexer.lex b/contrib/unbound/util/configlexer.lex index da8dd912de40..b1b7982d36f7 100644 --- a/contrib/unbound/util/configlexer.lex +++ b/contrib/unbound/util/configlexer.lex @@ -418,12 +418,19 @@ dnscrypt-port{COLON} { YDVAR(1, VAR_DNSCRYPT_PORT) } dnscrypt-provider{COLON} { YDVAR(1, VAR_DNSCRYPT_PROVIDER) } dnscrypt-secret-key{COLON} { YDVAR(1, VAR_DNSCRYPT_SECRET_KEY) } dnscrypt-provider-cert{COLON} { YDVAR(1, VAR_DNSCRYPT_PROVIDER_CERT) } +dnscrypt-shared-secret-cache-size{COLON} { + YDVAR(1, VAR_DNSCRYPT_SHARED_SECRET_CACHE_SIZE) } +dnscrypt-shared-secret-cache-slabs{COLON} { + YDVAR(1, VAR_DNSCRYPT_SHARED_SECRET_CACHE_SLABS) } ipsecmod-enabled{COLON} { YDVAR(1, VAR_IPSECMOD_ENABLED) } ipsecmod-ignore-bogus{COLON} { YDVAR(1, VAR_IPSECMOD_IGNORE_BOGUS) } ipsecmod-hook{COLON} { YDVAR(1, VAR_IPSECMOD_HOOK) } ipsecmod-max-ttl{COLON} { YDVAR(1, VAR_IPSECMOD_MAX_TTL) } ipsecmod-whitelist{COLON} { YDVAR(1, VAR_IPSECMOD_WHITELIST) } ipsecmod-strict{COLON} { YDVAR(1, VAR_IPSECMOD_STRICT) } +cachedb{COLON} { YDVAR(0, VAR_CACHEDB) } +backend{COLON} { YDVAR(1, VAR_CACHEDB_BACKEND) } +secret-seed{COLON} { YDVAR(1, VAR_CACHEDB_SECRETSEED) } {NEWLINE} { LEXOUT(("NL\n")); cfg_parser->line++; } /* Quoted strings. Strip leading and ending quotes */ diff --git a/contrib/unbound/util/configparser.y b/contrib/unbound/util/configparser.y index 7c8161442ccd..7b41b1d767d6 100644 --- a/contrib/unbound/util/configparser.y +++ b/contrib/unbound/util/configparser.y @@ -144,8 +144,11 @@ extern struct config_parser_state* cfg_parser; %token VAR_USE_SYSTEMD VAR_SHM_ENABLE VAR_SHM_KEY %token VAR_DNSCRYPT VAR_DNSCRYPT_ENABLE VAR_DNSCRYPT_PORT VAR_DNSCRYPT_PROVIDER %token VAR_DNSCRYPT_SECRET_KEY VAR_DNSCRYPT_PROVIDER_CERT +%token VAR_DNSCRYPT_SHARED_SECRET_CACHE_SIZE +%token VAR_DNSCRYPT_SHARED_SECRET_CACHE_SLABS %token VAR_IPSECMOD_ENABLED VAR_IPSECMOD_HOOK VAR_IPSECMOD_IGNORE_BOGUS %token VAR_IPSECMOD_MAX_TTL VAR_IPSECMOD_WHITELIST VAR_IPSECMOD_STRICT +%token VAR_CACHEDB VAR_CACHEDB_BACKEND VAR_CACHEDB_SECRETSEED %% toplevelvars: /* empty */ | toplevelvars toplevelvar ; @@ -153,7 +156,8 @@ toplevelvar: serverstart contents_server | stubstart contents_stub | forwardstart contents_forward | pythonstart contents_py | rcstart contents_rc | dtstart contents_dt | viewstart contents_view | - dnscstart contents_dnsc + dnscstart contents_dnsc | + cachedbstart contents_cachedb ; /* server: declaration */ @@ -2321,7 +2325,9 @@ contents_dnsc: contents_dnsc content_dnsc | ; content_dnsc: dnsc_dnscrypt_enable | dnsc_dnscrypt_port | dnsc_dnscrypt_provider | - dnsc_dnscrypt_secret_key | dnsc_dnscrypt_provider_cert + dnsc_dnscrypt_secret_key | dnsc_dnscrypt_provider_cert | + dnsc_dnscrypt_shared_secret_cache_size | + dnsc_dnscrypt_shared_secret_cache_slabs ; dnsc_dnscrypt_enable: VAR_DNSCRYPT_ENABLE STRING_ARG { @@ -2364,6 +2370,65 @@ dnsc_dnscrypt_secret_key: VAR_DNSCRYPT_SECRET_KEY STRING_ARG fatal_exit("out of memory adding dnscrypt-secret-key"); } ; +dnsc_dnscrypt_shared_secret_cache_size: VAR_DNSCRYPT_SHARED_SECRET_CACHE_SIZE STRING_ARG + { + OUTYY(("P(dnscrypt_shared_secret_cache_size:%s)\n", $2)); + if(!cfg_parse_memsize($2, &cfg_parser->cfg->dnscrypt_shared_secret_cache_size)) + yyerror("memory size expected"); + free($2); + } + ; +dnsc_dnscrypt_shared_secret_cache_slabs: VAR_DNSCRYPT_SHARED_SECRET_CACHE_SLABS STRING_ARG + { + OUTYY(("P(dnscrypt_shared_secret_cache_slabs:%s)\n", $2)); + if(atoi($2) == 0) + yyerror("number expected"); + else { + cfg_parser->cfg->dnscrypt_shared_secret_cache_slabs = atoi($2); + if(!is_pow2(cfg_parser->cfg->dnscrypt_shared_secret_cache_slabs)) + yyerror("must be a power of 2"); + } + free($2); + } + ; +cachedbstart: VAR_CACHEDB + { + OUTYY(("\nP(cachedb:)\n")); + } + ; +contents_cachedb: contents_cachedb content_cachedb + | ; +content_cachedb: cachedb_backend_name | cachedb_secret_seed + ; +cachedb_backend_name: VAR_CACHEDB_BACKEND STRING_ARG + { + #ifdef USE_CACHEDB + OUTYY(("P(backend:%s)\n", $2)); + if(cfg_parser->cfg->cachedb_backend) + yyerror("cachedb backend override, there must be one " + "backend"); + free(cfg_parser->cfg->cachedb_backend); + cfg_parser->cfg->cachedb_backend = $2; + #else + OUTYY(("P(Compiled without cachedb, ignoring)\n")); + #endif + } + ; +cachedb_secret_seed: VAR_CACHEDB_SECRETSEED STRING_ARG + { + #ifdef USE_CACHEDB + OUTYY(("P(secret-seed:%s)\n", $2)); + if(cfg_parser->cfg->cachedb_secret) + yyerror("cachedb secret-seed override, there must be " + "only one secret"); + free(cfg_parser->cfg->cachedb_secret); + cfg_parser->cfg->cachedb_secret = $2; + #else + OUTYY(("P(Compiled without cachedb, ignoring)\n")); + free($2); + #endif + } + ; %% /* parse helper routines could be here */ diff --git a/contrib/unbound/util/data/msgreply.c b/contrib/unbound/util/data/msgreply.c index 2ce898d7f031..6d80cce4cb50 100644 --- a/contrib/unbound/util/data/msgreply.c +++ b/contrib/unbound/util/data/msgreply.c @@ -840,7 +840,9 @@ log_reply_info(enum verbosity_value v, struct query_info *qinf, { log_info("%s - - - %s - - - ", clientip_buf, rcode_buf); } else { - dname_str(qinf->qname, qname_buf); + if(qinf->qname) + dname_str(qinf->qname, qname_buf); + else snprintf(qname_buf, sizeof(qname_buf), "null"); pktlen = sldns_buffer_limit(rmsg); sldns_wire2str_type_buf(qinf->qtype, type_buf, sizeof(type_buf)); sldns_wire2str_class_buf(qinf->qclass, class_buf, sizeof(class_buf)); diff --git a/contrib/unbound/util/fptr_wlist.c b/contrib/unbound/util/fptr_wlist.c index 2797d1fe8449..81ef487c5877 100644 --- a/contrib/unbound/util/fptr_wlist.c +++ b/contrib/unbound/util/fptr_wlist.c @@ -230,6 +230,9 @@ fptr_whitelist_hash_sizefunc(lruhash_sizefunc_type fptr) else if(fptr == &test_slabhash_sizefunc) return 1; #ifdef CLIENT_SUBNET else if(fptr == &msg_cache_sizefunc) return 1; +#endif +#ifdef USE_DNSCRYPT + else if(fptr == &dnsc_shared_secrets_sizefunc) return 1; #endif return 0; } @@ -244,6 +247,9 @@ fptr_whitelist_hash_compfunc(lruhash_compfunc_type fptr) else if(fptr == &rate_compfunc) return 1; else if(fptr == &ip_rate_compfunc) return 1; else if(fptr == &test_slabhash_compfunc) return 1; +#ifdef USE_DNSCRYPT + else if(fptr == &dnsc_shared_secrets_compfunc) return 1; +#endif return 0; } @@ -257,6 +263,9 @@ fptr_whitelist_hash_delkeyfunc(lruhash_delkeyfunc_type fptr) else if(fptr == &rate_delkeyfunc) return 1; else if(fptr == &ip_rate_delkeyfunc) return 1; else if(fptr == &test_slabhash_delkey) return 1; +#ifdef USE_DNSCRYPT + else if(fptr == &dnsc_shared_secrets_delkeyfunc) return 1; +#endif return 0; } @@ -271,6 +280,9 @@ fptr_whitelist_hash_deldatafunc(lruhash_deldatafunc_type fptr) else if(fptr == &test_slabhash_deldata) return 1; #ifdef CLIENT_SUBNET else if(fptr == &subnet_data_delete) return 1; +#endif +#ifdef USE_DNSCRYPT + else if(fptr == &dnsc_shared_secrets_deldatafunc) return 1; #endif return 0; } diff --git a/contrib/unbound/util/iana_ports.inc b/contrib/unbound/util/iana_ports.inc index dba3e62270c6..58c69fd1c1a7 100644 --- a/contrib/unbound/util/iana_ports.inc +++ b/contrib/unbound/util/iana_ports.inc @@ -2696,7 +2696,6 @@ 3068, 3069, 3070, -3071, 3072, 3073, 3074, @@ -4733,6 +4732,7 @@ 8003, 8005, 8006, +8007, 8008, 8019, 8020, @@ -4744,6 +4744,7 @@ 8033, 8034, 8040, +8041, 8052, 8053, 8054, diff --git a/contrib/unbound/util/net_help.c b/contrib/unbound/util/net_help.c index 6c0d68e312b8..ce136a337cff 100644 --- a/contrib/unbound/util/net_help.c +++ b/contrib/unbound/util/net_help.c @@ -114,8 +114,9 @@ fd_set_block(int s) #elif defined(HAVE_IOCTLSOCKET) unsigned long off = 0; if(ioctlsocket(s, FIONBIO, &off) != 0) { - log_err("can't ioctlsocket FIONBIO off: %s", - wsa_strerror(WSAGetLastError())); + if(WSAGetLastError() != WSAEINVAL || verbosity >= 4) + log_err("can't ioctlsocket FIONBIO off: %s", + wsa_strerror(WSAGetLastError())); } #endif return 1; @@ -610,6 +611,88 @@ log_crypto_err(const char* str) #endif /* HAVE_SSL */ } +int +listen_sslctx_setup(void* ctxt) +{ +#ifdef HAVE_SSL + SSL_CTX* ctx = (SSL_CTX*)ctxt; + /* no SSLv2, SSLv3 because has defects */ + if((SSL_CTX_set_options(ctx, SSL_OP_NO_SSLv2) & SSL_OP_NO_SSLv2) + != SSL_OP_NO_SSLv2){ + log_crypto_err("could not set SSL_OP_NO_SSLv2"); + return 0; + } + if((SSL_CTX_set_options(ctx, SSL_OP_NO_SSLv3) & SSL_OP_NO_SSLv3) + != SSL_OP_NO_SSLv3){ + log_crypto_err("could not set SSL_OP_NO_SSLv3"); + return 0; + } +#if defined(SSL_OP_NO_TLSv1) && defined(SSL_OP_NO_TLSv1_1) + /* if we have tls 1.1 disable 1.0 */ + if((SSL_CTX_set_options(ctx, SSL_OP_NO_TLSv1) & SSL_OP_NO_TLSv1) + != SSL_OP_NO_TLSv1){ + log_crypto_err("could not set SSL_OP_NO_TLSv1"); + return 0; + } +#endif +#if defined(SSL_OP_NO_TLSv1_1) && defined(SSL_OP_NO_TLSv1_2) + /* if we have tls 1.2 disable 1.1 */ + if((SSL_CTX_set_options(ctx, SSL_OP_NO_TLSv1_1) & SSL_OP_NO_TLSv1_1) + != SSL_OP_NO_TLSv1_1){ + log_crypto_err("could not set SSL_OP_NO_TLSv1_1"); + return 0; + } +#endif +#if defined(SHA256_DIGEST_LENGTH) && defined(USE_ECDSA) + /* if we have sha256, set the cipher list to have no known vulns */ + if(!SSL_CTX_set_cipher_list(ctx, "ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256")) + log_crypto_err("could not set cipher list with SSL_CTX_set_cipher_list"); +#endif + + if((SSL_CTX_set_options(ctx, SSL_OP_CIPHER_SERVER_PREFERENCE) & + SSL_OP_CIPHER_SERVER_PREFERENCE) != + SSL_OP_CIPHER_SERVER_PREFERENCE) { + log_crypto_err("could not set SSL_OP_CIPHER_SERVER_PREFERENCE"); + return 0; + } + +#ifdef HAVE_SSL_CTX_SET_SECURITY_LEVEL + SSL_CTX_set_security_level(ctx, 0); +#endif +#else + (void)ctxt; +#endif /* HAVE_SSL */ + return 1; +} + +void +listen_sslctx_setup_2(void* ctxt) +{ +#ifdef HAVE_SSL + SSL_CTX* ctx = (SSL_CTX*)ctxt; + (void)ctx; +#if HAVE_DECL_SSL_CTX_SET_ECDH_AUTO + if(!SSL_CTX_set_ecdh_auto(ctx,1)) { + log_crypto_err("Error in SSL_CTX_ecdh_auto, not enabling ECDHE"); + } +#elif defined(USE_ECDSA) + if(1) { + EC_KEY *ecdh = EC_KEY_new_by_curve_name (NID_X9_62_prime256v1); + if (!ecdh) { + log_crypto_err("could not find p256, not enabling ECDHE"); + } else { + if (1 != SSL_CTX_set_tmp_ecdh (ctx, ecdh)) { + log_crypto_err("Error in SSL_CTX_set_tmp_ecdh, not enabling ECDHE"); + } + EC_KEY_free (ecdh); + } + } +#endif +#else + (void)ctxt; +#endif /* HAVE_SSL */ +} + void* listen_sslctx_create(char* key, char* pem, char* verifypem) { #ifdef HAVE_SSL @@ -618,16 +701,7 @@ void* listen_sslctx_create(char* key, char* pem, char* verifypem) log_crypto_err("could not SSL_CTX_new"); return NULL; } - /* no SSLv2, SSLv3 because has defects */ - if((SSL_CTX_set_options(ctx, SSL_OP_NO_SSLv2) & SSL_OP_NO_SSLv2) - != SSL_OP_NO_SSLv2){ - log_crypto_err("could not set SSL_OP_NO_SSLv2"); - SSL_CTX_free(ctx); - return NULL; - } - if((SSL_CTX_set_options(ctx, SSL_OP_NO_SSLv3) & SSL_OP_NO_SSLv3) - != SSL_OP_NO_SSLv3){ - log_crypto_err("could not set SSL_OP_NO_SSLv3"); + if(!listen_sslctx_setup(ctx)) { SSL_CTX_free(ctx); return NULL; } @@ -649,24 +723,7 @@ void* listen_sslctx_create(char* key, char* pem, char* verifypem) SSL_CTX_free(ctx); return NULL; } -#if HAVE_DECL_SSL_CTX_SET_ECDH_AUTO - if(!SSL_CTX_set_ecdh_auto(ctx,1)) { - log_crypto_err("Error in SSL_CTX_ecdh_auto, not enabling ECDHE"); - } -#elif defined(USE_ECDSA) - if(1) { - EC_KEY *ecdh = EC_KEY_new_by_curve_name (NID_X9_62_prime256v1); - if (!ecdh) { - log_crypto_err("could not find p256, not enabling ECDHE"); - } else { - if (1 != SSL_CTX_set_tmp_ecdh (ctx, ecdh)) { - log_crypto_err("Error in SSL_CTX_set_tmp_ecdh, not enabling ECDHE"); - } - EC_KEY_free (ecdh); - } - } -#endif - + listen_sslctx_setup_2(ctx); if(verifypem && verifypem[0]) { if(!SSL_CTX_load_verify_locations(ctx, verifypem, NULL)) { log_crypto_err("Error in SSL_CTX verify locations"); diff --git a/contrib/unbound/util/net_help.h b/contrib/unbound/util/net_help.h index 54f4c9c0e7cd..f0236e5335df 100644 --- a/contrib/unbound/util/net_help.h +++ b/contrib/unbound/util/net_help.h @@ -345,6 +345,19 @@ void sock_list_merge(struct sock_list** list, struct regional* region, */ void log_crypto_err(const char* str); +/** + * Set SSL_OP_NOxxx options on SSL context to disable bad crypto + * @param ctxt: SSL_CTX* + * @return false on failure. + */ +int listen_sslctx_setup(void* ctxt); + +/** + * Further setup of listening SSL context, after keys loaded. + * @param ctxt: SSL_CTX* + */ +void listen_sslctx_setup_2(void* ctxt); + /** * create SSL listen context * @param key: private key file. diff --git a/contrib/unbound/util/netevent.c b/contrib/unbound/util/netevent.c index 6990cdb36f36..771cb6bc7101 100644 --- a/contrib/unbound/util/netevent.c +++ b/contrib/unbound/util/netevent.c @@ -1551,6 +1551,13 @@ comm_point_tcp_handle_callback(int fd, short event, void* arg) c->dnscrypt_buffer = sldns_buffer_new(sldns_buffer_capacity(c->buffer)); if(!c->dnscrypt_buffer) { log_err("Could not allocate dnscrypt buffer"); + reclaim_tcp_handler(c); + if(!c->tcp_do_close) { + fptr_ok(fptr_whitelist_comm_point( + c->callback)); + (void)(*c->callback)(c, c->cb_arg, + NETEVENT_CLOSED, NULL); + } return; } } diff --git a/contrib/unbound/util/shm_side/shm_main.c b/contrib/unbound/util/shm_side/shm_main.c index bba2a8396333..c0757ed7cdef 100644 --- a/contrib/unbound/util/shm_side/shm_main.c +++ b/contrib/unbound/util/shm_side/shm_main.c @@ -249,6 +249,13 @@ void shm_main_run(struct worker *worker) shm_stat->mem.msg = (long long)slabhash_get_mem(worker->env.msg_cache); shm_stat->mem.rrset = (long long)slabhash_get_mem(&worker->env.rrset_cache->table); + shm_stat->mem.dnscrypt_shared_secret = 0; +#ifdef USE_DNSCRYPT + if(worker->daemon->dnscenv) { + shm_stat->mem.dnscrypt_shared_secret = (long long)slabhash_get_mem( + worker->daemon->dnscenv->shared_secrets_cache); + } +#endif shm_stat->mem.val = (long long)mod_get_mem(&worker->env, "validator"); shm_stat->mem.iter = (long long)mod_get_mem(&worker->env, diff --git a/contrib/unbound/util/storage/lookup3.c b/contrib/unbound/util/storage/lookup3.c index e9b05af37e31..cc110748156f 100644 --- a/contrib/unbound/util/storage/lookup3.c +++ b/contrib/unbound/util/storage/lookup3.c @@ -5,6 +5,7 @@ added #ifdef VALGRIND to remove 298,384,660 'unused variable k8' warnings. added include of lookup3.h to check definitions match declarations. removed include of stdint - config.h takes care of platform independence. + added fallthrough comments for new gcc warning suppression. url http://burtleburtle.net/bob/hash/index.html. */ /* @@ -235,7 +236,9 @@ uint32_t initval) /* the previous hash, or an arbitrary value */ switch(length) /* all the case statements fall through */ { case 3 : c+=k[2]; + /* fallthrough */ case 2 : b+=k[1]; + /* fallthrough */ case 1 : a+=k[0]; final(a,b,c); case 0: /* case 0: nothing left to add */ @@ -473,16 +476,27 @@ uint32_t hashlittle( const void *key, size_t length, uint32_t initval) switch(length) /* all the case statements fall through */ { case 12: c+=((uint32_t)k[11])<<24; + /* fallthrough */ case 11: c+=((uint32_t)k[10])<<16; + /* fallthrough */ case 10: c+=((uint32_t)k[9])<<8; + /* fallthrough */ case 9 : c+=k[8]; + /* fallthrough */ case 8 : b+=((uint32_t)k[7])<<24; + /* fallthrough */ case 7 : b+=((uint32_t)k[6])<<16; + /* fallthrough */ case 6 : b+=((uint32_t)k[5])<<8; + /* fallthrough */ case 5 : b+=k[4]; + /* fallthrough */ case 4 : a+=((uint32_t)k[3])<<24; + /* fallthrough */ case 3 : a+=((uint32_t)k[2])<<16; + /* fallthrough */ case 2 : a+=((uint32_t)k[1])<<8; + /* fallthrough */ case 1 : a+=k[0]; break; case 0 : return c; diff --git a/contrib/unbound/validator/val_secalgo.c b/contrib/unbound/validator/val_secalgo.c index 88d23472118f..e9ec5a5b5879 100644 --- a/contrib/unbound/validator/val_secalgo.c +++ b/contrib/unbound/validator/val_secalgo.c @@ -1320,6 +1320,9 @@ verify_canonrrset(sldns_buffer* buf, int algo, unsigned char* sigblock, #include "ecdsa.h" #include "ecc-curve.h" #endif +#ifdef HAVE_NETTLE_EDDSA_H +#include "eddsa.h" +#endif static int _digest_nettle(int algo, uint8_t* buf, size_t len, @@ -1477,6 +1480,10 @@ dnskey_algo_id_is_supported(int id) case LDNS_ECDSAP384SHA384: #endif return 1; +#ifdef USE_ED25519 + case LDNS_ED25519: + return 1; +#endif case LDNS_RSAMD5: /* RFC 6725 deprecates RSAMD5 */ case LDNS_ECC_GOST: default: @@ -1718,6 +1725,30 @@ _verify_nettle_ecdsa(sldns_buffer* buf, unsigned int digest_size, unsigned char* } #endif +#ifdef USE_ED25519 +static char * +_verify_nettle_ed25519(sldns_buffer* buf, unsigned char* sigblock, + unsigned int sigblock_len, unsigned char* key, unsigned int keylen) +{ + int res = 0; + + if(sigblock_len != ED25519_SIGNATURE_SIZE) { + return "wrong ED25519 signature length"; + } + if(keylen != ED25519_KEY_SIZE) { + return "wrong ED25519 key length"; + } + + res = ed25519_sha512_verify((uint8_t*)key, sldns_buffer_limit(buf), + sldns_buffer_begin(buf), (uint8_t*)sigblock); + + if (!res) + return "ED25519 signature verification failed"; + else + return NULL; +} +#endif + /** * Check a canonical sig+rrset and signature against a dnskey * @param buf: buffer with data to verify, the first rrsig part and the @@ -1759,9 +1790,13 @@ verify_canonrrset(sldns_buffer* buf, int algo, unsigned char* sigblock, case LDNS_RSASHA1_NSEC3: digest_size = (digest_size ? digest_size : SHA1_DIGEST_SIZE); #endif + /* double fallthrough annotation to please gcc parser */ + /* fallthrough */ #ifdef USE_SHA2 + /* fallthrough */ case LDNS_RSASHA256: digest_size = (digest_size ? digest_size : SHA256_DIGEST_SIZE); + /* fallthrough */ case LDNS_RSASHA512: digest_size = (digest_size ? digest_size : SHA512_DIGEST_SIZE); @@ -1776,6 +1811,7 @@ verify_canonrrset(sldns_buffer* buf, int algo, unsigned char* sigblock, #ifdef USE_ECDSA case LDNS_ECDSAP256SHA256: digest_size = (digest_size ? digest_size : SHA256_DIGEST_SIZE); + /* fallthrough */ case LDNS_ECDSAP384SHA384: digest_size = (digest_size ? digest_size : SHA384_DIGEST_SIZE); *reason = _verify_nettle_ecdsa(buf, digest_size, sigblock, @@ -1784,6 +1820,15 @@ verify_canonrrset(sldns_buffer* buf, int algo, unsigned char* sigblock, return sec_status_bogus; else return sec_status_secure; +#endif +#ifdef USE_ED25519 + case LDNS_ED25519: + *reason = _verify_nettle_ed25519(buf, sigblock, sigblock_len, + key, keylen); + if (*reason != NULL) + return sec_status_bogus; + else + return sec_status_secure; #endif case LDNS_RSAMD5: case LDNS_ECC_GOST: diff --git a/contrib/unbound/validator/val_utils.c b/contrib/unbound/validator/val_utils.c index e4eff1b2523b..973473f9dc85 100644 --- a/contrib/unbound/validator/val_utils.c +++ b/contrib/unbound/validator/val_utils.c @@ -932,17 +932,24 @@ val_check_nonsecure(struct module_env* env, struct reply_info* rep) * Therefore the message is bogus. */ - /* check if authority consists of only an NS record + /* check if authority has an NS record * which is bad, and there is an answer section with * data. In that case, delete NS and additional to * be lenient and make a minimal response */ - if(rep->an_numrrsets != 0 && rep->ns_numrrsets == 1 && + if(rep->an_numrrsets != 0 && ntohs(rep->rrsets[i]->rk.type) == LDNS_RR_TYPE_NS) { verbose(VERB_ALGO, "truncate to minimal"); - rep->ns_numrrsets = 0; rep->ar_numrrsets = 0; - rep->rrset_count = rep->an_numrrsets; + rep->rrset_count = rep->an_numrrsets + + rep->ns_numrrsets; + /* remove this unneeded authority rrset */ + memmove(rep->rrsets+i, rep->rrsets+i+1, + sizeof(struct ub_packed_rrset_key*)* + (rep->rrset_count - i - 1)); + rep->ns_numrrsets--; + rep->rrset_count--; + i--; return; }