Lazy-link to bcrypt

Let's not make `bcrypt.dl` a link-time bound library. Instead, load the
`BCryptGenRandom()` function dynamically. When needed. If needed.

This helps reduce the start-up cost of any mimalloc user because the
time spent on loading dynamic libraries is non-negligible.

Note: In contrast to how `os.c` loads libraries and obtains function
addresses, we cannot call `FreeLibrary(hDll)` here because that would
unload the `bcrypt` library before we want to use it.

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
This commit is contained in:
Johannes Schindelin 2022-08-12 13:49:22 +02:00
parent 948a0c44df
commit edb181c377

View File

@ -187,10 +187,27 @@ static bool os_random_buf(void* buf, size_t buf_len) {
return (RtlGenRandom(buf, (ULONG)buf_len) != 0);
}
#else
#pragma comment (lib,"bcrypt.lib")
#include <bcrypt.h>
#ifndef BCRYPT_USE_SYSTEM_PREFERRED_RNG
#define BCRYPT_USE_SYSTEM_PREFERRED_RNG 0x00000002
#endif
typedef LONG (NTAPI *PBCryptGenRandom)(HANDLE, PUCHAR, ULONG, ULONG);
static PBCryptGenRandom pBCryptGenRandom = NULL;
static int BCryptGenRandom_is_initialized = 0;
static bool os_random_buf(void* buf, size_t buf_len) {
return (BCryptGenRandom(NULL, (PUCHAR)buf, (ULONG)buf_len, BCRYPT_USE_SYSTEM_PREFERRED_RNG) >= 0);
if (!BCryptGenRandom_is_initialized) {
HINSTANCE hDll;
hDll = LoadLibrary(TEXT("bcrypt.dll"));
if (hDll != NULL) {
pBCryptGenRandom = (PBCryptGenRandom)(void (*)(void))GetProcAddress(hDll, "BCryptGenRandom");
}
BCryptGenRandom_is_initialized = 1;
}
if (!pBCryptGenRandom)
return 0;
return (pBCryptGenRandom(NULL, (PUCHAR)buf, (ULONG)buf_len, BCRYPT_USE_SYSTEM_PREFERRED_RNG) >= 0);
}
#endif