@@ -1790,6 +1790,27 @@ version (linux)
17901790 }
17911791}
17921792
1793+ version (Windows )
1794+ {
1795+ pragma (lib, " Bcrypt.lib" );
1796+
1797+ private bool bcryptGenRandom (T)(out T result) @trusted
1798+ {
1799+ import core.sys.windows.windef : PUCHAR , ULONG ;
1800+ import core.sys.windows.ntdef : NTSTATUS , NT_SUCCESS ;
1801+ import core.sys.windows.bcrypt : BCryptGenRandom, BCRYPT_USE_SYSTEM_PREFERRED_RNG ;
1802+
1803+ const gotRandom = BCryptGenRandom(
1804+ null ,
1805+ cast (PUCHAR ) &result,
1806+ ULONG (T.sizeof),
1807+ BCRYPT_USE_SYSTEM_PREFERRED_RNG ,
1808+ );
1809+
1810+ return NT_SUCCESS (gotRandom);
1811+ }
1812+ }
1813+
17931814/**
17941815A "good" seed for initializing random number engines. Initializing
17951816with $(D_PARAM unpredictableSeed) makes engines generate different
@@ -1798,8 +1819,8 @@ random number sequences every run.
17981819This function utilizes the system $(I cryptographically-secure pseudo-random
17991820number generator (CSPRNG)) or $(I pseudo-random number generator (PRNG))
18001821where available and implemented (currently `arc4random` on applicable BSD
1801- systems or `getrandom` on Linux) to generate “high quality” pseudo-random
1802- numbers – if possible.
1822+ systems, `getrandom` on Linux or `BCryptGenRandom` on Windows) to generate
1823+ “high quality” pseudo-random numbers – if possible.
18031824As a consequence, calling it may block under certain circumstances (typically
18041825during early boot when the system's entropy pool has not yet been
18051826initialized).
@@ -1848,6 +1869,18 @@ how excellent the source of entropy is.
18481869
18491870 return buffer;
18501871 }
1872+ else version (Windows )
1873+ {
1874+ uint result;
1875+ if (! bcryptGenRandom! uint (result))
1876+ {
1877+ version (none )
1878+ return fallbackSeed ();
1879+ else
1880+ assert (false , " BCryptGenRandom() failed." );
1881+ }
1882+ return result;
1883+ }
18511884 else version (AnyARC4Random)
18521885 {
18531886 return arc4random ();
@@ -1915,6 +1948,18 @@ if (isUnsigned!UIntType)
19151948
19161949 return buffer;
19171950 }
1951+ else version (Windows )
1952+ {
1953+ UIntType result;
1954+ if (! bcryptGenRandom! UIntType(result))
1955+ {
1956+ version (none )
1957+ return fallbackSeed ();
1958+ else
1959+ assert (false , " BCryptGenRandom() failed." );
1960+ }
1961+ return result;
1962+ }
19181963 else version (AnyARC4Random)
19191964 {
19201965 static if (UIntType.sizeof <= uint .sizeof)
0 commit comments