diff --git a/src/backend/postmaster/fork_process.c b/src/backend/postmaster/fork_process.c index 15d6340800..5247b9f23c 100644 --- a/src/backend/postmaster/fork_process.c +++ b/src/backend/postmaster/fork_process.c @@ -16,9 +16,6 @@ #include #include #include -#ifdef USE_OPENSSL -#include -#endif #include "postmaster/fork_process.h" @@ -108,14 +105,8 @@ fork_process(void) } } - /* - * 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. - */ -#ifdef USE_OPENSSL - RAND_poll(); -#endif + /* do post-fork initialization for random number generation */ + pg_strong_random_init(); } return result; diff --git a/src/include/port.h b/src/include/port.h index d25716bf7f..5dfb00b07c 100644 --- a/src/include/port.h +++ b/src/include/port.h @@ -513,6 +513,7 @@ extern char *pg_inet_net_ntop(int af, const void *src, int bits, char *dst, size_t size); /* port/pg_strong_random.c */ +extern void pg_strong_random_init(void); extern bool pg_strong_random(void *buf, size_t len); /* diff --git a/src/port/pg_strong_random.c b/src/port/pg_strong_random.c index 14e8382cd8..6d85f50b7c 100644 --- a/src/port/pg_strong_random.c +++ b/src/port/pg_strong_random.c @@ -24,7 +24,7 @@ #include #include -#ifdef USE_OPENSSL +#ifdef USE_OPENSSL_RANDOM #include #endif #ifdef USE_WIN32_RANDOM @@ -75,6 +75,50 @@ random_from_file(const char *filename, void *buf, size_t len) } #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 *