1#include "crypto/tests/test_internal.h"
2
3TEST_GROUP_DEFINE(prng, .intensity_desc = {
4 .curve = SCALE_PIECEWISE_LOG,
5 .unit = "samples",
6 });
7
8TEST_DEFINE_UNIT(prng, same_seed_replays_sequence,
9 TEST_INTENSITY(16, 256, 65536)) {
10 size_t samples = ctx->intensity_val ? ctx->intensity_val : 256;
11 uint64_t seed_val = 0xDEADBEEFCAFEULL;
12 uint64_t *seq1 = vnews(seq1, samples, .flags = ALLOC_FLAGS_NONE);
13 TEST_ASSERT_NONNULL(seq1);
14
15 prng_seed(seed: seed_val);
16 for (size_t i = 0; i < samples; i++)
17 seq1[i] = prng_next();
18
19 prng_seed(seed: seed_val);
20 for (size_t i = 0; i < samples; i++) {
21 uint64_t val = prng_next();
22 TEST_ASSERT_EQ(seq1[i], val);
23 }
24
25 for (size_t i = 1; i < samples; i++)
26 TEST_ASSERT_NE(seq1[i], seq1[i - 1]);
27
28 vfree(seq1);
29 return TEST_SUCCESS;
30}
31
32TEST_DEFINE_UNIT(prng, splitmix64_determinism, TEST_INTENSITY(16, 256, 65536)) {
33 size_t samples = ctx->intensity_val ? ctx->intensity_val : 256;
34 uint64_t seed_val = 0x123456789ABCDEF0ULL;
35 uint64_t *seq1 = vnews(seq1, samples, .flags = ALLOC_FLAGS_NONE);
36 TEST_ASSERT_NONNULL(seq1);
37
38 uint64_t state1 = seed_val;
39 for (size_t i = 0; i < samples; i++)
40 seq1[i] = prng_splitmix64_next(state: &state1);
41
42 uint64_t state2 = seed_val;
43 for (size_t i = 0; i < samples; i++) {
44 uint64_t val = prng_splitmix64_next(state: &state2);
45 TEST_ASSERT_EQ(seq1[i], val);
46 }
47
48 for (size_t i = 1; i < samples; i++)
49 TEST_ASSERT_NE(seq1[i], seq1[i - 1]);
50
51 vfree(seq1);
52 return TEST_SUCCESS;
53}
54