8 #include <botan/internal/dev_random.h>
9 #include <botan/exceptn.h>
11 #include <sys/types.h>
12 #include <sys/select.h>
37 for(
auto fsname : fsnames)
39 int fd = ::open(fsname.c_str(),
flags);
48 if(errno != ENOENT && errno != EACCES)
49 throw Exception(
"Opening OS RNG device failed with errno " +
57 throw Exception(
"Open of OS RNG succeeded but fd is too large for fd_set");
60 m_dev_fds.push_back(fd);
71 for(
int fd : m_dev_fds)
85 if(m_dev_fds.size() > 0)
90 for(
int dev_fd : m_dev_fds)
92 FD_SET(dev_fd, &read_set);
97 struct ::timeval timeout;
98 timeout.tv_sec = (BOTAN_SYSTEM_RNG_POLL_TIMEOUT_MS / 1000);
99 timeout.tv_usec = (BOTAN_SYSTEM_RNG_POLL_TIMEOUT_MS % 1000) * 1000;
101 if(::
select(m_max_fd + 1, &read_set,
nullptr,
nullptr, &timeout) > 0)
103 for(
int dev_fd : m_dev_fds)
105 if(FD_ISSET(dev_fd, &read_set))
107 const ssize_t got = ::read(dev_fd, io_buf.data(), io_buf.size());
111 rng.
add_entropy(io_buf.data(),
static_cast<size_t>(got));
Device_EntropySource(const std::vector< std::string > &fsnames)
virtual void add_entropy(const uint8_t input[], size_t length)=0
std::string to_string(const BER_Object &obj)
std::vector< T, secure_allocator< T >> secure_vector
T select(T mask, T from0, T from1)
size_t poll(RandomNumberGenerator &rng) override