Provide getentropy() in the Windows OS shim using BCryptGenRandom() with the system preferred generator, which needs no algorithm provider handle. The POSIX 256 byte limit is kept so that callers see the same behaviour on all platforms.
This is needed EAL change that always uses getentropy(). The next patch is tagged for stable, and it does not build on Windows without this shim, so this one is tagged as well. Bugzilla ID: 2035 Cc: [email protected] Signed-off-by: Stephen Hemminger <[email protected]> --- lib/eal/common/rte_random.c | 1 + lib/eal/windows/include/rte_os_shim.h | 30 +++++++++++++++++++++++++++ lib/eal/windows/meson.build | 6 +++++- 3 files changed, 36 insertions(+), 1 deletion(-) diff --git a/lib/eal/common/rte_random.c b/lib/eal/common/rte_random.c index 576a32a46c..537fa035ee 100644 --- a/lib/eal/common/rte_random.c +++ b/lib/eal/common/rte_random.c @@ -17,6 +17,7 @@ #include <rte_random.h> #include <eal_export.h> +#include <rte_os_shim.h> #include "eal_private.h" struct __rte_cache_aligned rte_rand_state { diff --git a/lib/eal/windows/include/rte_os_shim.h b/lib/eal/windows/include/rte_os_shim.h index 44664a5062..4f9611d642 100644 --- a/lib/eal/windows/include/rte_os_shim.h +++ b/lib/eal/windows/include/rte_os_shim.h @@ -3,12 +3,16 @@ #ifndef _RTE_OS_SHIM_ #define _RTE_OS_SHIM_ +#include <errno.h> #include <time.h> #include <rte_os.h> #include <rte_windows.h> #include <getline.h> +/* Needs Windows SDK types, so must come after rte_windows.h. */ +#include <bcrypt.h> + /** * @file * @internal @@ -124,4 +128,30 @@ rte_localtime_r(const time_t *timep, struct tm *result) } #define localtime_r(timep, result) rte_localtime_r(timep, result) +/* + * Windows has no getentropy(), use the system preferred random + * generator which does not require a provider handle. + */ +static inline int +rte_getentropy(void *buffer, size_t length) +{ + NTSTATUS status; + + /* Match the POSIX limit so callers behave the same everywhere. */ + if (length > 256) { + errno = EIO; + return -1; + } + + status = BCryptGenRandom(NULL, (PUCHAR)buffer, (ULONG)length, + BCRYPT_USE_SYSTEM_PREFERRED_RNG); + if (!BCRYPT_SUCCESS(status)) { + errno = EIO; + return -1; + } + + return 0; +} +#define getentropy(buffer, length) rte_getentropy(buffer, length) + #endif /* _RTE_OS_SHIM_ */ diff --git a/lib/eal/windows/meson.build b/lib/eal/windows/meson.build index 6f909c2131..6387786530 100644 --- a/lib/eal/windows/meson.build +++ b/lib/eal/windows/meson.build @@ -37,7 +37,11 @@ ws2_32_dep = cc.find_library('ws2_32') if not cc.links(min_c_code, dependencies: ws2_32_dep) error('broken dependency, "ws2_32"') endif -ext_deps += [dbghelp_dep, setupapi_dep, ws2_32_dep] +bcrypt_dep = cc.find_library('bcrypt') +if not cc.links(min_c_code, dependencies: bcrypt_dep) + error('broken dependency, "bcrypt"') +endif +ext_deps += [dbghelp_dep, setupapi_dep, ws2_32_dep, bcrypt_dep] if is_ms_linker # Contrary to docs, VirtualAlloc2() is exported by mincore.lib. mincore_dep = cc.find_library('mincore') -- 2.53.0

