• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

randombit / botan / 13190843806

07 Feb 2025 12:50AM UTC coverage: 91.233% (+0.006%) from 91.227%
13190843806

push

github

web-flow
Merge pull request #4639 from randombit/jack/cleanup-build-h

Remove most toggles from build.h

94196 of 103248 relevant lines covered (91.23%)

11436231.99 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

96.72
/src/lib/entropy/entropy_srcs.cpp
1
/*
2
* Entropy Source Polling
3
* (C) 2008-2010,2015 Jack Lloyd
4
*
5
* Botan is released under the Simplified BSD License (see license.txt)
6
*/
7

8
#include <botan/entropy_src.h>
9

10
#include <botan/rng.h>
11

12
#if defined(BOTAN_HAS_SYSTEM_RNG)
13
   #include <botan/system_rng.h>
14
#endif
15

16
#if defined(BOTAN_HAS_PROCESSOR_RNG)
17
   #include <botan/processor_rng.h>
18
#endif
19

20
#if defined(BOTAN_HAS_ENTROPY_SRC_RDSEED)
21
   #include <botan/internal/rdseed.h>
22
#endif
23

24
#if defined(BOTAN_HAS_ENTROPY_SRC_WIN32)
25
   #include <botan/internal/es_win32.h>
26
#endif
27

28
#if defined(BOTAN_HAS_ENTROPY_SRC_GETENTROPY)
29
   #include <botan/internal/getentropy.h>
30
#endif
31

32
#if defined(BOTAN_HAS_JITTER_RNG)
33
   #include <botan/jitter_rng.h>
34
#endif
35

36
namespace Botan {
37

38
namespace {
39

40
#if defined(BOTAN_HAS_SYSTEM_RNG)
41

42
class System_RNG_EntropySource final : public Entropy_Source {
3✔
43
   public:
44
      size_t poll(RandomNumberGenerator& rng) override {
4✔
45
         const size_t poll_bits = RandomNumberGenerator::DefaultPollBits;
4✔
46
         rng.reseed_from_rng(system_rng(), poll_bits);
4✔
47
         return poll_bits;
4✔
48
      }
49

50
      std::string name() const override { return "system_rng"; }
6✔
51
};
52

53
#endif
54

55
#if defined(BOTAN_HAS_PROCESSOR_RNG)
56

57
class Processor_RNG_EntropySource final : public Entropy_Source {
3✔
58
   public:
59
      size_t poll(RandomNumberGenerator& rng) override {
5✔
60
         /*
61
         * Intel's documentation for RDRAND at
62
         * https://software.intel.com/en-us/articles/intel-digital-random-number-generator-drng-software-implementation-guide
63
         * claims that software can guarantee a reseed event by polling enough data:
64
         * "There is an upper bound of 511 samples per seed in the implementation
65
         * where samples are 128 bits in size and can provide two 64-bit random
66
         * numbers each."
67
         *
68
         * By requesting 65536 bits we are asking for 512 samples and thus are assured
69
         * that at some point in producing the output, at least one reseed of the
70
         * internal state will occur.
71
         *
72
         * The reseeding conditions of the POWER and ARM processor RNGs are not known
73
         * but probably work in a somewhat similar manner. The exact amount requested
74
         * may be tweaked if and when such conditions become publically known.
75
         */
76
         const size_t poll_bits = 65536;
5✔
77
         rng.reseed_from_rng(m_hwrng, poll_bits);
5✔
78
         // Avoid trusting a black box, don't count this as contributing entropy:
79
         return 0;
5✔
80
      }
81

82
      std::string name() const override { return m_hwrng.name(); }
14✔
83

84
   private:
85
      Processor_RNG m_hwrng;
86
};
87

88
#endif
89

90
#if defined(BOTAN_HAS_JITTER_RNG)
91

92
class Jitter_RNG_EntropySource final : public Entropy_Source {
1✔
93
   public:
94
      size_t poll(RandomNumberGenerator& rng) override {
1✔
95
         rng.reseed_from_rng(m_rng);
1✔
96
         return RandomNumberGenerator::DefaultPollBits;
1✔
97
      }
98

99
      std::string name() const override { return m_rng.name(); }
×
100

101
   private:
102
      Jitter_RNG m_rng;
103
};
104

105
#endif
106

107
}  // namespace
108

109
std::unique_ptr<Entropy_Source> Entropy_Source::create(std::string_view name) {
16✔
110
#if defined(BOTAN_HAS_SYSTEM_RNG)
111
   if(name == "system_rng") {
16✔
112
      return std::make_unique<System_RNG_EntropySource>();
3✔
113
   }
114
#endif
115

116
#if defined(BOTAN_HAS_PROCESSOR_RNG)
117
   if(name == "hwrng") {
13✔
118
      if(Processor_RNG::available()) {
3✔
119
         return std::make_unique<Processor_RNG_EntropySource>();
3✔
120
      }
121
   }
122
#endif
123

124
#if defined(BOTAN_HAS_ENTROPY_SRC_RDSEED)
125
   if(name == "rdseed") {
10✔
126
      return std::make_unique<Intel_Rdseed>();
3✔
127
   }
128
#endif
129

130
#if defined(BOTAN_HAS_ENTROPY_SRC_GETENTROPY)
131
   if(name == "getentropy") {
7✔
132
      return std::make_unique<Getentropy>();
3✔
133
   }
134
#endif
135

136
#if defined(BOTAN_HAS_ENTROPY_SRC_WIN32)
137
   if(name == "system_stats") {
138
      return std::make_unique<Win32_EntropySource>();
139
   }
140
#endif
141

142
#if defined(BOTAN_HAS_JITTER_RNG)
143
   if(name == "jitter_rng") {
4✔
144
      return std::make_unique<Jitter_RNG_EntropySource>();
1✔
145
   }
146
#endif
147

148
   BOTAN_UNUSED(name);
3✔
149
   return nullptr;
3✔
150
}
151

152
void Entropy_Sources::add_source(std::unique_ptr<Entropy_Source> src) {
22✔
153
   if(src) {
22✔
154
      m_srcs.push_back(std::move(src));
19✔
155
   }
156
}
22✔
157

158
std::vector<std::string> Entropy_Sources::enabled_sources() const {
2✔
159
   std::vector<std::string> sources;
2✔
160
   sources.reserve(m_srcs.size());
2✔
161
   for(const auto& src : m_srcs) {
10✔
162
      sources.push_back(src->name());
16✔
163
   }
164
   return sources;
2✔
165
}
×
166

167
size_t Entropy_Sources::poll(RandomNumberGenerator& rng, size_t poll_bits, std::chrono::milliseconds timeout) {
10✔
168
#if defined(BOTAN_TARGET_OS_HAS_SYSTEM_CLOCK)
169
   typedef std::chrono::system_clock clock;
10✔
170
   auto timeout_expired = [to = clock::now() + timeout] { return clock::now() > to; };
14✔
171
#else
172
   auto timeout_expired = [] { return false; };
173
#endif
174

175
   size_t bits_collected = 0;
10✔
176

177
   for(auto& src : m_srcs) {
14✔
178
      bits_collected += src->poll(rng);
10✔
179

180
      if(bits_collected >= poll_bits || timeout_expired()) {
10✔
181
         break;
182
      }
183
   }
184

185
   return bits_collected;
6✔
186
}
187

188
size_t Entropy_Sources::poll_just(RandomNumberGenerator& rng, std::string_view the_src) {
16✔
189
   for(auto& src : m_srcs) {
40✔
190
      if(src->name() == the_src) {
80✔
191
         return src->poll(rng);
16✔
192
      }
193
   }
194

195
   return 0;
196
}
197

198
Entropy_Sources::Entropy_Sources(const std::vector<std::string>& sources) {
3✔
199
   for(auto&& src_name : sources) {
18✔
200
      add_source(Entropy_Source::create(src_name));
30✔
201
   }
202
}
3✔
203

204
Entropy_Sources& Entropy_Sources::global_sources() {
8✔
205
   static Entropy_Sources global_entropy_sources({"rdseed", "hwrng", "getentropy", "system_rng", "system_stats"});
8✔
206

207
   return global_entropy_sources;
8✔
208
}
209

210
}  // namespace Botan
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc