summaryrefslogtreecommitdiff
path: root/Source/Core
diff options
context:
space:
mode:
authorJosJuice <josjuice@gmail.com>2021-02-08 10:58:09 +0100
committerGitHub <noreply@github.com>2021-02-08 10:58:09 +0100
commit3e4bf57c696ed1e4f465075ae311653de2cd33b0 (patch)
treef83f232833cf78b1bcb737c6d201b124c832eac0 /Source/Core
parent9a2d908aba78e83d600c90349b6ca334707cbc51 (diff)
parent1ab7657120cbd9552f89660e23b2d618cc03c4c7 (diff)
Merge pull request #9423 from MerryMage/arm64-movi2r-test
UnitTests: Add MOVI2R test
Diffstat (limited to 'Source/Core')
-rw-r--r--Source/Core/Common/Random.cpp42
-rw-r--r--Source/Core/Common/Random.h25
2 files changed, 62 insertions, 5 deletions
diff --git a/Source/Core/Common/Random.cpp b/Source/Core/Common/Random.cpp
index c512e7695d..754cea397f 100644
--- a/Source/Core/Common/Random.cpp
+++ b/Source/Core/Common/Random.cpp
@@ -11,10 +11,42 @@
namespace Common::Random
{
-class CSPRNG final
+struct PRNG::Impl
+{
+ Impl(void* seed, std::size_t size)
+ {
+ mbedtls_hmac_drbg_init(&m_context);
+ const int ret = mbedtls_hmac_drbg_seed_buf(
+ &m_context, mbedtls_md_info_from_type(MBEDTLS_MD_SHA256), static_cast<u8*>(seed), size);
+ ASSERT(ret == 0);
+ }
+
+ ~Impl() { mbedtls_hmac_drbg_free(&m_context); }
+
+ void Generate(void* buffer, std::size_t size)
+ {
+ const int ret = mbedtls_hmac_drbg_random(&m_context, static_cast<u8*>(buffer), size);
+ ASSERT(ret == 0);
+ }
+
+ mbedtls_hmac_drbg_context m_context;
+};
+
+PRNG::PRNG(void* seed, std::size_t size) : m_impl(std::make_unique<Impl>(seed, size))
+{
+}
+
+PRNG::~PRNG() = default;
+
+void PRNG::Generate(void* buffer, std::size_t size)
+{
+ m_impl->Generate(buffer, size);
+}
+
+class EntropySeededPRNG final
{
public:
- CSPRNG()
+ EntropySeededPRNG()
{
mbedtls_entropy_init(&m_entropy);
mbedtls_hmac_drbg_init(&m_context);
@@ -23,7 +55,7 @@ public:
ASSERT(ret == 0);
}
- ~CSPRNG()
+ ~EntropySeededPRNG()
{
mbedtls_hmac_drbg_free(&m_context);
mbedtls_entropy_free(&m_entropy);
@@ -40,10 +72,10 @@ private:
mbedtls_hmac_drbg_context m_context;
};
-static thread_local CSPRNG s_csprng;
+static thread_local EntropySeededPRNG s_esprng;
void Generate(void* buffer, std::size_t size)
{
- s_csprng.Generate(buffer, size);
+ s_esprng.Generate(buffer, size);
}
} // namespace Common::Random
diff --git a/Source/Core/Common/Random.h b/Source/Core/Common/Random.h
index 1f234f8ac3..789f62d9c1 100644
--- a/Source/Core/Common/Random.h
+++ b/Source/Core/Common/Random.h
@@ -5,12 +5,37 @@
#pragma once
#include <cstddef>
+#include <memory>
#include <type_traits>
#include "Common/CommonTypes.h"
namespace Common::Random
{
+/// Cryptographically secure pseudo-random number generator, with explicit seed.
+class PRNG final
+{
+public:
+ explicit PRNG(u64 seed) : PRNG(&seed, sizeof(u64)) {}
+ PRNG(void* seed, std::size_t size);
+ ~PRNG();
+
+ void Generate(void* buffer, std::size_t size);
+
+ template <typename T>
+ T GenerateValue()
+ {
+ static_assert(std::is_arithmetic<T>(), "T must be an arithmetic type in GenerateValue.");
+ T value;
+ Generate(&value, sizeof(value));
+ return value;
+ }
+
+private:
+ struct Impl;
+ std::unique_ptr<Impl> m_impl;
+};
+
/// Fill `buffer` with random bytes using a cryptographically secure pseudo-random number generator.
void Generate(void* buffer, std::size_t size);