aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/include/pg_config.h.in9
-rw-r--r--src/port/pg_strong_random.c201
-rw-r--r--src/tools/msvc/Solution.pm3
3 files changed, 83 insertions, 130 deletions
diff --git a/src/include/pg_config.h.in b/src/include/pg_config.h.in
index fb270df678a..de8f838e536 100644
--- a/src/include/pg_config.h.in
+++ b/src/include/pg_config.h.in
@@ -862,9 +862,6 @@
/* Define to 1 to build with BSD Authentication support. (--with-bsd-auth) */
#undef USE_BSD_AUTH
-/* Define to use /dev/urandom for random number generation */
-#undef USE_DEV_URANDOM
-
/* Define to build with ICU support. (--with-icu) */
#undef USE_ICU
@@ -887,9 +884,6 @@
/* Define to build with OpenSSL support. (--with-openssl) */
#undef USE_OPENSSL
-/* Define to use OpenSSL for random number generation */
-#undef USE_OPENSSL_RANDOM
-
/* Define to 1 to build with PAM support. (--with-pam) */
#undef USE_PAM
@@ -914,9 +908,6 @@
/* Define to select unnamed POSIX semaphores. */
#undef USE_UNNAMED_POSIX_SEMAPHORES
-/* Define to use native Windows API for random number generation */
-#undef USE_WIN32_RANDOM
-
/* Define to select Win32-style semaphores. */
#undef USE_WIN32_SEMAPHORES
diff --git a/src/port/pg_strong_random.c b/src/port/pg_strong_random.c
index 6d85f50b7c8..12bbd7fb08b 100644
--- a/src/port/pg_strong_random.c
+++ b/src/port/pg_strong_random.c
@@ -24,107 +24,15 @@
#include <unistd.h>
#include <sys/time.h>
-#ifdef USE_OPENSSL_RANDOM
-#include <openssl/rand.h>
-#endif
-#ifdef USE_WIN32_RANDOM
-#include <wincrypt.h>
-#endif
-
-#ifdef USE_WIN32_RANDOM
-/*
- * Cache a global crypto provider that only gets freed when the process
- * exits, in case we need random numbers more than once.
- */
-static HCRYPTPROV hProvider = 0;
-#endif
-
-#if defined(USE_DEV_URANDOM)
-/*
- * Read (random) bytes from a file.
- */
-static bool
-random_from_file(const char *filename, void *buf, size_t len)
-{
- int f;
- char *p = buf;
- ssize_t res;
-
- f = open(filename, O_RDONLY, 0);
- if (f == -1)
- return false;
-
- while (len)
- {
- res = read(f, p, len);
- if (res <= 0)
- {
- if (errno == EINTR)
- continue; /* interrupted by signal, just retry */
-
- close(f);
- return false;
- }
-
- p += res;
- len -= res;
- }
-
- close(f);
- return true;
-}
-#endif
-
/*
- * pg_strong_random_init
- *
- * Initialize the randomness state of "strong" random numbers. This is invoked
- * *after* forking a process, and should include initialization steps specific
- * to the chosen random source to prove fork-safety.
- */
-void
-pg_strong_random_init(void)
-{
-#if defined(USE_OPENSSL)
- /*
- * Make sure processes do not share OpenSSL randomness state. We need to
- * call this even if pg_strong_random is implemented using another source
- * for random numbers to ensure fork-safety in our TLS backend. This is no
- * longer required in OpenSSL 1.1.1 and later versions, but until we drop
- * support for version < 1.1.1 we need to do this.
- */
- RAND_poll();
-#endif
-
-#if defined(USE_OPENSSL_RANDOM)
- /*
- * In case the backend is using the PRNG from OpenSSL without being built
- * with support for OpenSSL, make sure to perform post-fork initialization.
- * If the backend is using OpenSSL then we have already performed this
- * step. The same version caveat as discussed in the comment above applies
- * here as well.
- */
-#ifndef USE_OPENSSL
- RAND_poll();
-#endif
-
-#elif defined(USE_WIN32_RANDOM)
- /* no initialization needed for WIN32 */
-
-#elif defined(USE_DEV_URANDOM)
- /* no initialization needed for /dev/urandom */
-
-#else
-#error no source of random numbers configured
-#endif
-}
-
-/*
- * pg_strong_random
+ * pg_strong_random & pg_strong_random_init
*
* Generate requested number of random bytes. The returned bytes are
* cryptographically secure, suitable for use e.g. in authentication.
*
+ * Before pg_strong_random is called in any process, the generator must first
+ * be initialized by calling pg_strong_random_init().
+ *
* We rely on system facilities for actually generating the numbers.
* We support a number of sources:
*
@@ -132,21 +40,32 @@ pg_strong_random_init(void)
* 2. Windows' CryptGenRandom() function
* 3. /dev/urandom
*
- * The configure script will choose which one to use, and set
- * a USE_*_RANDOM flag accordingly.
- *
* Returns true on success, and false if none of the sources
* were available. NB: It is important to check the return value!
* Proceeding with key generation when no random data was available
* would lead to predictable keys and security issues.
*/
-bool
-pg_strong_random(void *buf, size_t len)
+
+
+
+#ifdef USE_OPENSSL
+
+#include <openssl/rand.h>
+
+void
+pg_strong_random_init(void)
{
/*
- * When built with OpenSSL, use OpenSSL's RAND_bytes function.
+ * Make sure processes do not share OpenSSL randomness state. This is no
+ * longer required in OpenSSL 1.1.1 and later versions, but until we drop
+ * support for version < 1.1.1 we need to do this.
*/
-#if defined(USE_OPENSSL_RANDOM)
+ RAND_poll();
+}
+
+bool
+pg_strong_random(void *buf, size_t len)
+{
int i;
/*
@@ -174,11 +93,26 @@ pg_strong_random(void *buf, size_t len)
if (RAND_bytes(buf, len) == 1)
return true;
return false;
+}
- /*
- * Windows has CryptoAPI for strong cryptographic numbers.
- */
-#elif defined(USE_WIN32_RANDOM)
+#elif WIN32
+
+#include <wincrypt.h>
+/*
+ * Cache a global crypto provider that only gets freed when the process
+ * exits, in case we need random numbers more than once.
+ */
+static HCRYPTPROV hProvider = 0;
+
+void
+pg_strong_random_init(void)
+{
+ /* No initialization needed on WIN32 */
+}
+
+bool
+pg_strong_random(void *buf, size_t len)
+{
if (hProvider == 0)
{
if (!CryptAcquireContext(&hProvider,
@@ -201,17 +135,48 @@ pg_strong_random(void *buf, size_t len)
return true;
}
return false;
+}
- /*
- * Read /dev/urandom ourselves.
- */
-#elif defined(USE_DEV_URANDOM)
- if (random_from_file("/dev/urandom", buf, len))
- return true;
- return false;
+#else /* not USE_OPENSSL or WIN32 */
-#else
- /* The autoconf script should not have allowed this */
-#error no source of random numbers configured
-#endif
+/*
+ * Without OpenSSL or Win32 support, just read /dev/urandom ourselves.
+ */
+
+void
+pg_strong_random_init(void)
+{
+ /* No initialization needed */
+}
+
+bool
+pg_strong_random(void *buf, size_t len)
+{
+ int f;
+ char *p = buf;
+ ssize_t res;
+
+ f = open("/dev/urandom", O_RDONLY, 0);
+ if (f == -1)
+ return false;
+
+ while (len)
+ {
+ res = read(f, p, len);
+ if (res <= 0)
+ {
+ if (errno == EINTR)
+ continue; /* interrupted by signal, just retry */
+
+ close(f);
+ return false;
+ }
+
+ p += res;
+ len -= res;
+ }
+
+ close(f);
+ return true;
}
+#endif
diff --git a/src/tools/msvc/Solution.pm b/src/tools/msvc/Solution.pm
index 17e480546cf..22d6abd3674 100644
--- a/src/tools/msvc/Solution.pm
+++ b/src/tools/msvc/Solution.pm
@@ -475,7 +475,6 @@ sub GenerateFiles
USE_ASSERT_CHECKING => $self->{options}->{asserts} ? 1 : undef,
USE_BONJOUR => undef,
USE_BSD_AUTH => undef,
- USE_DEV_URANDOM => undef,
USE_ICU => $self->{options}->{icu} ? 1 : undef,
USE_LIBXML => undef,
USE_LIBXSLT => undef,
@@ -483,7 +482,6 @@ sub GenerateFiles
USE_LLVM => undef,
USE_NAMED_POSIX_SEMAPHORES => undef,
USE_OPENSSL => undef,
- USE_OPENSSL_RANDOM => undef,
USE_PAM => undef,
USE_SLICING_BY_8_CRC32C => undef,
USE_SSE42_CRC32C => undef,
@@ -492,7 +490,6 @@ sub GenerateFiles
USE_SYSV_SEMAPHORES => undef,
USE_SYSV_SHARED_MEMORY => undef,
USE_UNNAMED_POSIX_SEMAPHORES => undef,
- USE_WIN32_RANDOM => 1,
USE_WIN32_SEMAPHORES => 1,
USE_WIN32_SHARED_MEMORY => 1,
WCSTOMBS_L_IN_XLOCALE => undef,