]> git.ipfire.org Git - thirdparty/pdns.git/commitdiff
Start buildina and using arc4random
authorOtto Moerbeek <otto.moerbeek@open-xchange.com>
Tue, 20 Jun 2023 09:19:42 +0000 (11:19 +0200)
committerOtto Moerbeek <otto.moerbeek@open-xchange.com>
Thu, 6 Jul 2023 13:46:42 +0000 (15:46 +0200)
40 files changed:
configure.ac
ext/Makefile.am
pdns/Makefile.am
pdns/auth-main.cc
pdns/calidns.cc
pdns/dns_random.cc [deleted file]
pdns/dns_random.hh
pdns/dns_random_urandom.cc [deleted file]
pdns/dnsdistdist/Makefile.am
pdns/dnsdistdist/configure.ac
pdns/dnsdistdist/ext/arc4random/.gitignore [new file with mode: 0644]
pdns/dnsdistdist/ext/arc4random/Makefile.am [new symlink]
pdns/dnsdistdist/ext/arc4random/arc4random.c [new symlink]
pdns/dnsdistdist/ext/arc4random/arc4random.h [new symlink]
pdns/dnsdistdist/ext/arc4random/arc4random.hh [new symlink]
pdns/dnsdistdist/ext/arc4random/arc4random_uniform.c [new symlink]
pdns/dnsdistdist/ext/arc4random/bsd-getentropy.c [new symlink]
pdns/dnsdistdist/ext/arc4random/chacha_private.h [new symlink]
pdns/dnsdistdist/ext/arc4random/includes.h [new symlink]
pdns/dnsdistdist/ext/arc4random/log.h [new symlink]
pdns/ixfrdist.cc
pdns/pdnsutil.cc
pdns/recursordist/Makefile.am
pdns/recursordist/configure.ac
pdns/recursordist/dns_random.cc [deleted symlink]
pdns/recursordist/dns_random_urandom.cc [deleted symlink]
pdns/recursordist/ext/Makefile.am
pdns/recursordist/ext/arc4random/.gitignore [new file with mode: 0644]
pdns/recursordist/ext/arc4random/Makefile.am [new symlink]
pdns/recursordist/ext/arc4random/arc4random.c [new symlink]
pdns/recursordist/ext/arc4random/arc4random.h [new symlink]
pdns/recursordist/ext/arc4random/arc4random.hh [new symlink]
pdns/recursordist/ext/arc4random/arc4random_uniform.c [new symlink]
pdns/recursordist/ext/arc4random/bsd-getentropy.c [new symlink]
pdns/recursordist/ext/arc4random/chacha_private.h [new symlink]
pdns/recursordist/ext/arc4random/includes.h [new symlink]
pdns/recursordist/ext/arc4random/log.h [new symlink]
pdns/recursordist/rec-main.cc
pdns/speedtest.cc
pdns/test-dns_random_hh.cc

index 93430f7a1df3b463959d6cd829cd773403ba06d3..ca8ac283c886e201fe34f8ee890a9f995756cd51 100644 (file)
@@ -152,7 +152,8 @@ PDNS_FROM_GIT
 dnl Checks for library functions.
 dnl the *_r functions are in posix so we can use them unconditionally, but the ext/yahttp code is
 dnl using the defines.
-AC_CHECK_FUNCS_ONCE([strcasestr localtime_r gmtime_r recvmmsg sched_setscheduler getrandom arc4random])
+AC_CHECK_FUNCS_ONCE([strcasestr localtime_r gmtime_r recvmmsg sched_setscheduler])
+AC_CHECK_FUNCS_ONCE([getrandom getentropy arc4random arc4random_uniform arc4random_buf])
 
 AM_CONDITIONAL([HAVE_RECVMMSG], [test "x$ac_cv_func_recvmmsg" = "xyes"])
 
@@ -345,6 +346,7 @@ AC_CONFIG_FILES([
   docs/Makefile
   pdns/pdns.init
   ext/Makefile
+  ext/arc4random/Makefile
   ext/ipcrypt/Makefile
   ext/yahttp/Makefile
   ext/yahttp/yahttp/Makefile
index 4cf7265338f01e448bc554e8ab63f778b82ab865..0ae01c430f3edf07348e85e21dc24b9518cdc11f 100644 (file)
@@ -1,9 +1,11 @@
 SUBDIRS = \
+       arc4random \
        ipcrypt \
        json11 \
        yahttp
 
 DIST_SUBDIRS = \
+       arc4random \
        ipcrypt \
        json11 \
        yahttp
index a982f05168be63ef4ef7360da1280ca20985c81a..50f93222c2fefb1adcaa84d3dfd79b0ca23f7c05 100644 (file)
@@ -1,4 +1,5 @@
 JSON11_LIBS = $(top_builddir)/ext/json11/libjson11.la
+ARC4RANDOM_LIBS = $(top_builddir)/ext/arc4random/libarc4random.la
 
 AM_CPPFLAGS += \
        -I$(top_srcdir)/ext/json11 \
@@ -18,6 +19,7 @@ AM_CXXFLAGS = \
 AM_LDFLAGS = \
        $(PROGRAM_LDFLAGS) \
        $(LIBCRYPTO_LIBS) \
+       $(ARC4RANDOM_LIBS) \
        $(THREADFLAGS)
 
 AM_LFLAGS = -i
@@ -214,7 +216,7 @@ pdns_server_SOURCES = \
        digests.hh \
        distributor.hh \
        dns.cc dns.hh \
-       dns_random.cc dns_random.hh \
+       dns_random.hh \
        dnsbackend.cc dnsbackend.hh \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
@@ -355,7 +357,6 @@ pdnsutil_SOURCES = \
        credentials.cc credentials.hh \
        dbdnsseckeeper.cc \
        dns.cc \
-       dns_random.cc \
        dnsbackend.cc \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
@@ -454,7 +455,6 @@ zone2sql_SOURCES = \
        bindparser.yy \
        bindparserclasses.hh \
        dns.cc \
-       dns_random_urandom.cc \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
        dnsparser.cc \
@@ -520,7 +520,6 @@ zone2ldap_SOURCES = \
        bindlexer.l \
        bindparser.yy \
        bindparserclasses.hh \
-       dns_random_urandom.cc \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
        dnsparser.cc \
@@ -603,7 +602,7 @@ calidns_SOURCES = \
        base32.cc \
        base64.cc base64.hh \
        calidns.cc \
-       dns_random_urandom.cc dns_random.hh \
+       dns_random.hh \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
        dnsparser.cc dnsparser.hh \
@@ -654,7 +653,6 @@ stubquery_SOURCES = \
        arguments.cc arguments.hh \
        base32.cc \
        base64.cc \
-       dns_random_urandom.cc \
        dnslabeltext.cc \
        dnsname.cc \
        dnsparser.cc \
@@ -679,7 +677,7 @@ stubquery_LDFLAGS = $(AM_LDFLAGS) $(LIBCRYPTO_LDFLAGS)
 saxfr_SOURCES = \
        base32.cc \
        base64.cc base64.hh \
-       dns_random_urandom.cc dns_random.hh \
+       dns_random.hh \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
        dnsparser.cc dnsparser.hh \
@@ -719,7 +717,7 @@ ixfrdist_SOURCES = \
        base64.cc base64.hh \
        credentials.cc credentials.hh \
        dns.cc \
-       dns_random_urandom.cc dns_random.hh \
+       dns_random.hh \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
        dnsparser.cc dnsparser.hh \
@@ -785,7 +783,7 @@ ixplore_SOURCES = \
        base32.cc \
        base64.cc base64.hh \
        dns.cc \
-       dns_random_urandom.cc dns_random.hh \
+       dns_random.hh \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
        dnsparser.cc dnsparser.hh \
@@ -896,7 +894,7 @@ tsig_tests_SOURCES = \
        base64.cc base64.hh \
        digests.hh \
        dns.cc \
-       dns_random_urandom.cc dns_random.hh \
+       dns_random.hh \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
        dnsparser.cc dnsparser.hh \
@@ -933,7 +931,7 @@ speedtest_SOURCES = \
        base32.cc \
        base64.cc base64.hh \
        credentials.cc credentials.hh \
-       dns_random.cc dns_random.hh \
+       dns_random.hh \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
        dnsparser.cc dnsparser.hh \
@@ -980,7 +978,7 @@ dnsbulktest_SOURCES = \
        arguments.cc arguments.hh \
        base32.cc \
        base64.cc \
-       dns_random.cc dns_random.hh \
+       dns_random.hh \
        dnsbulktest.cc \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
@@ -1134,7 +1132,6 @@ pdns_notify_SOURCES = \
        base32.cc \
        base64.cc base64.hh \
        dns.cc \
-       dns_random.cc \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
        dnsparser.cc dnsparser.hh \
@@ -1341,7 +1338,6 @@ testrunner_SOURCES = \
        credentials.cc credentials.hh \
        dbdnsseckeeper.cc \
        dns.cc \
-       dns_random.cc \
        dnsbackend.cc \
        dnslabeltext.cc \
        dnsname.cc \
index 12722088bb2ab39e239a5532ef118e3e2ba9a06c..390f7188f4c02e36d6daf4351391a041024f4c53 100644 (file)
@@ -1303,8 +1303,6 @@ int main(int argc, char** argv)
 
     openssl_thread_setup();
     openssl_seed();
-    /* setup rng */
-    dns_random_init();
 
 #ifdef HAVE_LUA_RECORDS
     MiniCurl::init();
index 89886e3a704929968e6b5687dc165e4bde2bb4f2..87bfbe57edbabaa08d8f63d9b319b85e987fbac1 100644 (file)
@@ -299,7 +299,6 @@ try
 
   Netmask ecsRange;
   if (g_vm.count("ecs")) {
-    dns_random_init("0123456789abcdef");
 
     try {
       ecsRange = Netmask(g_vm["ecs"].as<string>());
diff --git a/pdns/dns_random.cc b/pdns/dns_random.cc
deleted file mode 100644 (file)
index a1991f4..0000000
+++ /dev/null
@@ -1,407 +0,0 @@
-/*
- * This file is part of PowerDNS or dnsdist.
- * Copyright -- PowerDNS.COM B.V. and its contributors
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of version 2 of the GNU General Public License as
- * published by the Free Software Foundation.
- *
- * In addition, for the avoidance of any doubt, permission is granted to
- * link this program with OpenSSL and to (re)distribute the binaries
- * produced as the result of such linking.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
- */
-#ifdef HAVE_CONFIG_H
-#include "config.h"
-#endif
-#include <sys/types.h>
-#include <sys/stat.h>
-#include <fcntl.h>
-#include <unistd.h>
-#include <cstdlib>
-#include <string>
-#include "dns_random.hh"
-#include "arguments.hh"
-#include "logger.hh"
-
-#if defined(HAVE_RANDOMBYTES_STIR)
-#include <sodium.h>
-#endif
-#if defined(HAVE_RAND_BYTES)
-#include <openssl/rand.h>
-#endif
-#if defined(HAVE_GETRANDOM)
-#include <sys/random.h>
-#endif
-
-static enum DNS_RNG {
-  RNG_UNINITIALIZED = 0,
-  RNG_SODIUM,
-  RNG_OPENSSL,
-  RNG_GETRANDOM,
-  RNG_ARC4RANDOM,
-  RNG_URANDOM,
-  RNG_KISS,
-} chosen_rng
-  = RNG_UNINITIALIZED;
-
-static int urandom_fd = -1;
-
-#if defined(HAVE_KISS_RNG)
-/* KISS is intended for development use only */
-static unsigned int kiss_seed;
-static uint32_t kiss_z, kiss_w, kiss_jsr, kiss_jcong;
-
-static void
-kiss_init(unsigned int seed)
-{
-  kiss_seed = seed;
-  kiss_jsr = 0x5eed5eed; /* simply mustn't be 0 */
-  kiss_z = 1 ^ (kiss_w = kiss_jcong = seed); /* w=z=0 is bad, see Rose */
-}
-
-static unsigned int
-kiss_rand(void)
-{
-  kiss_z = 36969 * (kiss_z & 65535) + (kiss_z >> 16);
-  kiss_w = 18000 * (kiss_w & 65535) + (kiss_w >> 16);
-  kiss_jcong = 69069 * kiss_jcong + 1234567;
-  kiss_jsr ^= (kiss_jsr << 13); /* <<17, >>13 gives cycle length 2^28.2 max */
-  kiss_jsr ^= (kiss_jsr >> 17); /* <<13, >>17 gives maximal cycle length */
-  kiss_jsr ^= (kiss_jsr << 5);
-  return (((kiss_z << 16) + kiss_w) ^ kiss_jcong) + kiss_jsr;
-}
-#endif
-
-static void dns_random_setup(bool force = false)
-{
-  string rdev;
-  string rng;
-  /* check if selection has been done */
-  if (chosen_rng > RNG_UNINITIALIZED && !force) {
-    return;
-  }
-
-/* XXX: A horrible hack to allow using dns_random in places where arguments are not available.
-        Forces /dev/urandom usage
-*/
-#if defined(USE_URANDOM_ONLY)
-  chosen_rng = RNG_URANDOM;
-  rdev = "/dev/urandom";
-#else
-  rng = ::arg()["rng"];
-  rdev = ::arg()["entropy-source"];
-  if (rng == "auto") { // NOLINT: I see no way to avoid repeating blocks reported by clang-tidy
-#if defined(HAVE_GETRANDOM)
-    chosen_rng = RNG_GETRANDOM;
-#elif defined(HAVE_ARC4RANDOM)
-    chosen_rng = RNG_ARC4RANDOM;
-#elif defined(HAVE_RANDOMBYTES_STIR)
-    chosen_rng = RNG_SODIUM;
-#elif defined(HAVE_RAND_BYTES)
-    chosen_rng = RNG_OPENSSL;
-#else
-    chosen_rng = RNG_URANDOM;
-#endif
-#if defined(HAVE_RANDOMBYTES_STIR)
-  }
-  else if (rng == "sodium") {
-    chosen_rng = RNG_SODIUM;
-#endif
-#if defined(HAVE_RAND_BYTES)
-  }
-  else if (rng == "openssl") {
-    chosen_rng = RNG_OPENSSL;
-#endif
-#if defined(HAVE_GETRANDOM)
-  }
-  else if (rng == "getrandom") {
-    chosen_rng = RNG_GETRANDOM;
-#endif
-#if defined(HAVE_ARC4RANDOM)
-  }
-  else if (rng == "arc4random") {
-    chosen_rng = RNG_ARC4RANDOM;
-#endif
-  }
-  else if (rng == "urandom") {
-    chosen_rng = RNG_URANDOM;
-#if defined(HAVE_KISS_RNG)
-  }
-  else if (rng == "kiss") {
-    chosen_rng = RNG_KISS;
-    g_log << Logger::Warning << "kiss rng should not be used in production environment" << std::endl;
-#endif
-  }
-  else {
-    throw std::runtime_error("Unsupported rng '" + rng + "'");
-  }
-
-#if defined(HAVE_RANDOMBYTES_STIR)
-  if (chosen_rng == RNG_SODIUM) {
-    if (sodium_init() == -1) {
-      throw std::runtime_error("Unable to initialize sodium crypto library");
-    }
-    /*  make sure it's set up */
-    randombytes_stir();
-  }
-#endif
-
-#if defined(HAVE_GETRANDOM)
-  if (chosen_rng == RNG_GETRANDOM) {
-    char buf = 0;
-    // some systems define getrandom but it does not really work, e.g. because it's
-    // not present in kernel.
-    if (getrandom(&buf, sizeof(buf), 0) == -1 && errno != EINTR) {
-      g_log << Logger::Warning << "getrandom() failed: " << stringerror() << ", falling back to " + rdev << std::endl;
-      chosen_rng = RNG_URANDOM;
-    }
-  }
-#endif
-
-#if defined(HAVE_RAND_BYTES)
-  if (chosen_rng == RNG_OPENSSL) {
-    int ret = 0;
-    unsigned char buf = 0;
-    if ((ret = RAND_bytes(&buf, sizeof(buf))) == -1) {
-      throw std::runtime_error("RAND_bytes not supported by current SSL engine");
-    }
-    if (ret == 0) {
-      throw std::runtime_error("Openssl RNG was not seeded");
-    }
-  }
-#endif
-#endif /* USE_URANDOM_ONLY */
-  if (chosen_rng == RNG_URANDOM) {
-    urandom_fd = open(rdev.c_str(), O_RDONLY);
-    if (urandom_fd == -1) {
-      throw std::runtime_error("Cannot open " + rdev + ": " + stringerror());
-    }
-  }
-#if defined(HAVE_KISS_RNG)
-  if (chosen_rng == RNG_KISS) {
-    int fileDesc = open(rdev.c_str(), O_RDONLY);
-    if (fileDesc == -1) {
-      throw std::runtime_error("Cannot open " + rdev + ": " + stringerror());
-    }
-    unsigned int seed = 0;
-    if (read(urandom_fd, &seed, sizeof(seed)) < 0) {
-      (void)close(fileDesc);
-      throw std::runtime_error("Cannot read random device");
-    }
-    kiss_init(seed);
-    (void)close(fileDesc);
-  }
-#endif
-}
-
-void dns_random_init(const string& data __attribute__((unused)), bool force)
-{
-  dns_random_setup(force);
-  (void)dns_random(1);
-  // init should occur already in dns_random_setup
-  // this interface is only for KISS
-#if defined(HAVE_KISS_RNG)
-  unsigned int seed;
-  if (chosen_rng != RNG_KISS)
-    return;
-  if (data.size() != 16)
-    throw std::runtime_error("invalid seed");
-  seed = (data[0] + (data[1] << 8) + (data[2] << 16) + (data[3] << 24)) ^ (data[4] + (data[5] << 8) + (data[6] << 16) + (data[7] << 24)) ^ (data[8] + (data[9] << 8) + (data[10] << 16) + (data[11] << 24)) ^ (data[12] + (data[13] << 8) + (data[14] << 16) + (data[15] << 24));
-  kiss_init(seed);
-#endif
-}
-
-uint32_t dns_random_uint32()
-{
-  if (chosen_rng == RNG_UNINITIALIZED) {
-    dns_random_setup();
-  }
-
-  switch (chosen_rng) {
-  case RNG_UNINITIALIZED:
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-  case RNG_SODIUM:
-#if defined(HAVE_RANDOMBYTES_STIR) && !defined(USE_URANDOM_ONLY)
-    return randombytes_random();
-#else
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-#endif /* RND_SODIUM */
-  case RNG_OPENSSL: {
-#if defined(HAVE_RAND_BYTES) && !defined(USE_URANDOM_ONLY)
-    uint32_t num = 0;
-    if (RAND_bytes(reinterpret_cast<unsigned char*>(&num), sizeof(num)) < 1) { // NOLINT: API
-      throw std::runtime_error("Openssl RNG was not seeded");
-    }
-    return num;
-#else
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-#endif /* RNG_OPENSSL */
-  }
-  case RNG_GETRANDOM: {
-#if defined(HAVE_GETRANDOM) && !defined(USE_URANDOM_ONLY)
-    uint32_t num = 0;
-    do {
-      auto got = getrandom(&num, sizeof(num), 0);
-      if (got == -1 && errno == EINTR) {
-        continue;
-      }
-      if (got != sizeof(num)) {
-        throw std::runtime_error("getrandom() failed: " + stringerror());
-      }
-      break;
-    } while (true);
-    return num;
-#else
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-#endif
-  }
-  case RNG_ARC4RANDOM:
-#if defined(HAVE_ARC4RANDOM) && !defined(USE_URANDOM_ONLY)
-    return arc4random();
-#else
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-#endif
-  case RNG_URANDOM: {
-    uint32_t num = 0;
-    size_t attempts = 5;
-    ssize_t got = read(urandom_fd, &num, sizeof(num));
-    do {
-      if (got < 0) {
-        if (errno == EINTR) {
-          continue;
-        }
-        throw std::runtime_error("Cannot read random device");
-      }
-      if (static_cast<size_t>(got) != sizeof(num)) {
-        /* short read, let's retry */
-        if (attempts == 0) {
-          throw std::runtime_error("Too many short reads on random device");
-        }
-        attempts--;
-        continue;
-      }
-      break;
-    } while (true);
-    return num;
-  }
-#if defined(HAVE_KISS_RNG)
-  case RNG_KISS: {
-    uint32_t num = kiss_rand();
-    return num;
-  }
-#endif
-  default:
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-  };
-}
-
-uint32_t dns_random(uint32_t upper_bound)
-{
-  if (chosen_rng == RNG_UNINITIALIZED) {
-    dns_random_setup();
-  }
-
-  if (upper_bound < 2) {
-    return 0;
-  }
-
-  unsigned int min = pdns::random_minimum_acceptable_value(upper_bound);
-
-  switch (chosen_rng) {
-  case RNG_UNINITIALIZED:
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-  case RNG_SODIUM:
-#if defined(HAVE_RANDOMBYTES_STIR) && !defined(USE_URANDOM_ONLY)
-    return randombytes_uniform(upper_bound);
-#else
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-#endif /* RND_SODIUM */
-  case RNG_OPENSSL: {
-#if defined(HAVE_RAND_BYTES) && !defined(USE_URANDOM_ONLY)
-    uint32_t num = 0;
-    do {
-      if (RAND_bytes(reinterpret_cast<unsigned char*>(&num), sizeof(num)) < 1) { // NOLINT: API
-        throw std::runtime_error("Openssl RNG was not seeded");
-      }
-    } while (num < min);
-
-    return num % upper_bound;
-#else
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-#endif /* RNG_OPENSSL */
-  }
-  case RNG_GETRANDOM: {
-#if defined(HAVE_GETRANDOM) && !defined(USE_URANDOM_ONLY)
-    uint32_t num = 0;
-    do {
-      auto got = getrandom(&num, sizeof(num), 0);
-      if (got == -1 && errno == EINTR) {
-        continue;
-      }
-      if (got != sizeof(num)) {
-        throw std::runtime_error("getrandom() failed: " + stringerror());
-      }
-    } while (num < min);
-
-    return num % upper_bound;
-#else
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-#endif
-  }
-  case RNG_ARC4RANDOM:
-#if defined(HAVE_ARC4RANDOM) && !defined(USE_URANDOM_ONLY)
-    return arc4random_uniform(upper_bound);
-#else
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-#endif
-  case RNG_URANDOM: {
-    uint32_t num = 0;
-    size_t attempts = 5;
-    do {
-      ssize_t got = read(urandom_fd, &num, sizeof(num));
-      if (got < 0) {
-        if (errno == EINTR) {
-          continue;
-        }
-        throw std::runtime_error("Cannot read random device");
-      }
-      if (static_cast<size_t>(got) != sizeof(num)) {
-        /* short read, let's retry */
-        if (attempts == 0) {
-          throw std::runtime_error("Too many short reads on random device");
-        }
-        attempts--;
-        continue;
-      }
-    } while (num < min);
-
-    return num % upper_bound;
-  }
-#if defined(HAVE_KISS_RNG)
-  case RNG_KISS: {
-    uint32_t num = 0;
-    do {
-      num = kiss_rand();
-    } while (num < min);
-
-    return num % upper_bound;
-  }
-#endif
-  default:
-    throw std::runtime_error("Unreachable at " __FILE__ ":" + std::to_string(__LINE__)); // cannot be reached
-  };
-}
-
-uint16_t dns_random_uint16()
-{
-  return dns_random_uint32() & 0xffff;
-}
index 634d233c1c39702d3e15a348cad2c1b262998df8..c3bd314d16f77dba43917af8c6007b2cc1f8709a 100644 (file)
 #include <limits>
 #include <string>
 
-void dns_random_init(const std::string& data = "", bool force_reinit = false);
-uint32_t dns_random(uint32_t upper_bound);
-uint32_t dns_random_uint32();
-uint16_t dns_random_uint16();
+#include <ext/arc4random/arc4random.hh>
+
+inline uint32_t dns_random(uint32_t upper_bound)
+{
+  return arc4random_uniform(upper_bound);
+}
+
+inline uint32_t dns_random_uint32()
+{
+  return arc4random();
+}
+
+inline uint16_t dns_random_uint16()
+{
+  return arc4random() & 0xffff;
+}
 
 namespace pdns
 {
diff --git a/pdns/dns_random_urandom.cc b/pdns/dns_random_urandom.cc
deleted file mode 100644 (file)
index 708d3df..0000000
+++ /dev/null
@@ -1,2 +0,0 @@
-#define USE_URANDOM_ONLY
-#include "dns_random.cc"
index aaac2e20666614f0b500b01f228fd73c5be04f6f..9b951a58669444df7ef415a935fbd226d0680908 100644 (file)
@@ -13,7 +13,8 @@ AM_CPPFLAGS += $(SYSTEMD_CFLAGS) \
 
 ACLOCAL_AMFLAGS = -I m4
 
-SUBDIRS=ext/ipcrypt \
+SUBDIRS=ext/arc4random \
+       ext/ipcrypt \
        ext/yahttp
 
 CLEANFILES = \
@@ -354,7 +355,8 @@ dnsdist_LDADD = \
        $(SYSTEMD_LIBS) \
        $(NET_SNMP_LIBS) \
        $(LIBCAP_LIBS) \
-       $(IPCRYPT_LIBS)
+       $(IPCRYPT_LIBS) \
+       $(ARC4RANDOM_LIBS)
 
 testrunner_LDFLAGS = \
        $(AM_LDFLAGS) \
@@ -368,7 +370,8 @@ testrunner_LDADD = \
        $(LIBSODIUM_LIBS) \
        $(LUA_LIBS) \
        $(RT_LIBS) \
-       $(LIBCAP_LIBS)
+       $(LIBCAP_LIBS) \
+       $(ARC4RANDOM_LIBS)
 
 if HAVE_CDB
 dnsdist_LDADD += $(CDB_LDFLAGS) $(CDB_LIBS)
index 96caf08194aeb184b547eb35fac6c29204314370..6e758c63d7f9e5d93255c90955db9dd70578df18 100644 (file)
@@ -48,11 +48,13 @@ PDNS_WITH_SERVICE_USER([dnsdist])
 
 dnl the *_r functions are in posix so we can use them unconditionally, but the ext/yahttp code is
 dnl using the defines.
-AC_CHECK_FUNCS_ONCE([localtime_r gmtime_r getrandom])
+AC_CHECK_FUNCS_ONCE([localtime_r gmtime_r])
+AC_CHECK_FUNCS_ONCE([getrandom getentropy arc4random arc4random_uniform arc4random_buf])
 AC_SUBST([YAHTTP_CFLAGS], ['-I$(top_srcdir)/ext/yahttp'])
 AC_SUBST([YAHTTP_LIBS], ['$(top_builddir)/ext/yahttp/yahttp/libyahttp.la'])
 AC_SUBST([IPCRYPT_CFLAGS], ['-I$(top_srcdir)/ext/ipcrypt'])
 AC_SUBST([IPCRYPT_LIBS], ['$(top_builddir)/ext/ipcrypt/libipcrypt.la'])
+AC_SUBST([ARC4RANDOM_LIBS], ['$(top_builddir)/ext/arc4random/libarc4random.la'])
 
 PDNS_WITH_LUA([mandatory])
 AS_IF([test "x$LUAPC" = "xluajit"], [
@@ -156,6 +158,7 @@ AS_IF([test "x$PACKAGEVERSION" != "x"],
 )
 
 AC_CONFIG_FILES([Makefile
+        ext/arc4random/Makefile
         ext/yahttp/Makefile
         ext/yahttp/yahttp/Makefile
         ext/ipcrypt/Makefile])
diff --git a/pdns/dnsdistdist/ext/arc4random/.gitignore b/pdns/dnsdistdist/ext/arc4random/.gitignore
new file mode 100644 (file)
index 0000000..24ad051
--- /dev/null
@@ -0,0 +1,5 @@
+*.la
+*.lo
+*.o
+Makefile
+Makefile.in
diff --git a/pdns/dnsdistdist/ext/arc4random/Makefile.am b/pdns/dnsdistdist/ext/arc4random/Makefile.am
new file mode 120000 (symlink)
index 0000000..c55d4b1
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/Makefile.am
\ No newline at end of file
diff --git a/pdns/dnsdistdist/ext/arc4random/arc4random.c b/pdns/dnsdistdist/ext/arc4random/arc4random.c
new file mode 120000 (symlink)
index 0000000..9ffca36
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/arc4random.c
\ No newline at end of file
diff --git a/pdns/dnsdistdist/ext/arc4random/arc4random.h b/pdns/dnsdistdist/ext/arc4random/arc4random.h
new file mode 120000 (symlink)
index 0000000..55bd2ca
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/arc4random.h
\ No newline at end of file
diff --git a/pdns/dnsdistdist/ext/arc4random/arc4random.hh b/pdns/dnsdistdist/ext/arc4random/arc4random.hh
new file mode 120000 (symlink)
index 0000000..9fde95a
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/arc4random.hh
\ No newline at end of file
diff --git a/pdns/dnsdistdist/ext/arc4random/arc4random_uniform.c b/pdns/dnsdistdist/ext/arc4random/arc4random_uniform.c
new file mode 120000 (symlink)
index 0000000..fdc2e98
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/arc4random_uniform.c
\ No newline at end of file
diff --git a/pdns/dnsdistdist/ext/arc4random/bsd-getentropy.c b/pdns/dnsdistdist/ext/arc4random/bsd-getentropy.c
new file mode 120000 (symlink)
index 0000000..afa68dd
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/bsd-getentropy.c
\ No newline at end of file
diff --git a/pdns/dnsdistdist/ext/arc4random/chacha_private.h b/pdns/dnsdistdist/ext/arc4random/chacha_private.h
new file mode 120000 (symlink)
index 0000000..b721783
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/chacha_private.h
\ No newline at end of file
diff --git a/pdns/dnsdistdist/ext/arc4random/includes.h b/pdns/dnsdistdist/ext/arc4random/includes.h
new file mode 120000 (symlink)
index 0000000..7536dff
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/includes.h
\ No newline at end of file
diff --git a/pdns/dnsdistdist/ext/arc4random/log.h b/pdns/dnsdistdist/ext/arc4random/log.h
new file mode 120000 (symlink)
index 0000000..60bb752
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/log.h
\ No newline at end of file
index 6c1193f5fca7601635f686f6b15868b5662bad00..81d7b03cef55ba3c418a4fc079a6b87c32b6fd55 100644 (file)
@@ -1382,8 +1382,6 @@ int main(int argc, char** argv) {
   // Init the things we need
   reportAllTypes();
 
-  dns_random_init();
-
   std::thread ut(updateThread,
       config["work-dir"].as<string>(),
       config["keep"].as<uint16_t>(),
index 525b4636f43a2e50ccaad1b81b0673707f087169..2f6a173ca0e224b52e866f514f5a10cfcd5e8cc0 100644 (file)
@@ -156,8 +156,6 @@ static void loadMainConfig(const std::string& configdir)
   }
 #endif
   openssl_seed();
-  /* init rng before chroot */
-  dns_random_init();
 
   if (!::arg()["chroot"].empty()) {
     if (chroot(::arg()["chroot"].c_str())<0 || chdir("/") < 0) {
index ac6a44ea4730e70e78186c7bd3433dae8614910f..f65fa102c5e37d7a5254ee052a0b2bddd8f3b5c2 100644 (file)
@@ -1,5 +1,6 @@
 JSON11_LIBS = $(top_srcdir)/ext/json11/libjson11.la
 PROBDS_LIBS = $(top_srcdir)/ext/probds/libprobds.la
+ARC4RANDOM_LIBS = $(top_srcdir)/ext/arc4random/libarc4random.la
 
 AM_CPPFLAGS = $(LUA_CFLAGS) $(YAHTTP_CFLAGS) $(BOOST_CPPFLAGS) $(LIBSODIUM_CFLAGS) $(NET_SNMP_CFLAGS) $(LIBCAP_CFLAGS) $(SANITIZER_FLAGS) -O3 -Wall -pthread -DSYSCONFDIR=\"${sysconfdir}\" $(SYSTEMD_CFLAGS)
 
@@ -113,7 +114,7 @@ pdns_recursor_SOURCES = \
        comment.hh \
        credentials.cc credentials.hh \
        dns.hh dns.cc \
-       dns_random.hh dns_random.cc \
+       dns_random.hh \
        dnsbackend.hh \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
@@ -236,7 +237,8 @@ pdns_recursor_LDADD = \
        $(RT_LIBS) \
        $(BOOST_SYSTEM_LIBS) \
        $(PROBDS_LIBS) \
-       $(LIBCAP_LIBS)
+       $(LIBCAP_LIBS) \
+       $(ARC4RANDOM_LIBS)
 
 pdns_recursor_LDFLAGS = $(AM_LDFLAGS) \
        $(LIBCRYPTO_LDFLAGS) $(BOOST_CONTEXT_LDFLAGS) \
@@ -264,7 +266,7 @@ testrunner_SOURCES = \
        circular_buffer.hh \
        credentials.cc credentials.hh \
        dns.cc dns.hh \
-       dns_random.cc dns_random.hh \
+       dns_random.hh \
        dnslabeltext.cc \
        dnsname.cc dnsname.hh \
        dnsparser.hh dnsparser.cc \
@@ -382,7 +384,8 @@ testrunner_LDADD = \
        $(RT_LIBS) \
        $(BOOST_SYSTEM_LIBS) \
        $(PROBDS_LIBS) \
-       $(LIBCAP_LIBS)
+       $(LIBCAP_LIBS) \
+       $(ARC4RANDOM_LIBS)
 
 if NOD_ENABLED
 testrunner_SOURCES +=   nod.hh nod.cc \
@@ -399,7 +402,7 @@ pdns_recursor_SOURCES += \
        sodiumsigners.cc
 pdns_recursor_LDADD += $(LIBSODIUM_LIBS)
 
-rec_control_LDADD += $(LIBSODIUM_LIBS)
+rec_control_LDADD += $(LIBSODIUM_LIBS) $(ARC4RANDOM_LIBS)
 
 testrunner_SOURCES += \
        sodiumsigners.cc
index 8f7e900b7e1da47677680bc49a040db5fd1cf4ce..52bc6d89348e27bd2f53c15e9d397e4c40c9a26f 100644 (file)
@@ -112,7 +112,8 @@ PDNS_CHECK_CURL
 
 dnl the *_r functions are in posix so we can use them unconditionally, but the ext/yahttp code is
 dnl using the defines.
-AC_CHECK_FUNCS_ONCE([localtime_r gmtime_r strcasestr getrandom arc4random])
+AC_CHECK_FUNCS_ONCE([localtime_r gmtime_r strcasestr])
+AC_CHECK_FUNCS_ONCE([getrandom getentropy arc4random arc4random_uniform arc4random_buf])
 
 PDNS_CHECK_PTHREAD_NP
 
@@ -190,6 +191,7 @@ CXXVERSION=`$CXX --version | head -1`
 
 AC_CONFIG_FILES([Makefile
        ext/Makefile
+       ext/arc4random/Makefile
        ext/json11/Makefile
        ext/probds/Makefile
        ext/yahttp/Makefile
diff --git a/pdns/recursordist/dns_random.cc b/pdns/recursordist/dns_random.cc
deleted file mode 120000 (symlink)
index 9fa1021..0000000
+++ /dev/null
@@ -1 +0,0 @@
-../dns_random.cc
\ No newline at end of file
diff --git a/pdns/recursordist/dns_random_urandom.cc b/pdns/recursordist/dns_random_urandom.cc
deleted file mode 120000 (symlink)
index a412aea..0000000
+++ /dev/null
@@ -1 +0,0 @@
-../dns_random_urandom.cc
\ No newline at end of file
index a908d92a41a21726106bbdbdd4897b9c614c8384..65131d0b277e4c834d4cef4d47d3011cfa477cd3 100644 (file)
@@ -1,9 +1,11 @@
 SUBDIRS = \
+       arc4random \
        yahttp \
        json11 \
        probds
 
 DIST_SUBDIRS = \
+       arc4random \
        yahttp \
        json11 \
        probds
diff --git a/pdns/recursordist/ext/arc4random/.gitignore b/pdns/recursordist/ext/arc4random/.gitignore
new file mode 100644 (file)
index 0000000..24ad051
--- /dev/null
@@ -0,0 +1,5 @@
+*.la
+*.lo
+*.o
+Makefile
+Makefile.in
diff --git a/pdns/recursordist/ext/arc4random/Makefile.am b/pdns/recursordist/ext/arc4random/Makefile.am
new file mode 120000 (symlink)
index 0000000..c55d4b1
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/Makefile.am
\ No newline at end of file
diff --git a/pdns/recursordist/ext/arc4random/arc4random.c b/pdns/recursordist/ext/arc4random/arc4random.c
new file mode 120000 (symlink)
index 0000000..9ffca36
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/arc4random.c
\ No newline at end of file
diff --git a/pdns/recursordist/ext/arc4random/arc4random.h b/pdns/recursordist/ext/arc4random/arc4random.h
new file mode 120000 (symlink)
index 0000000..55bd2ca
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/arc4random.h
\ No newline at end of file
diff --git a/pdns/recursordist/ext/arc4random/arc4random.hh b/pdns/recursordist/ext/arc4random/arc4random.hh
new file mode 120000 (symlink)
index 0000000..9fde95a
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/arc4random.hh
\ No newline at end of file
diff --git a/pdns/recursordist/ext/arc4random/arc4random_uniform.c b/pdns/recursordist/ext/arc4random/arc4random_uniform.c
new file mode 120000 (symlink)
index 0000000..fdc2e98
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/arc4random_uniform.c
\ No newline at end of file
diff --git a/pdns/recursordist/ext/arc4random/bsd-getentropy.c b/pdns/recursordist/ext/arc4random/bsd-getentropy.c
new file mode 120000 (symlink)
index 0000000..afa68dd
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/bsd-getentropy.c
\ No newline at end of file
diff --git a/pdns/recursordist/ext/arc4random/chacha_private.h b/pdns/recursordist/ext/arc4random/chacha_private.h
new file mode 120000 (symlink)
index 0000000..b721783
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/chacha_private.h
\ No newline at end of file
diff --git a/pdns/recursordist/ext/arc4random/includes.h b/pdns/recursordist/ext/arc4random/includes.h
new file mode 120000 (symlink)
index 0000000..7536dff
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/includes.h
\ No newline at end of file
diff --git a/pdns/recursordist/ext/arc4random/log.h b/pdns/recursordist/ext/arc4random/log.h
new file mode 120000 (symlink)
index 0000000..60bb752
--- /dev/null
@@ -0,0 +1 @@
+../../../../ext/arc4random/log.h
\ No newline at end of file
index f46d32eab1c66527f98ef6d301a52ab566e2b316..e94401e74f18c4efd620a73aecdedfe21a9c8837 100644 (file)
@@ -2131,8 +2131,6 @@ static int serviceMain(Logr::log_t log)
 
   openssl_thread_setup();
   openssl_seed();
-  /* setup rng before chroot */
-  dns_random_init();
 
   if (::arg()["server-id"].empty()) {
     ::arg().set("server-id") = myHostname.has_value() ? *myHostname : "";
index b8268d01d240b99a2817c640eca9845c4009960f..055cb44bed9d9638a7c4df6bf3479cfc69515e8b 100644 (file)
@@ -1084,7 +1084,6 @@ struct RndSpeedTest
   explicit RndSpeedTest(std::string which) : name(which){
     ::arg().set("entropy-source", "If set, read entropy from this file")="/dev/urandom";
     ::arg().set("rng", "") = which;
-    dns_random_init("", true);
   }
   string getName() const
   {
index db8a0eb0ab782aa7842a60727b20da10b2ff8c84..7c19d72ec82a9944e8c80a6a5aa24cb870fbc5cd 100644 (file)
@@ -44,11 +44,8 @@ const std::vector<string> rndSources = {
 
 BOOST_AUTO_TEST_CASE(test_dns_random_garbage)
 {
-
   ::arg().set("rng") = "garbage";
   ::arg().set("entropy-source") = "/dev/urandom";
-
-  BOOST_CHECK_THROW(dns_random_init("", true), std::runtime_error);
 }
 
 BOOST_AUTO_TEST_CASE(test_dns_random_upper_bound)
@@ -56,8 +53,6 @@ BOOST_AUTO_TEST_CASE(test_dns_random_upper_bound)
   ::arg().set("rng") = "auto";
   ::arg().set("entropy-source") = "/dev/urandom";
 
-  dns_random_init("", true);
-
   map<unsigned int, bool> seen;
   for (unsigned int iteration = 0; iteration < 100000; ++iteration) {
     seen[dns_random(10)] = true;
@@ -81,8 +76,6 @@ static void test_dns_random_avg(const string& source)
   ::arg().set("rng") = source;
   ::arg().set("entropy-source") = "/dev/urandom";
 
-  dns_random_init("", true);
-
   acc_t acc;
 
   for (unsigned int iteration = 0; iteration < 100000; ++iteration) {
@@ -99,8 +92,6 @@ static void test_dns_random_uint32_avg(const string& source)
   ::arg().set("rng") = source;
   ::arg().set("entropy-source") = "/dev/urandom";
 
-  dns_random_init("", true);
-
   acc_t acc;
 
   for (unsigned int iteration = 0; iteration < 100000; ++iteration) {