aboutsummaryrefslogtreecommitdiffstats
path: root/src/lib/entropy/entropy_srcs.cpp
blob: d57160c88060dc36b9c430cb7187de04041f6c35 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
/*
* Entropy Source Polling
* (C) 2008-2010,2015 Jack Lloyd
*
* Botan is released under the Simplified BSD License (see license.txt)
*/

#include <botan/entropy_src.h>

#if defined(BOTAN_HAS_ENTROPY_SRC_HIGH_RESOLUTION_TIMER)
  #include <botan/internal/hres_timer.h>
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_RDRAND)
  #include <botan/internal/rdrand.h>
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_DEV_RANDOM)
  #include <botan/internal/dev_random.h>
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_EGD)
  #include <botan/internal/es_egd.h>
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_UNIX_PROCESS_RUNNER)
  #include <botan/internal/unix_procs.h>
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_BEOS)
  #include <botan/internal/es_beos.h>
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_CAPI)
  #include <botan/internal/es_capi.h>
#endif

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

#if defined(BOTAN_HAS_ENTROPY_SRC_PROC_WALKER)
  #include <botan/internal/proc_walk.h>
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_DARWIN_SECRANDOM)
  #include <botan/internal/darwin_secrandom.h>
#endif

namespace Botan {

namespace {

std::vector<std::unique_ptr<EntropySource>> get_default_entropy_sources()
   {
   std::vector<std::unique_ptr<EntropySource>> sources;

#if defined(BOTAN_HAS_ENTROPY_SRC_HIGH_RESOLUTION_TIMER)
   sources.push_back(std::unique_ptr<EntropySource>(new High_Resolution_Timestamp));
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_RDRAND)
   sources.push_back(std::unique_ptr<EntropySource>(new Intel_Rdrand));
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_UNIX_PROCESS_RUNNER)
   sources.push_back(std::unique_ptr<EntropySource>(new UnixProcessInfo_EntropySource));
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_DEV_RANDOM)
   sources.push_back(std::unique_ptr<EntropySource>(new Device_EntropySource(
      { "/dev/random", "/dev/srandom", "/dev/urandom" }
   )));
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_CAPI)
   sources.push_back(std::unique_ptr<EntropySource>(new Win32_CAPI_EntropySource));
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_PROC_WALKER)
   sources.push_back(std::unique_ptr<EntropySource>(new ProcWalking_EntropySource("/proc")));
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_WIN32)
   sources.push_back(std::unique_ptr<EntropySource>(new Win32_EntropySource));
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_BEOS)
   sources.push_back(std::unique_ptr<EntropySource>(new BeOS_EntropySource));
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_UNIX_PROCESS_RUNNER)
   sources.push_back(std::unique_ptr<EntropySource>(new Unix_EntropySource(
         { "/bin", "/sbin", "/usr/bin", "/usr/sbin" }
      )));
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_EGD)
   sources.push_back(std::unique_ptr<EntropySource>(
      new EGD_EntropySource({ "/var/run/egd-pool", "/dev/egd-pool" })
      ));
#endif

#if defined(BOTAN_HAS_ENTROPY_SRC_DARWIN_SECRANDOM)
   sources.push_back(std::unique_ptr<EntropySource>(new Darwin_SecRandom));
#endif

   return sources;
   }

}

//static
void EntropySource::poll_available_sources(class Entropy_Accumulator& accum)
   {
   static std::vector<std::unique_ptr<EntropySource>> g_sources(get_default_entropy_sources());

   if(g_sources.empty())
      throw std::runtime_error("No entropy sources enabled at build time, RNG poll failed");

   size_t poll_attempt = 0;

   while(!accum.polling_finished() && poll_attempt < 16)
      {
      const size_t src_idx = poll_attempt % g_sources.size();
      g_sources[src_idx]->poll(accum);
      ++poll_attempt;
      }
   }

}