22#include "pycore_initconfig.h"
33#ifdef MS_WINDOWS
44# include <windows.h>
5- /* All sample MSDN wincrypt programs include the header below. It is at least
6- * required with Min GW. */
7- # include <wincrypt.h>
5+ # include <bcrypt.h>
86#else
97# include <fcntl.h>
108# ifdef HAVE_SYS_STAT_H
2523# include <sanitizer/msan_interface.h>
2624#endif
2725
28- #if defined(__APPLE__ ) && defined(__has_builtin )
26+ #if defined(__APPLE__ ) && defined(__has_builtin )
2927# if __has_builtin (__builtin_available )
3028# define HAVE_GETENTRYPY_GETRANDOM_RUNTIME __builtin_available(macOS 10.12, iOS 10.10, tvOS 10.0, watchOS 3.0, *)
3129# endif
@@ -42,43 +40,18 @@ static int _Py_HashSecret_Initialized = 0;
4240#endif
4341
4442#ifdef MS_WINDOWS
45- static HCRYPTPROV hCryptProv = 0 ;
46-
47- static int
48- win32_urandom_init (int raise )
49- {
50- /* Acquire context */
51- if (!CryptAcquireContextW (& hCryptProv , NULL , NULL ,
52- PROV_RSA_FULL , CRYPT_VERIFYCONTEXT ))
53- goto error ;
54-
55- return 0 ;
56-
57- error :
58- if (raise ) {
59- PyErr_SetFromWindowsErr (0 );
60- }
61- return -1 ;
62- }
6343
6444/* Fill buffer with size pseudo-random bytes generated by the Windows CryptoGen
6545 API. Return 0 on success, or raise an exception and return -1 on error. */
6646static int
6747win32_urandom (unsigned char * buffer , Py_ssize_t size , int raise )
6848{
69- if (hCryptProv == 0 )
70- {
71- if (win32_urandom_init (raise ) == -1 ) {
72- return -1 ;
73- }
74- }
75-
7649 while (size > 0 )
7750 {
7851 DWORD chunk = (DWORD )Py_MIN (size , PY_DWORD_MAX );
79- if (! CryptGenRandom ( hCryptProv , chunk , buffer ))
80- {
81- /* CryptGenRandom () failed */
52+ NTSTATUS status = BCryptGenRandom ( NULL , buffer , chunk , BCRYPT_USE_SYSTEM_PREFERRED_RNG );
53+ if (! BCRYPT_SUCCESS ( status )) {
54+ /* BCryptGenRandom () failed */
8255 if (raise ) {
8356 PyErr_SetFromWindowsErr (0 );
8457 }
@@ -221,7 +194,7 @@ py_getrandom(void *buffer, Py_ssize_t size, int blocking, int raise)
221194
222195#if defined(__APPLE__ ) && defined(__has_attribute ) && __has_attribute (availability )
223196static int
224- py_getentropy (char * buffer , Py_ssize_t size , int raise )
197+ py_getentropy (char * buffer , Py_ssize_t size , int raise )
225198 __attribute__((availability (macos ,introduced = 10.12 )))
226199 __attribute__((availability (ios ,introduced = 10.0 )))
227200 __attribute__((availability (tvos ,introduced = 10.0 )))
@@ -458,7 +431,7 @@ lcg_urandom(unsigned int x0, unsigned char *buffer, size_t size)
458431
459432 Used sources of entropy ordered by preference, preferred source first:
460433
461- - CryptGenRandom () on Windows
434+ - BCryptGenRandom () on Windows
462435 - getrandom() function (ex: Linux and Solaris): call py_getrandom()
463436 - getentropy() function (ex: OpenBSD): call py_getentropy()
464437 - /dev/urandom device
@@ -612,12 +585,7 @@ _Py_HashRandomization_Init(const PyConfig *config)
612585void
613586_Py_HashRandomization_Fini (void )
614587{
615- #ifdef MS_WINDOWS
616- if (hCryptProv ) {
617- CryptReleaseContext (hCryptProv , 0 );
618- hCryptProv = 0 ;
619- }
620- #else
588+ #ifndef MS_WINDOWS
621589 dev_urandom_close ();
622590#endif
623591}
0 commit comments