rand/rdrand: add rdrand generator
This commit is contained in:
parent
3a83851e90
commit
f86989bc67
@ -440,6 +440,8 @@ list (
|
|||||||
rand/mwc64x.hpp
|
rand/mwc64x.hpp
|
||||||
rand/pcg.cpp
|
rand/pcg.cpp
|
||||||
rand/pcg.hpp
|
rand/pcg.hpp
|
||||||
|
rand/rdrand.cpp
|
||||||
|
rand/rdrand.hpp
|
||||||
rand/system.hpp
|
rand/system.hpp
|
||||||
random.cpp
|
random.cpp
|
||||||
random.hpp
|
random.hpp
|
||||||
|
44
rand/rdrand.cpp
Normal file
44
rand/rdrand.cpp
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
/*
|
||||||
|
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||||
|
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||||
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||||
|
*
|
||||||
|
* Copyright 2019 Danny Robson <danny@nerdcruft.net>
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "rdrand.hpp"
|
||||||
|
|
||||||
|
using cruft::rand::rdrand;
|
||||||
|
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
rdrand::rdrand ()
|
||||||
|
{ ; }
|
||||||
|
|
||||||
|
|
||||||
|
//---------------------------------------------------------------------------------------
|
||||||
|
rdrand::rdrand (std::string const &)
|
||||||
|
: rdrand ()
|
||||||
|
{ ; }
|
||||||
|
|
||||||
|
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
rdrand::result_type
|
||||||
|
rdrand::operator() ()
|
||||||
|
{
|
||||||
|
uint64_t res;
|
||||||
|
char success;
|
||||||
|
|
||||||
|
__asm__ __volatile__ (
|
||||||
|
"rdrand %0;"
|
||||||
|
"setc %1;"
|
||||||
|
|
||||||
|
: "=r" (res)
|
||||||
|
, "=qm" (success)
|
||||||
|
);
|
||||||
|
|
||||||
|
if (!__builtin_expect(success, 1))
|
||||||
|
throw std::runtime_error ("no value available for rdrand");
|
||||||
|
|
||||||
|
return res;
|
||||||
|
}
|
40
rand/rdrand.hpp
Normal file
40
rand/rdrand.hpp
Normal file
@ -0,0 +1,40 @@
|
|||||||
|
/*
|
||||||
|
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||||
|
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||||
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||||
|
*
|
||||||
|
* Copyright 2019 Danny Robson <danny@nerdcruft.net>
|
||||||
|
*/
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "../posix/fd.hpp"
|
||||||
|
|
||||||
|
|
||||||
|
namespace cruft::rand {
|
||||||
|
/// Models std::random_device and is suitable as a drop-in replacement.
|
||||||
|
///
|
||||||
|
/// This implementation assumes that the CPU supports the `rdrand`
|
||||||
|
/// instruction, and does not check that this is the case.
|
||||||
|
///
|
||||||
|
/// It is safe to instantiatate the object even if the instructions are
|
||||||
|
/// not supported, but it is the users responsibility to prevent calls to
|
||||||
|
/// the object if this is not the case.
|
||||||
|
class rdrand {
|
||||||
|
public:
|
||||||
|
using result_type = unsigned;
|
||||||
|
|
||||||
|
rdrand ();
|
||||||
|
rdrand (std::string const&);
|
||||||
|
rdrand (rdrand const &) = delete;
|
||||||
|
|
||||||
|
rdrand& operator= (rdrand const&) = delete;
|
||||||
|
|
||||||
|
result_type operator() (void);
|
||||||
|
|
||||||
|
double entropy (void) const noexcept;
|
||||||
|
|
||||||
|
static constexpr result_type min (void) { return std::numeric_limits<result_type>::min (); }
|
||||||
|
static constexpr result_type max (void) { return std::numeric_limits<result_type>::max (); }
|
||||||
|
};
|
||||||
|
}
|
@ -55,6 +55,7 @@ main (int,char**)
|
|||||||
test_buckets<cruft::rand::mwc64x> (tap, 0x1234u);
|
test_buckets<cruft::rand::mwc64x> (tap, 0x1234u);
|
||||||
test_buckets<cruft::rand::pcg_xsh_rr<>> (tap, 0x1234u);
|
test_buckets<cruft::rand::pcg_xsh_rr<>> (tap, 0x1234u);
|
||||||
test_buckets<cruft::rand::system> (tap);
|
test_buckets<cruft::rand::system> (tap);
|
||||||
|
test_buckets<cruft::rand::rdrand> (tap);
|
||||||
|
|
||||||
return tap.status ();
|
return tap.status ();
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user