Release 1.4.2

-----BEGIN PGP SIGNATURE-----
 
 iQIxBAABCAAbBQJa9XQrFBx3aWxsZW1AbmxuZXRsYWJzLm5sAAoJEOX4+CEvd6SY
 QjYP/1hDH9Y1+JZFVdcDk0JLrMhrhfnPq1RdefiEzXPwcoFvbahwb7G5ARXQCkUz
 dgiJoae1euaCeQQyscJ83Vv9zxRetxCquuaA6j3eeiR3HtVJr6ayGfg1JPHcgO+O
 S7IJkUuRcpSB7PK4f/FqyrnrJNSFUfN25y9WvXOS5mJBq1OX8QhqWHN63uHXKVQt
 lfipQE/WiQic07a1bObNJcdmot4M6cCa6QcSc1JS37dvvHCHZc0HQox/VCUJpqrr
 rx1hbRCZFZ3B+DY4Fded4rIZSYG9Y/J64X7IW5hdv2z2G//Q9YBf16rkzz6xcpA/
 CIniaFXNliaugkHD7Nag/D32yMpUhDnJt2BloNQodZNMPRzerfLj9R8IKOjjM+py
 vEe+xCyrs7s7TKyK9nSacyJ5BWZDE1vOKDF1tNHK9KzJ4YtfGtmxjjmB1VytNy6O
 BXs3ml/VSgVgBZbmcevWDXn6anByacKADDkiyVJ9PRCL2+qFOt3CR3t8GWlCwK5O
 GvrKmNkeUYfjyw03qCXXJ54Ti6xrmBJPcUeBE1NdTF7OgYhSyImhQqAnInG/Z3ZU
 c1j7pKYw2LNQ7F/CaW+AQ4HpizltIHRiBHhMvaArhp4idvyFMTr1YV7MrCWixqpx
 2fGSVuaLSYGOxsqM7m2lrbTckIESBAxX+f4vGj2nxP9qzna0
 =DfcS
 -----END PGP SIGNATURE-----

Merge tag 'v1.4.2'

Release 1.4.2
This commit is contained in:
Willem Toorop 2018-05-11 12:45:26 +02:00
commit 86e5c39159
12 changed files with 257 additions and 122 deletions

View File

@ -1,3 +1,19 @@
* 2018-05-11: Version 1.4.2
* Bugfix getdnsapi/stubby#106: Core dump when printing certain
configuration. Thanks Han Vinke
* Bugfix getdnsapi/stubby#99: Partly trace DNSSEC from the root
up (for tld and sld), to find insecure delegations quicker.
Thanks UniverseXXX
* Bugfix: Allow NSEC spans starting from (unexpanded) wildcards
Bug was introduced when dealing with CVE-2017-15105
* Bugfix getdnsapi/stubby#46: Don't assume trailing zero with
string bindata's. Thanks Lonnie Abelbeck
* Bugfix #394: Update src/compat/getentropy_linux.c in order to
handle ENOSYS (not implemented) fallback.
Thanks Brent Blood
* Bugfix #395: Clarify that libidn2 dependency is for version 2.0.0
or higher. Thanks mire3212
* 2018-03-12: Version 1.4.1 * 2018-03-12: Version 1.4.1
* Bugfix #388: Prevent fallback to an earlier tries upstream within a * Bugfix #388: Prevent fallback to an earlier tries upstream within a
single query. Thanks Robert Groenenberg single query. Thanks Robert Groenenberg

View File

@ -221,6 +221,8 @@ $(distdir):
mkdir -p $(distdir)/stubby/src mkdir -p $(distdir)/stubby/src
mkdir -p $(distdir)/stubby/src/yaml mkdir -p $(distdir)/stubby/src/yaml
mkdir -p $(distdir)/stubby/doc mkdir -p $(distdir)/stubby/doc
mkdir -p $(distdir)/stubby/systemd
mkdir -p $(distdir)/stubby/contrib/upstart
cp $(srcdir)/configure.ac $(distdir) cp $(srcdir)/configure.ac $(distdir)
cp $(srcdir)/configure $(distdir) cp $(srcdir)/configure $(distdir)
cp $(srcdir)/AUTHORS $(distdir) cp $(srcdir)/AUTHORS $(distdir)
@ -270,6 +272,10 @@ $(distdir):
cp $(srcdir)/stubby/COPYING $(distdir)/stubby cp $(srcdir)/stubby/COPYING $(distdir)/stubby
cp $(srcdir)/stubby/README.md $(distdir)/stubby cp $(srcdir)/stubby/README.md $(distdir)/stubby
cp $(srcdir)/stubby/doc/stubby.1.in $(distdir)/stubby/doc cp $(srcdir)/stubby/doc/stubby.1.in $(distdir)/stubby/doc
cp $(srcdir)/stubby/systemd/README.md $(distdir)/stubby/systemd
cp $(srcdir)/stubby/systemd/stubby.conf $(distdir)/stubby/systemd
cp $(srcdir)/stubby/systemd/stubby.service $(distdir)/stubby/systemd
cp $(srcdir)/stubby/contrib/upstart/stubby.conf $(distdir)/stubby/contrib/upstart
cp $(srcdir)/src/jsmn/*.[ch] $(distdir)/src/jsmn cp $(srcdir)/src/jsmn/*.[ch] $(distdir)/src/jsmn
cp $(srcdir)/src/jsmn/LICENSE $(distdir)/src/jsmn cp $(srcdir)/src/jsmn/LICENSE $(distdir)/src/jsmn
cp $(srcdir)/src/jsmn/README.md $(distdir)/src/jsmn cp $(srcdir)/src/jsmn/README.md $(distdir)/src/jsmn

View File

@ -70,7 +70,7 @@ If you are installing from packages, you have to install the library and also th
External dependencies are linked outside the getdns API build tree (we rely on configure to find them). We would like to keep the dependency tree short. Please refer to section for building on Windows for separate dependency and build instructions for that platform. External dependencies are linked outside the getdns API build tree (we rely on configure to find them). We would like to keep the dependency tree short. Please refer to section for building on Windows for separate dependency and build instructions for that platform.
* [libunbound from NLnet Labs](https://unbound.net/) version 1.4.16 or later. * [libunbound from NLnet Labs](https://unbound.net/) version 1.4.16 or later.
* [libidn from the FSF](https://www.gnu.org/software/libidn/) version 1 or 2. (Note that the libidn version means the conversions between A-labels and U-labels may permit conversion of formally invalid labels under IDNA2008.) * [libidn from the FSF](https://www.gnu.org/software/libidn/) version 1 or 2 (from version 2.0.0 and higher). (Note that the libidn version means the conversions between A-labels and U-labels may permit conversion of formally invalid labels under IDNA2008.)
* [libssl and libcrypto from the OpenSSL Project](https://www.openssl.org/) version 0.9.7 or later. (Note: version 1.0.1 or later is required for TLS support, version 1.0.2 or later is required for TLS hostname authentication) * [libssl and libcrypto from the OpenSSL Project](https://www.openssl.org/) version 0.9.7 or later. (Note: version 1.0.1 or later is required for TLS support, version 1.0.2 or later is required for TLS hostname authentication)
* Doxygen is used to generate documentation; while this is not technically necessary for the build it makes things a lot more pleasant. * Doxygen is used to generate documentation; while this is not technically necessary for the build it makes things a lot more pleasant.

View File

@ -36,7 +36,7 @@ sinclude(./m4/acx_getaddrinfo.m4)
sinclude(./m4/ax_check_compile_flag.m4) sinclude(./m4/ax_check_compile_flag.m4)
sinclude(./m4/pkg.m4) sinclude(./m4/pkg.m4)
AC_INIT([getdns], [1.4.1], [team@getdnsapi.net], [getdns], [https://getdnsapi.net]) AC_INIT([getdns], [1.4.2], [team@getdnsapi.net], [getdns], [https://getdnsapi.net])
# Autoconf 2.70 will have set up runstatedir. 2.69 is frequently (Debian) # Autoconf 2.70 will have set up runstatedir. 2.69 is frequently (Debian)
# patched to do the same, but frequently (MacOS) not. So add a with option # patched to do the same, but frequently (MacOS) not. So add a with option
@ -63,13 +63,13 @@ AC_ARG_WITH([current-date],
[CURRENT_DATE="`date -u +%Y-%m-%dT%H:%M:%SZ`"]) [CURRENT_DATE="`date -u +%Y-%m-%dT%H:%M:%SZ`"])
AC_SUBST(GETDNS_VERSION, ["AC_PACKAGE_VERSION$RELEASE_CANDIDATE"]) AC_SUBST(GETDNS_VERSION, ["AC_PACKAGE_VERSION$RELEASE_CANDIDATE"])
AC_SUBST(GETDNS_NUMERIC_VERSION, [0x01040100]) AC_SUBST(GETDNS_NUMERIC_VERSION, [0x01040200])
AC_SUBST(API_VERSION, ["December 2015"]) AC_SUBST(API_VERSION, ["December 2015"])
AC_SUBST(API_NUMERIC_VERSION, [0x07df0c00]) AC_SUBST(API_NUMERIC_VERSION, [0x07df0c00])
GETDNS_COMPILATION_COMMENT="AC_PACKAGE_NAME $GETDNS_VERSION configured on $CURRENT_DATE for the $API_VERSION version of the API" GETDNS_COMPILATION_COMMENT="AC_PACKAGE_NAME $GETDNS_VERSION configured on $CURRENT_DATE for the $API_VERSION version of the API"
AC_DEFINE_UNQUOTED([STUBBY_PACKAGE], ["stubby"], [Stubby package]) AC_DEFINE_UNQUOTED([STUBBY_PACKAGE], ["stubby"], [Stubby package])
AC_DEFINE_UNQUOTED([STUBBY_PACKAGE_STRING], ["0.2.2$STUBBY_RELEASE_CANDIDATE"], [Stubby package string]) AC_DEFINE_UNQUOTED([STUBBY_PACKAGE_STRING], ["0.2.3$STUBBY_RELEASE_CANDIDATE"], [Stubby package string])
# Library version # Library version
# --------------- # ---------------
@ -104,9 +104,9 @@ AC_DEFINE_UNQUOTED([STUBBY_PACKAGE_STRING], ["0.2.2$STUBBY_RELEASE_CANDIDATE"],
# getdns-1.2.1 had libversion 8:1:2 # getdns-1.2.1 had libversion 8:1:2
# getdns-1.3.0 had libversion 9:0:3 # getdns-1.3.0 had libversion 9:0:3
# getdns-1.4.0 had libversion 10:0:0 # getdns-1.4.0 had libversion 10:0:0
# getdns-1.4.1 has libversion 10:1:0 # getdns-1.4.1 had libversion 10:1:0
# # getdns-1.4.2 has libversion 10:2:0
GETDNS_LIBVERSION=10:1:0 GETDNS_LIBVERSION=10:2:0
AC_SUBST(GETDNS_COMPILATION_COMMENT) AC_SUBST(GETDNS_COMPILATION_COMMENT)
AC_SUBST(GETDNS_LIBVERSION) AC_SUBST(GETDNS_LIBVERSION)
@ -887,7 +887,7 @@ then
LIBS="-lidn2 $LIBS" LIBS="-lidn2 $LIBS"
AC_DEFINE_UNQUOTED([HAVE_LIBIDN2], [1], [Define to 1 if you have the `idn2' library (-lidn).]) dnl ` AC_DEFINE_UNQUOTED([HAVE_LIBIDN2], [1], [Define to 1 if you have the `idn2' library (-lidn).]) dnl `
], [ ], [
MISSING_DEPS="${MISSING_DEPS}${MISSING_SEP}libidn2" MISSING_DEPS="${MISSING_DEPS}${MISSING_SEP}libidn2 (version 2.0.0 or higher)"
MISSING_SEP=", " MISSING_SEP=", "
]) ])
fi fi

14
project-doc/packages.txt Normal file
View File

@ -0,0 +1,14 @@
Some notes about packages and maintainers.
For Homebrew, created and maintained by ilovezfs
https://github.com/Homebrew/homebrew-core/Formula/getdns.rb
https://github.com/Homebrew/homebrew-core/Formula/stubby.rb
For Arch, created and maintained by Bruno Pagani (ArchangeGabriel)
For OpenWRT, created and maintained by David Mora (iamperson347)
https://github.com/openwrt/packages/tree/master/libs/getdns
https://github.com/openwrt/packages/tree/master/net/stubby
For AstLinux Project, created and maintained by Lonnie Abelbeck (abelbeck)
https://github.com/astlinux-project/astlinux/tree/master/package/getdns

View File

@ -1,4 +1,4 @@
/* $OpenBSD: getentropy_linux.c,v 1.20 2014/07/12 15:43:49 beck Exp $ */ /* $OpenBSD: getentropy_linux.c,v 1.45 2018/03/13 22:53:28 bcook Exp $ */
/* /*
* Copyright (c) 2014 Theo de Raadt <deraadt@openbsd.org> * Copyright (c) 2014 Theo de Raadt <deraadt@openbsd.org>
@ -15,13 +15,17 @@
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*
* Emulation of getentropy(2) as documented at:
* http://man.openbsd.org/getentropy.2
*/ */
#define WITH_DL_ITERATE_PHDR 1
#ifdef WITH_DL_ITERATE_PHDR
#define _GNU_SOURCE 1
/* #define _POSIX_C_SOURCE 199309L */
#endif
#include "config.h" #include "config.h"
/*
#define _POSIX_C_SOURCE 199309L
#define _GNU_SOURCE 1
*/
#include <sys/types.h> #include <sys/types.h>
#include <sys/param.h> #include <sys/param.h>
#include <sys/ioctl.h> #include <sys/ioctl.h>
@ -39,6 +43,9 @@
#include <stdlib.h> #include <stdlib.h>
#include <stdint.h> #include <stdint.h>
#include <stdio.h> #include <stdio.h>
#ifdef WITH_DL_ITERATE_PHDR
#include <link.h>
#endif
#include <termios.h> #include <termios.h>
#include <fcntl.h> #include <fcntl.h>
#include <signal.h> #include <signal.h>
@ -55,7 +62,6 @@
#include <linux/types.h> #include <linux/types.h>
#include <linux/random.h> #include <linux/random.h>
#include <linux/sysctl.h>
#ifdef HAVE_GETAUXVAL #ifdef HAVE_GETAUXVAL
#include <sys/auxv.h> #include <sys/auxv.h>
#endif #endif
@ -75,6 +81,7 @@
#if defined(HAVE_SSL) #if defined(HAVE_SSL)
#define CRYPTO_SHA512_CTX SHA512_CTX #define CRYPTO_SHA512_CTX SHA512_CTX
#define CRYPTO_SHA512_INIT(x) SHA512_Init(x) #define CRYPTO_SHA512_INIT(x) SHA512_Init(x)
#define CRYPTO_SHA512_UPDATE(c, x, l) (SHA512_Update((c), (char *)(x), (l)))
#define CRYPTO_SHA512_FINAL(r, c) SHA512_Final(r, c) #define CRYPTO_SHA512_FINAL(r, c) SHA512_Final(r, c)
#define HR(x, l) (SHA512_Update(&ctx, (char *)(x), (l))) #define HR(x, l) (SHA512_Update(&ctx, (char *)(x), (l)))
#define HD(x) (SHA512_Update(&ctx, (char *)&(x), sizeof (x))) #define HD(x) (SHA512_Update(&ctx, (char *)&(x), sizeof (x)))
@ -82,6 +89,7 @@
#elif defined(HAVE_NETTLE) #elif defined(HAVE_NETTLE)
#define CRYPTO_SHA512_CTX struct sha512_ctx #define CRYPTO_SHA512_CTX struct sha512_ctx
#define CRYPTO_SHA512_INIT(x) sha512_init(x) #define CRYPTO_SHA512_INIT(x) sha512_init(x)
#define CRYPTO_SHA512_UPDATE(c, x, l) (sha512_update((c), (l), (uint8_t *)(x)))
#define CRYPTO_SHA512_FINAL(r, c) sha512_digest(c, SHA512_DIGEST_SIZE, r) #define CRYPTO_SHA512_FINAL(r, c) sha512_digest(c, SHA512_DIGEST_SIZE, r)
#define HR(x, l) (sha512_update(&ctx, (l), (uint8_t *)(x))) #define HR(x, l) (sha512_update(&ctx, (l), (uint8_t *)(x)))
#define HD(x) (sha512_update(&ctx, sizeof (x), (uint8_t *)&(x))) #define HD(x) (sha512_update(&ctx, sizeof (x), (uint8_t *)&(x)))
@ -90,11 +98,8 @@
int getentropy(void *buf, size_t len); int getentropy(void *buf, size_t len);
#ifdef CAN_REFERENCE_MAIN
extern int main(int, char *argv[]);
#endif
static int gotdata(char *buf, size_t len); static int gotdata(char *buf, size_t len);
#ifdef SYS_getrandom #if defined(SYS_getrandom) && defined(GRND_NONBLOCK)
static int getentropy_getrandom(void *buf, size_t len); static int getentropy_getrandom(void *buf, size_t len);
#endif #endif
static int getentropy_urandom(void *buf, size_t len); static int getentropy_urandom(void *buf, size_t len);
@ -102,6 +107,9 @@ static int getentropy_urandom(void *buf, size_t len);
static int getentropy_sysctl(void *buf, size_t len); static int getentropy_sysctl(void *buf, size_t len);
#endif #endif
static int getentropy_fallback(void *buf, size_t len); static int getentropy_fallback(void *buf, size_t len);
#ifdef WITH_DL_ITERATE_PHDR
static int getentropy_phdr(struct dl_phdr_info *info, size_t size, void *data);
#endif
int int
getentropy(void *buf, size_t len) getentropy(void *buf, size_t len)
@ -110,18 +118,21 @@ getentropy(void *buf, size_t len)
if (len > 256) { if (len > 256) {
errno = EIO; errno = EIO;
return -1; return (-1);
} }
#ifdef SYS_getrandom #if defined(SYS_getrandom) && defined(GRND_NONBLOCK)
/* /*
* Try descriptor-less getrandom() * Try descriptor-less getrandom(), in non-blocking mode.
*
* The design of Linux getrandom is broken. It has an
* uninitialized phase coupled with blocking behaviour, which
* is unacceptable from within a library at boot time without
* possible recovery. See http://bugs.python.org/issue26839#msg267745
*/ */
ret = getentropy_getrandom(buf, len); ret = getentropy_getrandom(buf, len);
if (ret != -1) if (ret != -1)
return (ret); return (ret);
if (errno != ENOSYS)
return (-1);
#endif #endif
/* /*
@ -175,7 +186,7 @@ getentropy(void *buf, size_t len)
* - Do the best under the circumstances.... * - Do the best under the circumstances....
* *
* This code path exists to bring light to the issue that Linux * This code path exists to bring light to the issue that Linux
* does not provide a failsafe API for entropy collection. * still does not provide a failsafe API for entropy collection.
* *
* We hope this demonstrates that Linux should either retain their * We hope this demonstrates that Linux should either retain their
* sysctl ABI, or consider providing a new failsafe API which * sysctl ABI, or consider providing a new failsafe API which
@ -205,11 +216,11 @@ gotdata(char *buf, size_t len)
for (i = 0; i < len; ++i) for (i = 0; i < len; ++i)
any_set |= buf[i]; any_set |= buf[i];
if (any_set == 0) if (any_set == 0)
return -1; return (-1);
return 0; return (0);
} }
#ifdef SYS_getrandom #if defined(SYS_getrandom) && defined(GRND_NONBLOCK)
static int static int
getentropy_getrandom(void *buf, size_t len) getentropy_getrandom(void *buf, size_t len)
{ {
@ -218,7 +229,7 @@ getentropy_getrandom(void *buf, size_t len)
if (len > 256) if (len > 256)
return (-1); return (-1);
do { do {
ret = syscall(SYS_getrandom, buf, len, 0); ret = syscall(SYS_getrandom, buf, len, GRND_NONBLOCK);
} while (ret == -1 && errno == EINTR); } while (ret == -1 && errno == EINTR);
if (ret != (int)len) if (ret != (int)len)
@ -279,11 +290,11 @@ start:
close(fd); close(fd);
if (gotdata(buf, len) == 0) { if (gotdata(buf, len) == 0) {
errno = save_errno; errno = save_errno;
return 0; /* satisfied */ return (0); /* satisfied */
} }
nodevrandom: nodevrandom:
errno = EIO; errno = EIO;
return -1; return (-1);
} }
#ifdef SYS__sysctl #ifdef SYS__sysctl
@ -314,11 +325,11 @@ getentropy_sysctl(void *buf, size_t len)
} }
sysctlfailed: sysctlfailed:
errno = EIO; errno = EIO;
return -1; return (-1);
} }
#endif /* SYS__sysctl */ #endif /* SYS__sysctl */
static int cl[] = { static const int cl[] = {
CLOCK_REALTIME, CLOCK_REALTIME,
#ifdef CLOCK_MONOTONIC #ifdef CLOCK_MONOTONIC
CLOCK_MONOTONIC, CLOCK_MONOTONIC,
@ -343,6 +354,18 @@ static int cl[] = {
#endif #endif
}; };
#ifdef WITH_DL_ITERATE_PHDR
static int
getentropy_phdr(struct dl_phdr_info *info, size_t size, void *data)
{
CRYPTO_SHA512_CTX *ctx = data;
(void)size;
CRYPTO_SHA512_UPDATE(ctx, &info->dlpi_addr, sizeof (info->dlpi_addr));
return (0);
}
#endif
static int static int
getentropy_fallback(void *buf, size_t len) getentropy_fallback(void *buf, size_t len)
{ {
@ -379,6 +402,10 @@ getentropy_fallback(void *buf, size_t len)
cnt += (int)tv.tv_usec; cnt += (int)tv.tv_usec;
} }
#ifdef WITH_DL_ITERATE_PHDR
dl_iterate_phdr(getentropy_phdr, &ctx);
#endif
for (ii = 0; ii < sizeof(cl)/sizeof(cl[0]); ii++) for (ii = 0; ii < sizeof(cl)/sizeof(cl[0]); ii++)
HX(clock_gettime(cl[ii], &ts) == -1, ts); HX(clock_gettime(cl[ii], &ts) == -1, ts);
@ -398,9 +425,6 @@ getentropy_fallback(void *buf, size_t len)
HX(sigprocmask(SIG_BLOCK, NULL, &sigset) == -1, HX(sigprocmask(SIG_BLOCK, NULL, &sigset) == -1,
sigset); sigset);
#ifdef CAN_REFERENCE_MAIN
HF(main); /* an addr in program */
#endif
HF(getentropy); /* an addr in this library */ HF(getentropy); /* an addr in this library */
HF(printf); /* an addr in libc */ HF(printf); /* an addr in libc */
p = (char *)&p; p = (char *)&p;
@ -541,17 +565,18 @@ getentropy_fallback(void *buf, size_t len)
if (p) if (p)
HD(p); HD(p);
#endif #endif
#endif /* HAVE_GETAUXVAL */ #endif
CRYPTO_SHA512_FINAL(results, &ctx); CRYPTO_SHA512_FINAL(results, &ctx);
memcpy((char *)buf + i, results, min(sizeof(results), len - i)); memcpy((char *)buf + i, results, min(sizeof(results), len - i));
i += min(sizeof(results), len - i); i += min(sizeof(results), len - i);
} }
memset(&ctx, 0, sizeof ctx);
memset(results, 0, sizeof results); memset(results, 0, sizeof results);
if (gotdata(buf, len) == 0) { if (gotdata(buf, len) == 0) {
errno = save_errno; errno = save_errno;
return 0; /* satisfied */ return (0); /* satisfied */
} }
errno = EIO; errno = EIO;
return -1; return (-1);
} }

View File

@ -3787,13 +3787,14 @@ _getdns_strdup(const struct mem_funcs *mfs, const char *s)
return memcpy(r, s, sz); return memcpy(r, s, sz);
} }
static uint8_t _getdns_bindata_nodata[] = { 0, 0, 0, 0, 0, 0, 0, 0 };
struct getdns_bindata * struct getdns_bindata *
_getdns_bindata_copy(struct mem_funcs *mfs, size_t size, const uint8_t *data) _getdns_bindata_copy(struct mem_funcs *mfs, size_t size, const uint8_t *data)
{ {
/* Don't know why, but nodata allows /* Don't know why, but nodata allows
* empty bindatas with the python bindings * empty bindatas with the python bindings
*/ */
static uint8_t nodata[] = { 0, 0, 0, 0, 0, 0, 0, 0 };
struct getdns_bindata *dst; struct getdns_bindata *dst;
if (!(dst = GETDNS_MALLOC(*mfs, struct getdns_bindata))) if (!(dst = GETDNS_MALLOC(*mfs, struct getdns_bindata)))
@ -3807,7 +3808,7 @@ _getdns_bindata_copy(struct mem_funcs *mfs, size_t size, const uint8_t *data)
} }
(void) memcpy(dst->data, data, size); (void) memcpy(dst->data, data, size);
} else { } else {
dst->data = nodata; dst->data = _getdns_bindata_nodata;
} }
return dst; return dst;
} }
@ -3819,7 +3820,8 @@ _getdns_bindata_destroy(struct mem_funcs *mfs,
if (!bindata) if (!bindata)
return; return;
if (bindata->size) GETDNS_FREE(*mfs, bindata->data); if (bindata->data && bindata->data != _getdns_bindata_nodata)
GETDNS_FREE(*mfs, bindata->data);
GETDNS_FREE(*mfs, bindata); GETDNS_FREE(*mfs, bindata);
} }
@ -4806,9 +4808,19 @@ static getdns_return_t _get_list_or_read_file(const getdns_dict *config_dict,
#define CONTEXT_SETTING_STRING(X) \ #define CONTEXT_SETTING_STRING(X) \
} else if (_streq(setting, #X )) { \ } else if (_streq(setting, #X )) { \
if (!(r = getdns_dict_get_bindata(config_dict, #X , &bd))) \ if (!(r = getdns_dict_get_bindata(config_dict, #X , &bd))) { \
if (bd->size < sizeof(str_buf)) { \
(void) memcpy(str_buf, (char *)bd->data, bd->size); \
str_buf[bd->size] = '\0'; \
r = getdns_context_set_ ## X( \ r = getdns_context_set_ ## X( \
context, (char *)bd->data); context, str_buf); \
} else if ((tmp_str = _getdns_strdup2(&context->mf, bd))) { \
r = getdns_context_set_ ## X( \
context, tmp_str); \
GETDNS_FREE(context->mf, tmp_str); \
} else \
r = GETDNS_RETURN_MEMORY_ERROR; \
}
static getdns_return_t static getdns_return_t
_getdns_context_config_setting(getdns_context *context, _getdns_context_config_setting(getdns_context *context,
@ -4823,6 +4835,7 @@ _getdns_context_config_setting(getdns_context *context,
uint32_t n; uint32_t n;
getdns_bindata *bd; getdns_bindata *bd;
int destroy_list = 0; int destroy_list = 0;
char str_buf[1024], *tmp_str;
if (_streq(setting, "all_context")) { if (_streq(setting, "all_context")) {
if (!(r = getdns_dict_get_dict(config_dict, "all_context", &dict))) if (!(r = getdns_dict_get_dict(config_dict, "all_context", &dict)))
@ -5039,6 +5052,7 @@ static size_t _getdns_get_appdata(getdns_context *context, char *path)
return len; return len;
} }
} }
path[0] = '\0';
return 0; return 0;
} }
@ -5046,14 +5060,19 @@ FILE *_getdns_context_get_priv_fp(getdns_context *context, const char *fn)
{ {
char path[_GETDNS_PATH_MAX]; char path[_GETDNS_PATH_MAX];
FILE *f = NULL; FILE *f = NULL;
size_t len; size_t len = _getdns_get_appdata(context, path);
(void) context; (void) context;
if (!(len = _getdns_get_appdata(context, path))) /*
DEBUG_ANCHOR("ERROR %s(): Could nog get application data path\n" * Commented out to enable fallback to current directory
, __FUNC__); *
* if (!(len = _getdns_get_appdata(context, path)))
else if (len + strlen(fn) >= sizeof(path)) * DEBUG_ANCHOR("ERROR %s(): Could nog get application data path\n"
* , __FUNC__);
*
* else
*/
if (len + strlen(fn) >= sizeof(path))
DEBUG_ANCHOR("ERROR %s(): Application data too long\n", __FUNC__); DEBUG_ANCHOR("ERROR %s(): Application data too long\n", __FUNC__);
else if (!strcpy(path + len, fn)) else if (!strcpy(path + len, fn))
@ -5113,27 +5132,32 @@ int _getdns_context_write_priv_file(getdns_context *context,
char path[_GETDNS_PATH_MAX], tmpfn[_GETDNS_PATH_MAX]; char path[_GETDNS_PATH_MAX], tmpfn[_GETDNS_PATH_MAX];
int fd = -1; int fd = -1;
FILE *f = NULL; FILE *f = NULL;
size_t len; size_t len = _getdns_get_appdata(context, path);
if (!(len = _getdns_get_appdata(context, path))) /*
DEBUG_ANCHOR("ERROR %s(): Could nog get application data path\n" * Commented out to enable fallback to current directory
, __FUNC__); *
* if (!(len = _getdns_get_appdata(context, path)))
else if (len + 6 >= sizeof(tmpfn) * DEBUG_ANCHOR("ERROR %s(): Could nog get application data path\n"
* , __FUNC__);
*
* else
*/
if (len + 6 >= sizeof(tmpfn)
|| len + strlen(fn) >= sizeof(path)) || len + strlen(fn) >= sizeof(path))
DEBUG_ANCHOR("ERROR %s(): Application data too long\n", __FUNC__); DEBUG_ANCHOR("ERROR %s(): Application data too long\n", __FUNC__);
else if (snprintf(tmpfn, sizeof(tmpfn), "%sXXXXXX", path) < 0) else if (snprintf(tmpfn, sizeof(tmpfn), "%sXXXXXX", path) < 0)
DEBUG_ANCHOR("ERROR %s(): Creating temporary filename template\n" DEBUG_ANCHOR("ERROR %s(): Creating temporary filename template: \"%s\"\n"
, __FUNC__); , __FUNC__, tmpfn);
else if (!strcpy(path + len, fn)) else if (!strcpy(path + len, fn))
; /* strcpy returns path + len always */ ; /* strcpy returns path + len always */
else if ((fd = mkstemp(tmpfn)) < 0) else if ((fd = mkstemp(tmpfn)) < 0)
DEBUG_ANCHOR("ERROR %s(): Creating temporary file: %s\n" DEBUG_ANCHOR("ERROR %s(): Creating temporary file \"%s\": %s\n"
, __FUNC__, strerror(errno)); , __FUNC__, tmpfn, strerror(errno));
else if (!(f = fdopen(fd, "w"))) else if (!(f = fdopen(fd, "w")))
DEBUG_ANCHOR("ERROR %s(): Opening temporary file: %s\n" DEBUG_ANCHOR("ERROR %s(): Opening temporary file: %s\n"
@ -5182,11 +5206,18 @@ int _getdns_context_can_write_appdata(getdns_context *context)
if (!_getdns_context_write_priv_file(context, test_fn, &test_content)) if (!_getdns_context_write_priv_file(context, test_fn, &test_content))
return 0; return 0;
if (!(len = _getdns_get_appdata(context, path))) len = _getdns_get_appdata(context, path);
DEBUG_ANCHOR("ERROR %s(): Could nog get application data path\n" /*
, __FUNC__); * Commented out to enable fallback to current directory
*
else if (len + strlen(test_fn) >= sizeof(path)) *
* if (!(len = _getdns_get_appdata(context, path)))
* DEBUG_ANCHOR("ERROR %s(): Could not get application data path\n"
* , __FUNC__);
*
* else
*/
if (len + strlen(test_fn) >= sizeof(path))
DEBUG_ANCHOR("ERROR %s(): Application data too long\n", __FUNC__); DEBUG_ANCHOR("ERROR %s(): Application data too long\n", __FUNC__);
else if (!strcpy(path + len, test_fn)) else if (!strcpy(path + len, test_fn))

View File

@ -737,21 +737,16 @@ getdns_pp_base64(gldns_buffer *buf, getdns_bindata *bindata)
{ {
size_t p = gldns_buffer_position(buf); size_t p = gldns_buffer_position(buf);
size_t base64str_sz; size_t base64str_sz;
char *target;
size_t avail;
if (gldns_buffer_printf(buf, " <bindata of ") < 0) if (gldns_buffer_printf(buf, " <bindata of ") < 0)
return -1; return -1;
base64str_sz = gldns_b64_ntop_calculate_size(bindata->size); base64str_sz = gldns_b64_ntop_calculate_size(bindata->size);
target = (char *)gldns_buffer_current(buf); if (!gldns_buffer_reserve(buf, base64str_sz))
avail = gldns_buffer_remaining(buf); return -1;
if (avail >= base64str_sz)
gldns_buffer_skip(buf, gldns_b64_ntop( gldns_buffer_skip(buf, gldns_b64_ntop(bindata->data, bindata->size,
bindata->data, bindata->size, (char *)gldns_buffer_current(buf), base64str_sz));
target, base64str_sz));
else
gldns_buffer_skip(buf, base64str_sz);
if (gldns_buffer_printf(buf, ">") < 0) if (gldns_buffer_printf(buf, ">") < 0)
return -1; return -1;

View File

@ -244,13 +244,16 @@ static inline int _dname_equal(const uint8_t *left, const uint8_t *right)
static int _dname_is_parent( static int _dname_is_parent(
const uint8_t * const parent, const uint8_t *subdomain) const uint8_t * const parent, const uint8_t *subdomain)
{ {
while (*subdomain) { if (*parent == 0)
return 1;
else while (*subdomain) {
if (_dname_equal(parent, subdomain)) if (_dname_equal(parent, subdomain))
return 1; return 1;
subdomain += *subdomain + 1; subdomain += *subdomain + 1;
} }
return *parent == 0; return 0;
} }
static uint8_t *_dname_label_copy(uint8_t *dst, const uint8_t *src, size_t dst_len) static uint8_t *_dname_label_copy(uint8_t *dst, const uint8_t *src, size_t dst_len)
@ -668,8 +671,16 @@ static chain_head *add_rrset2val_chain(struct mem_funcs *mf,
/* On the first chain, max_node == NULL. /* On the first chain, max_node == NULL.
* Schedule a root DNSKEY query, we always need that. * Schedule a root DNSKEY query, we always need that.
*/ */
if (!(node[-1].parent = max_node)) if (!(node[-1].parent = max_node)) {
val_chain_sched(head, (uint8_t *)"\0"); val_chain_sched(head, (uint8_t *)"\0");
if (head->node_count > 1)
val_chain_sched(head, node[-2].ds.name);
if (head->node_count > 2)
val_chain_sched(head, node[-3].ds.name);
} else if ((max_labels == 1 || max_labels == 2) && head->node_count > 0)
val_chain_sched(head, node[-1].ds.name);
if (max_labels == 1 && head->node_count > 1)
val_chain_sched(head, node[-2].ds.name);
return head; return head;
} }
@ -1051,6 +1062,46 @@ static void val_chain_sched_signer(chain_head *head, _getdns_rrsig_iter *rrsig)
val_chain_sched_signer_node(head->parent, rrsig); val_chain_sched_signer_node(head->parent, rrsig);
} }
/* Cancel all DS and DNSKEY for subdomains of parent_dname,
* and also the DNSKEY query at the parent_dname
*/
static void cancel_requests_for_subdomains_of(
chain_head *head, const uint8_t *parent_dname)
{
chain_head *next;
chain_node *node;
size_t node_count;
while (head) {
next = head->next;
if (!_dname_is_parent(parent_dname, head->rrset.name)) {
head = next;
continue;
}
for ( node_count = head->node_count, node = head->parent
; node_count
; node_count--, node = node->parent ) {
if (!_getdns_netreq_finished(node->dnskey_req)) {
_getdns_context_cancel_request(
node->dnskey_req->owner);
node->dnskey_req = NULL;
}
if (_dname_equal(parent_dname, node->ds.name))
break;
if (!_getdns_netreq_finished(node->ds_req)) {
_getdns_context_cancel_request(
node->ds_req->owner);
node->ds_req = NULL;
}
}
head = next;
}
}
static void val_chain_node_cb(getdns_dns_req *dnsreq) static void val_chain_node_cb(getdns_dns_req *dnsreq)
{ {
chain_node *node = (chain_node *)dnsreq->user_pointer; chain_node *node = (chain_node *)dnsreq->user_pointer;
@ -1092,12 +1143,22 @@ static void val_chain_node_cb(getdns_dns_req *dnsreq)
n_signers++; n_signers++;
} }
} }
if (netreq->request_type == GETDNS_RRTYPE_DS && n_signers == 0) if (netreq->request_type != GETDNS_RRTYPE_DS)
; /* pass */
else if (n_signers) {
_getdns_rrtype_iter ds_spc;
if (!_getdns_rrtype_iter_init(&ds_spc, &node->ds)) {
debug_sec_print_rrset("A DS NX proof for ", &node->ds);
DEBUG_SEC("Cancel all more specific requests\n");
cancel_requests_for_subdomains_of(node->chains, node->ds.name);
}
} else {
/* No signed DS and no signed proof of non-existance. /* No signed DS and no signed proof of non-existance.
* Search further up the tree... * Search further up the tree...
*/ */
val_chain_sched_ds_node(node->parent); val_chain_sched_ds_node(node->parent);
}
if (node->lock) node->lock--; if (node->lock) node->lock--;
check_chain_complete(node->chains); check_chain_complete(node->chains);
} }
@ -1685,7 +1746,7 @@ static int a_key_signed_rrset_no_wc(struct mem_funcs *mf, time_t now,
uint32_t skew, _getdns_rrset *keyset, _getdns_rrset *rrset) uint32_t skew, _getdns_rrset *keyset, _getdns_rrset *rrset)
{ {
_getdns_rrtype_iter dnskey_spc, *dnskey; _getdns_rrtype_iter dnskey_spc, *dnskey;
const uint8_t *nc_name; const uint8_t *nc_name; /* Initialized by dnskey_signed_rrset() */
int keytag; int keytag;
assert(keyset->rr_type == GETDNS_RRTYPE_DNSKEY); assert(keyset->rr_type == GETDNS_RRTYPE_DNSKEY);
@ -1693,8 +1754,17 @@ static int a_key_signed_rrset_no_wc(struct mem_funcs *mf, time_t now,
for ( dnskey = _getdns_rrtype_iter_init(&dnskey_spc, keyset) for ( dnskey = _getdns_rrtype_iter_init(&dnskey_spc, keyset)
; dnskey ; dnskey = _getdns_rrtype_iter_next(dnskey) ) { ; dnskey ; dnskey = _getdns_rrtype_iter_next(dnskey) ) {
if ((keytag = dnskey_signed_rrset(mf, now, skew, if (!(keytag = dnskey_signed_rrset(mf, now, skew,
dnskey, rrset, &nc_name)) && !nc_name) dnskey, rrset, &nc_name)))
continue;
if (!nc_name) /* Not a wildcard, then success! */
return keytag;
/* Not a wildcard expansion, but the wildcard name itself. */
if (rrset->rr_type == GETDNS_RRTYPE_NSEC &&
rrset->name[0] == 1 && rrset->name[1] == '*' &&
nc_name == rrset->name)
return keytag; return keytag;
} }
return 0; return 0;
@ -1709,7 +1779,8 @@ static int a_key_signed_rrset(struct mem_funcs *mf, time_t now, uint32_t skew,
_getdns_rrset *keyset, _getdns_rrset *rrset) _getdns_rrset *keyset, _getdns_rrset *rrset)
{ {
_getdns_rrtype_iter dnskey_spc, *dnskey; _getdns_rrtype_iter dnskey_spc, *dnskey;
const uint8_t *nc_name; const uint8_t *nc_name; /* Initialized by dnskey_signed_rrset() */
int keytag; int keytag;
assert(keyset->rr_type == GETDNS_RRTYPE_DNSKEY); assert(keyset->rr_type == GETDNS_RRTYPE_DNSKEY);
@ -1728,7 +1799,8 @@ static int a_key_signed_rrset(struct mem_funcs *mf, time_t now, uint32_t skew,
* There is no more specific! * There is no more specific!
*/ */
if (rrset->rr_type == GETDNS_RRTYPE_NSEC && if (rrset->rr_type == GETDNS_RRTYPE_NSEC &&
rrset->name[0] == 1 && rrset->name[1] == '*') rrset->name[0] == 1 && rrset->name[1] == '*' &&
nc_name == rrset->name)
return keytag; return keytag;
debug_sec_print_rrset("wildcard expanded to: ", rrset); debug_sec_print_rrset("wildcard expanded to: ", rrset);
@ -1751,7 +1823,7 @@ static int ds_authenticates_keys(struct mem_funcs *mf,
_getdns_rrtype_iter dnskey_spc, *dnskey; _getdns_rrtype_iter dnskey_spc, *dnskey;
_getdns_rrtype_iter ds_spc, *ds; _getdns_rrtype_iter ds_spc, *ds;
uint16_t keytag; uint16_t keytag;
const uint8_t *nc_name; const uint8_t *nc_name; /* Initialized by dnskey_signed_rrset() */
size_t valid_dsses = 0, supported_dsses = 0; size_t valid_dsses = 0, supported_dsses = 0;
uint8_t max_supported_digest = 0; uint8_t max_supported_digest = 0;
int max_supported_result = 0; int max_supported_result = 0;
@ -3312,31 +3384,7 @@ void _getdns_ta_notify_dnsreqs(getdns_context *context)
void _getdns_validation_chain_timeout(getdns_dns_req *dnsreq) void _getdns_validation_chain_timeout(getdns_dns_req *dnsreq)
{ {
chain_head *head = dnsreq->chain, *next; cancel_requests_for_subdomains_of(dnsreq->chain, (uint8_t *)"\0");
chain_node *node;
size_t node_count;
while (head) {
next = head->next;
for ( node_count = head->node_count, node = head->parent
; node_count
; node_count--, node = node->parent ) {
if (!_getdns_netreq_finished(node->dnskey_req)) {
_getdns_context_cancel_request(
node->dnskey_req->owner);
node->dnskey_req = NULL;
}
if (!_getdns_netreq_finished(node->ds_req)) {
_getdns_context_cancel_request(
node->ds_req->owner);
node->ds_req = NULL;
}
}
head = next;
}
dnsreq->request_timed_out = 1; dnsreq->request_timed_out = 1;
check_chain_complete(dnsreq->chain); check_chain_complete(dnsreq->chain);
} }

View File

@ -361,7 +361,7 @@
struct getdns_context *context = NULL; struct getdns_context *context = NULL;
struct getdns_dict *address = NULL; struct getdns_dict *address = NULL;
struct getdns_bindata address_type = { 5, (void *)"IPv4" }; struct getdns_bindata address_type = { 5, (void *)"IPv4" };
struct getdns_bindata address_data = { 4, (void *)"\x01\x01\x01\x01" }; struct getdns_bindata address_data = { 4, (void *)"\xb9\x31\x8c\x00" };
void* eventloop = NULL; void* eventloop = NULL;
getdns_transaction_t transaction_id = 0; getdns_transaction_t transaction_id = 0;

View File

@ -304,7 +304,7 @@
struct getdns_context *context = NULL; struct getdns_context *context = NULL;
struct getdns_dict *address = NULL; struct getdns_dict *address = NULL;
struct getdns_bindata address_type = { 5, (void *)"IPv4" }; struct getdns_bindata address_type = { 5, (void *)"IPv4" };
struct getdns_bindata address_data = { 4, (void *)"\x01\x01\x01\x01" }; struct getdns_bindata address_data = { 4, (void *)"\xb9\x31\x8c\x00" };
struct getdns_dict *response = NULL; struct getdns_dict *response = NULL;
CONTEXT_CREATE(TRUE); CONTEXT_CREATE(TRUE);

2
stubby

@ -1 +1 @@
Subproject commit 1a6acd642c7dc9a04cf092e1a3837c5636d4b465 Subproject commit 8fb853ac8d6148fd9b53fdcbc107ecd375071ec5