Repository: randombit/botan
Pull request #2673 (2021-03-29 12:10:13)

fix: forward executor through async_shutdown wrapper
Make TLS::Stream::async_shutdown's internal wrapper correctly forward the executor to the new handler as suggested in #2648. Backport from #2667.


Patch:
diff --git a/configure.py b/configure.py
index 1cea37e16..e8ed0a24a 100755
--- a/configure.py
+++ b/configure.py
@@ -333,9 +333,6 @@ def process_command_line(args): # pylint: disable=too-many-locals,too-many-state
     target_group.add_option('--ldflags', metavar='FLAGS',
                             help='set linker flags', default=None)
 
-    target_group.add_option('--extra-libs', metavar='LIBS',
-                            help='specify extra libraries to link against', default='')
-
     target_group.add_option('--ar-command', dest='ar_command', metavar='AR', default=None,
                             help='set path to static archive creator')
 
@@ -2010,12 +2007,6 @@ def create_template_vars(source_paths, build_paths, options, modules, cc, arch,
         else:
             return '%s %s' % (options.compiler_cache, cxx)
 
-    def extra_libs(libs, cc):
-        if libs is None:
-            return ''
-
-        return ' '.join([(cc.add_lib_option % lib) for lib in libs.split(',') if lib != ''])
-
     variables = {
         'version_major':  Version.major(),
         'version_minor':  Version.minor(),
@@ -2140,7 +2131,6 @@ def create_template_vars(source_paths, build_paths, options, modules, cc, arch,
         'cc_sysroot': sysroot_option(),
         'cc_compile_flags': options.cxxflags or cc.cc_compile_flags(options),
         'ldflags': options.ldflags or '',
-        'extra_libs': extra_libs(options.extra_libs, cc),
         'cc_warning_flags': cc.cc_warning_flags(options),
         'output_to_exe': cc.output_to_exe,
         'cc_macro': cc.macro_name,
@@ -3016,10 +3006,6 @@ def canonicalize_options(options, info_os, info_arch):
     if options.build_fuzzers == 'libfuzzer' and options.fuzzer_lib is None:
         options.fuzzer_lib = 'Fuzzer'
 
-    if options.ldflags is not None:
-        libs = [m.group(1) for m in re.finditer(r'-l([a-z0-9]+)', options.ldflags)]
-        options.extra_libs += ','.join(libs)
-
 # Checks user options for consistency
 # This method DOES NOT change options on behalf of the user but explains
 # why the given configuration does not work.
diff --git a/news.rst b/news.rst
index a3f083d00..da1d827e1 100644
--- a/news.rst
+++ b/news.rst
@@ -1,26 +1,11 @@
 Release Notes
 ========================================
 
-Version 2.18.0, Not Yet Released
-^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-
-* Add support for implementing custom RNG objects through the
-  FFI interface (GH #2627 #2600)
-
-* Improve safegcd bounds, improving runtime performance (GH #2628 #2619)
-
-* Fix a bug introduced in 2.9.0 where BigInt::operator< would return
-  an incorrect result if both operands were negative. (GH #2641 #2638)
-
-* Fix a regression introduced in 2.17.0 where LDFLAGS which add an extra
-  library (such as ``-latomic`` needed on SPARC) were not always applied
-  effectively. (GH #2622 #2623 #2625)
-
 Version 2.17.3, 2020-12-21
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-* CVE-2021-24115 Change base64, base58, base32, and hex encoding and
-  decoding opearations to run in constant time (GH #2549)
+* Change base64, base58, base32, and hex encoding and decoding opearations
+  to run in constant time (GH #2549)
 
 * Fix a build problem on PPC64 building with Clang (GH #2547)
 
diff --git a/src/build-data/makefile.in b/src/build-data/makefile.in
index 16d077e82..253ff2a98 100644
--- a/src/build-data/makefile.in
+++ b/src/build-data/makefile.in
@@ -21,7 +21,7 @@ LDFLAGS        = %{ldflags}
 EXE_LINK_CMD   = %{exe_link_cmd}
 
 LIB_LINKS_TO   = %{external_link_cmd} %{link_to}
-EXE_LINKS_TO   = %{link_to_botan} $(LIB_LINKS_TO) %{extra_libs}
+EXE_LINKS_TO   = %{link_to_botan} $(LIB_LINKS_TO)
 
 BUILD_FLAGS    = $(ABI_FLAGS) $(LANG_FLAGS) $(CXXFLAGS) $(WARN_FLAGS)
 
diff --git a/src/build-data/version.txt b/src/build-data/version.txt
index 95f85d964..2da2d05cf 100644
--- a/src/build-data/version.txt
+++ b/src/build-data/version.txt
@@ -1,9 +1,9 @@
 
 release_major = 2
-release_minor = 18
-release_patch = 0
+release_minor = 17
+release_patch = 3
 release_suffix = ''
-release_so_abi_rev = 18
+release_so_abi_rev = 17
 
 # These are set by the distribution script
 release_vc_rev = None
diff --git a/src/fuzzer/bn_cmp.cpp b/src/fuzzer/bn_cmp.cpp
deleted file mode 100644
index 48c25f324..000000000
--- a/src/fuzzer/bn_cmp.cpp
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
-* (C) 2021 Jack Lloyd
-*
-* Botan is released under the Simplified BSD License (see license.txt)
-*/
-
-#include "fuzzers.h"
-
-#include <botan/bigint.h>
-
-void fuzz(const uint8_t in[], size_t len)
-   {
-   const size_t max_bits = 512;
-
-   if(len < 3 || len > 1 + 2*(max_bits/8))
-      return;
-
-   const uint8_t signs = in[0];
-   const size_t x_len = (len - 1) / 2;
-
-   Botan::BigInt x = Botan::BigInt::decode(in + 1, x_len);
-   Botan::BigInt y = Botan::BigInt::decode(in + 1 + x_len, len - x_len - 1);
-
-   if(signs & 1)
-      x.flip_sign();
-   if(signs & 2)
-      y.flip_sign();
-
-   const Botan::BigInt d1 = x - y;
-   const Botan::BigInt d2 = y - x;
-
-   FUZZER_ASSERT_TRUE(d1.cmp(d2, false) == 0);
-
-   const bool is_eq = (x == y);
-   const bool is_lt = (x < y);
-   const bool is_gt = (x > y);
-   const bool is_lte = (x <= y);
-   const bool is_gte = (x >= y);
-
-   if(is_eq)
-      {
-      FUZZER_ASSERT_TRUE(d1.is_zero());
-      FUZZER_ASSERT_TRUE(d2.is_zero());
-      }
-
-   if(is_lte)
-      {
-      FUZZER_ASSERT_TRUE(is_lt || is_eq);
-      }
-
-   if(is_gte)
-      {
-      FUZZER_ASSERT_TRUE(is_gt || is_eq);
-      }
-
-   if(is_lt)
-      {
-      FUZZER_ASSERT_TRUE(!is_gt);
-      FUZZER_ASSERT_TRUE(d1.is_nonzero());
-      FUZZER_ASSERT_TRUE(d2.is_nonzero());
-      FUZZER_ASSERT_TRUE(d1.is_negative());
-      FUZZER_ASSERT_TRUE(d2.is_positive());
-      }
-
-   if(is_gt)
-      {
-      FUZZER_ASSERT_TRUE(!is_lt);
-      FUZZER_ASSERT_TRUE(d1.is_nonzero());
-      FUZZER_ASSERT_TRUE(d2.is_nonzero());
-      FUZZER_ASSERT_TRUE(d1.is_positive());
-      FUZZER_ASSERT_TRUE(d2.is_negative());
-      }
-   }
-
diff --git a/src/lib/ffi/ffi.cpp b/src/lib/ffi/ffi.cpp
index 9126394ed..257871a61 100644
--- a/src/lib/ffi/ffi.cpp
+++ b/src/lib/ffi/ffi.cpp
@@ -200,10 +200,6 @@ uint32_t botan_ffi_api_version()
 
 int botan_ffi_supports_api(uint32_t api_version)
    {
-   // This is the API introduced in 2.18
-   if(api_version == 20210220)
-      return BOTAN_FFI_SUCCESS;
-
    // This is the API introduced in 2.13
    if(api_version == 20191214)
       return BOTAN_FFI_SUCCESS;
diff --git a/src/lib/ffi/ffi.h b/src/lib/ffi/ffi.h
index c9511e97e..cf8931acf 100644
--- a/src/lib/ffi/ffi.h
+++ b/src/lib/ffi/ffi.h
@@ -1,7 +1,6 @@
 /*
 * FFI (C89 API)
 * (C) 2015,2017 Jack Lloyd
-* (C) 2021 René Fischer
 *
 * Botan is released under the Simplified BSD License (see license.txt)
 */
@@ -201,20 +200,6 @@ typedef struct botan_rng_struct* botan_rng_t;
 */
 BOTAN_PUBLIC_API(2,0) int botan_rng_init(botan_rng_t* rng, const char* rng_type);
 
-/**
-* Initialize a custom random number generator from a set of callback functions
-* @param rng rng object
-* @param rng_name name of the rng
-* @param context An application-specific context passed to the callback functions
-* @param get_cb Callback for getting random bytes from the rng, return 0 for success
-* @param add_entry_cb Callback for adding entropy to the rng, return 0 for success, may be NULL
-* @param destroy_cb Callback called when rng is destroyed, may be NULL
-*/
-BOTAN_PUBLIC_API(2,17) int botan_rng_init_custom(botan_rng_t* rng_out, const char* rng_name, void* context,
-                                                 int(* get_cb)(void* context, uint8_t* out, size_t out_len),
-                                                 int(* add_entropy_cb)(void* context, const uint8_t input[], size_t length),
-                                                 void(* destroy_cb)(void* context));
-
 /**
 * Get random bytes from a random number generator
 * @param rng rng object
diff --git a/src/lib/ffi/ffi_rng.cpp b/src/lib/ffi/ffi_rng.cpp
index 7bb365a24..617723cdd 100644
--- a/src/lib/ffi/ffi_rng.cpp
+++ b/src/lib/ffi/ffi_rng.cpp
@@ -1,6 +1,5 @@
 /*
 * (C) 2015,2017 Jack Lloyd
-* (C) 2021 René Fischer
 *
 * Botan is released under the Simplified BSD License (see license.txt)
 */
@@ -11,8 +10,6 @@
 #include <botan/system_rng.h>
 #include <botan/auto_rng.h>
 
-#include <functional>
-
 #if defined(BOTAN_HAS_PROCESSOR_RNG)
    #include <botan/processor_rng.h>
 #endif
@@ -60,101 +57,6 @@ int botan_rng_init(botan_rng_t* rng_out, const char* rng_type)
       });
    }
 
-int botan_rng_init_custom(botan_rng_t* rng_out, const char* rng_name, void* context,
-                          int(* get_cb)(void* context, uint8_t* out, size_t out_len),
-                          int(* add_entropy_cb)(void* context, const uint8_t input[], size_t length),
-                          void(* destroy_cb)(void* context))
-{
-return ffi_guard_thunk(__func__,[=]() -> int {
-   if(rng_out == nullptr)
-      return BOTAN_FFI_ERROR_NULL_POINTER;
-
-   if(rng_name == nullptr)
-      return BOTAN_FFI_ERROR_NULL_POINTER;
-
-   if(get_cb == nullptr)
-      return BOTAN_FFI_ERROR_NULL_POINTER;
-
-   class Custom_RNG : public Botan::RandomNumberGenerator
-      {
-      public:
-         Custom_RNG(const std::string& name, void* context,
-                    int(* get_cb)(void* context, uint8_t* out, size_t out_len),
-                    int(* add_entropy_cb)(void* context, const uint8_t input[], size_t length),
-                    void(* destroy_cb)(void* context)) :
-            m_name(name)
-            {
-               m_context = context;
-               m_get_cb = get_cb;
-               m_add_entropy_cb = add_entropy_cb;
-               m_destroy_cb = destroy_cb;
-            }
-
-         ~Custom_RNG()
-         {
-            if(m_destroy_cb)
-            {
-               m_destroy_cb(m_context);
-            }
-         }
-
-         void randomize(uint8_t output[], size_t length) override
-         {
-            int rc = m_get_cb(m_context, output, length);
-            if(rc)
-            {
-               throw Botan::Invalid_State("Failed to get random from C callback, rc=" + std::to_string(rc));
-            }
-         }
-
-         bool accepts_input() const override
-         {
-            return m_add_entropy_cb != nullptr;
-         }
-
-         void add_entropy(const uint8_t input[], size_t length) override
-         {
-            if(m_add_entropy_cb == nullptr)
-            {
-               return;
-            }
-
-            int rc = m_add_entropy_cb(m_context, input, length);
-            if(rc)
-            {
-               throw Botan::Invalid_State("Failed to add entropy via C callback, rc=" + std::to_string(rc));
-            }
-         }
-
-         std::string name() const override
-         {
-            return m_name;
-         }
-
-         void clear() override
-         {
-         }
-
-         bool is_seeded() const override
-         {
-            return true;
-         }
-
-      private:
-         std::string m_name;
-         void* m_context;
-         std::function<int(void* context, uint8_t* out, size_t out_len)> m_get_cb;
-         std::function<int(void* context, const uint8_t input[], size_t length)> m_add_entropy_cb;
-         std::function<void(void* context)> m_destroy_cb;
-   };
-
-   std::unique_ptr<Botan::RandomNumberGenerator> rng(new Custom_RNG(rng_name, context, get_cb, add_entropy_cb, destroy_cb));
-
-   *rng_out = new botan_rng_struct(rng.release());
-   return BOTAN_FFI_SUCCESS;
-   });
-}
-
 int botan_rng_destroy(botan_rng_t rng)
    {
    return BOTAN_FFI_CHECKED_DELETE(rng);
diff --git a/src/lib/ffi/info.txt b/src/lib/ffi/info.txt
index 865beb61e..3de60322e 100644
--- a/src/lib/ffi/info.txt
+++ b/src/lib/ffi/info.txt
@@ -1,5 +1,5 @@
 <defines>
-FFI -> 20210220
+FFI -> 20191214
 </defines>
 
 <header:internal>
diff --git a/src/lib/math/bigint/bigint.cpp b/src/lib/math/bigint/bigint.cpp
index 7bcbaf37f..8510da1d3 100644
--- a/src/lib/math/bigint/bigint.cpp
+++ b/src/lib/math/bigint/bigint.cpp
@@ -165,8 +165,8 @@ bool BigInt::is_less_than(const BigInt& other) const
 
    if(other.is_negative() && this->is_negative())
       {
-      return bigint_ct_is_lt(other.data(), other.sig_words(),
-                             this->data(), this->sig_words()).is_set();
+      return !bigint_ct_is_lt(other.data(), other.sig_words(),
+                              this->data(), this->sig_words(), true).is_set();
       }
 
    return bigint_ct_is_lt(this->data(), this->sig_words(),
diff --git a/src/lib/math/numbertheory/numthry.cpp b/src/lib/math/numbertheory/numthry.cpp
index 51afa94c6..06d837801 100644
--- a/src/lib/math/numbertheory/numthry.cpp
+++ b/src/lib/math/numbertheory/numthry.cpp
@@ -61,29 +61,13 @@ size_t low_zero_bits(const BigInt& n)
    return seen_nonempty_word.if_set_return(low_zero);
    }
 
-namespace {
-
-size_t safegcd_loop_bound(size_t f_bits, size_t g_bits)
-   {
-   const size_t d = std::max(f_bits, g_bits);
-
-   if(d < 46)
-      return (49*d + 80) / 17;
-   else
-      return (49*d + 57) / 17;
-   }
-
-}
-
 /*
 * Calculate the GCD
 */
 BigInt gcd(const BigInt& a, const BigInt& b)
    {
-   if(a.is_zero())
-      return abs(b);
-   if(b.is_zero())
-      return abs(a);
+   if(a.is_zero() || b.is_zero())
+      return 0;
    if(a == 1 || b == 1)
       return 1;
 
@@ -107,7 +91,7 @@ BigInt gcd(const BigInt& a, const BigInt& b)
 
    int32_t delta = 1;
 
-   const size_t loop_cnt = safegcd_loop_bound(f.bits(), g.bits());
+   const size_t loop_cnt = 4 + 3*std::max(f.bits(), g.bits());
 
    BigInt newg, t;
    for(size_t i = 0; i != loop_cnt; ++i)
@@ -116,8 +100,8 @@ BigInt gcd(const BigInt& a, const BigInt& b)
 
       const bool need_swap = (g.is_odd() && delta > 0);
 
-      // if(need_swap) { delta *= -1 } else { delta *= 1 }
-      delta *= CT::Mask<uint8_t>::expand(need_swap).if_not_set_return(2) - 1;
+      // if(need_swap) delta *= -1
+      delta *= CT::Mask<uint8_t>::expand(need_swap).select(0, 2) - 1;
       f.ct_cond_swap(need_swap, g);
       g.ct_cond_swap(need_swap, newg);
 
@@ -132,8 +116,6 @@ BigInt gcd(const BigInt& a, const BigInt& b)
    f.const_time_unpoison();
    g.const_time_unpoison();
 
-   BOTAN_ASSERT_NOMSG(g.is_zero());
-
    return f;
    }
 
diff --git a/src/lib/tls/asio/asio_stream.h b/src/lib/tls/asio/asio_stream.h
index 24286f10d..bef95e44a 100644
--- a/src/lib/tls/asio/asio_stream.h
+++ b/src/lib/tls/asio/asio_stream.h
@@ -334,28 +334,36 @@ class Stream
 
    private:
       /**
-       * @brief Internal wrapper type to adapt the expected signature of `async_shutdown`
-       *        to the completion handler signature of `AsyncWriteOperation`.
+       * @brief Internal wrapper type to adapt the expected signature of `async_shutdown` to the completion handler
+       *        signature of `AsyncWriteOperation`.
        *
-       * This is boilerplate to ignore the `size_t` parameter that is passed to the
-       * completion handler of `AsyncWriteOperation`.
-       *
-       * @todo in C++14 and above this could be implemented as a mutable lambda expression
-       *       that captures `handler` by perfect forwarding, like so:
-       *
-       *       [h = std::forward<Handler>(handler)] (...) mutable { return h(ec); }
+       * This is boilerplate to ignore the `size_t` parameter that is passed to the completion handler of
+       * `AsyncWriteOperation`. Note that it needs to retain the wrapped handler's executor.
        */
-      template <typename Handler>
-      class Wrapper
+      template <typename Handler, typename Executor>
+      struct Wrapper
          {
-         public:
-            Wrapper(Handler&& handler) : _handler(std::forward<Handler>(handler)) {}
-            void operator()(boost::system::error_code ec, size_t)
-               {
-               _handler(ec);
-               }
-         private:
-            Handler _handler;
+         void operator()(boost::system::error_code ec, std::size_t)
+            {
+            handler(ec);
+            }
+
+         using executor_type = boost::asio::associated_executor_t<Handler, Executor>;
+
+         executor_type get_executor() const noexcept
+            {
+            return boost::asio::get_associated_executor(handler, io_executor);
+            }
+
+         using allocator_type = boost::asio::associated_allocator_t<Handler>;
+
+         allocator_type get_allocator() const noexcept
+            {
+            return boost::asio::get_associated_allocator(handler);
+            }
+
+         Handler handler;
+         Executor io_executor;
          };
 
    public:
@@ -380,9 +388,9 @@ class Stream
          // If ec is set by native_handle->close(), the AsyncWriteOperation created below will do nothing but call the
          // handler with the error_code set appropriately - no need to early return here.
 
-         using ShutdownHandlerWrapper = Wrapper<ShutdownHandler>;
+         using ShutdownHandlerWrapper = Wrapper<ShutdownHandler, typename Stream::executor_type>;
 
-         ShutdownHandlerWrapper w(std::forward<ShutdownHandler>(handler));
+         ShutdownHandlerWrapper w{std::forward<ShutdownHandler>(handler), get_executor()};
          BOOST_ASIO_SHUTDOWN_HANDLER_CHECK(ShutdownHandler, w) type_check;
 
          boost::asio::async_completion<ShutdownHandlerWrapper, void(boost::system::error_code, std::size_t)>
diff --git a/src/lib/utils/rotate.h b/src/lib/utils/rotate.h
index 8599a2695..15c78ac26 100644
--- a/src/lib/utils/rotate.h
+++ b/src/lib/utils/rotate.h
@@ -69,20 +69,14 @@ inline T rotr_var(T input, size_t rot)
 template<>
 inline uint32_t rotl_var(uint32_t input, size_t rot)
    {
-   asm("roll %1,%0"
-       : "+r" (input)
-       : "c" (static_cast<uint8_t>(rot))
-       : "cc");
+   asm("roll %1,%0" : "+r" (input) : "c" (static_cast<uint8_t>(rot)));
    return input;
    }
 
 template<>
 inline uint32_t rotr_var(uint32_t input, size_t rot)
    {
-   asm("rorl %1,%0"
-       : "+r" (input)
-       : "c" (static_cast<uint8_t>(rot))
-       : "cc");
+   asm("rorl %1,%0" : "+r" (input) : "c" (static_cast<uint8_t>(rot)));
    return input;
    }
 


Test patch:
diff --git a/src/tests/data/bn/cmp.vec b/src/tests/data/bn/cmp.vec
deleted file mode 100644
index 935634fb0..000000000
--- a/src/tests/data/bn/cmp.vec
+++ /dev/null
@@ -1,78 +0,0 @@
-[EQ]
-X = 5
-Y = 5
-R = true
-
-X = -5
-Y = 5
-R = false
-
-X = 5
-Y = -5
-R = false
-
-X = -5
-Y = -5
-R = true
-
-X = 4
-Y = 5
-R = false
-
-X = 5
-Y = 4
-R = false
-
-[LT]
-X = 5
-Y = 5
-R = false
-
-X = -5
-Y = 5
-R = true
-
-X = 5
-Y = -5
-R = false
-
-X = -5
-Y = -5
-R = false
-
-X = -1
-Y = -3
-R = false
-
-X = -2
-Y = -1
-R = true
-
-[LTE]
-X = 5
-Y = 5
-R = true
-
-X = 5
-Y = 6
-R = true
-
-X = 6
-Y = 5
-R = false
-
-X = -5
-Y = 5
-R = true
-
-X = 5
-Y = -5
-R = false
-
-X = -1
-Y = -2
-R = false
-
-X = -2
-Y = -1
-R = true
diff --git a/src/tests/test_bigint.cpp b/src/tests/test_bigint.cpp
index 424a37cf9..8f1e4717f 100644
--- a/src/tests/test_bigint.cpp
+++ b/src/tests/test_bigint.cpp
@@ -219,50 +219,6 @@ class BigInt_Unit_Tests final : public Test
 
 BOTAN_REGISTER_TEST("math", "bigint_unit", BigInt_Unit_Tests);
 
-class BigInt_Cmp_Test final : public Text_Based_Test
-   {
-   public:
-      BigInt_Cmp_Test() : Text_Based_Test("bn/cmp.vec", "X,Y,R") {}
-
-      Test::Result run_one_test(const std::string& op, const VarMap& vars) override
-         {
-         Test::Result result("BigInt Comparison " + op);
-
-         const BigInt x = vars.get_req_bn("X");
-         const BigInt y = vars.get_req_bn("Y");
-         const bool expected = vars.get_req_bool("R");
-
-         if(op == "EQ")
-            {
-            result.confirm("Values equal", x == y, expected);
-            }
-         else if(op == "LT")
-            {
-            result.confirm("Values LT", x < y, expected);
-
-            if(expected)
-               result.confirm("If LT then reverse is GT", y >= x);
-            else
-               result.confirm("If not LT then GTE", x >= y);
-            }
-         else if(op == "LTE")
-            {
-            result.confirm("Values LTE", x <= y, expected);
-
-            if(expected)
-               result.confirm("If LTE then either LT or EQ", x < y || x == y);
-            else
-               result.confirm("If not LTE then GT", x > y);
-            }
-         else
-            throw Test_Error("Unknown BigInt comparison type " + op);
-
-         return result;
-         }
-   };
-
-BOTAN_REGISTER_TEST("math", "bn_cmp", BigInt_Cmp_Test);
-
 class BigInt_Add_Test final : public Text_Based_Test
    {
    public:
diff --git a/src/tests/test_ffi.cpp b/src/tests/test_ffi.cpp
index 90a3a0760..eef8a39d7 100644
--- a/src/tests/test_ffi.cpp
+++ b/src/tests/test_ffi.cpp
@@ -201,7 +201,6 @@ class FFI_Unit_Tests final : public Test
          botan_rng_t system_rng;
          botan_rng_t rdrand_rng = nullptr;
          botan_rng_t null_rng;
-         botan_rng_t custom_rng;
 
          TEST_FFI_FAIL("invalid rng type", botan_rng_init, (&rng, "invalid_type"));
 
@@ -248,50 +247,6 @@ class FFI_Unit_Tests final : public Test
             TEST_FFI_OK(botan_rng_add_entropy, (rng, not_really_entropy, 32));
             }
 
-         size_t cb_counter = 0;
-
-         auto custom_get_cb = [](void* context, uint8_t* out, size_t out_len) -> int
-            {
-            Botan::set_mem(out, out_len, 0x12);
-            BOTAN_UNUSED(out, out_len);
-            (*(static_cast<size_t*>(context)))++;
-            return 0;
-            };
-
-         auto custom_add_entropy_cb = [](void* context, const uint8_t input[], size_t length) -> int
-            {
-            BOTAN_UNUSED(input, length);
-            (*(static_cast<size_t*>(context)))++;
-            return 0;
-            };
-
-         auto custom_destroy_cb = [](void* context) -> void
-            {
-            (*(static_cast<size_t*>(context)))++;
-            };
-
-         if(TEST_FFI_OK(botan_rng_init_custom, (&custom_rng, "custom rng", &cb_counter, custom_get_cb, custom_add_entropy_cb, custom_destroy_cb)))
-            {
-               Botan::clear_mem(outbuf.data(), outbuf.size());
-               TEST_FFI_OK(botan_rng_get, (custom_rng, outbuf.data(), outbuf.size()));
-               result.test_eq("custom_get_cb called", cb_counter, 1);
-               std::vector<uint8_t> pattern(outbuf.size(), 0x12);
-               result.test_eq("custom_get_cb returned bytes", pattern, outbuf);
-
-               TEST_FFI_OK(botan_rng_reseed, (custom_rng, 256));
-               result.test_eq("custom_add_entropy_cb called", cb_counter, 2);
-
-               TEST_FFI_OK(botan_rng_reseed_from_rng, (custom_rng, system_rng, 256));
-               result.test_eq("custom_add_entropy_cb called", cb_counter, 3);
-
-               uint8_t not_really_entropy[32] = { 0 };
-               TEST_FFI_OK(botan_rng_add_entropy, (custom_rng, not_really_entropy, 32));
-               result.test_eq("custom_add_entropy_cb called", cb_counter, 4);
-
-               TEST_FFI_OK(botan_rng_destroy, (custom_rng));
-               result.test_eq("custom_destroy_cb called", cb_counter, 5);
-            }
-
          TEST_FFI_OK(botan_rng_destroy, (rng));
          TEST_FFI_OK(botan_rng_destroy, (null_rng));
          TEST_FFI_OK(botan_rng_destroy, (system_rng));
diff --git a/src/tests/tests.h b/src/tests/tests.h
index 05e5e5ffe..694779ac5 100644
--- a/src/tests/tests.h
+++ b/src/tests/tests.h
@@ -233,9 +233,9 @@ class Test
                test_failure(what, buf.data(), buf.size());
                }
 
-            bool confirm(const std::string& what, bool expr, bool expected = true)
+            bool confirm(const std::string& what, bool expr)
                {
-               return test_eq(what, expr, expected);
+               return test_eq(what, expr, true);
                }
 
             template<typename T>