/** * mono_rand_try_get_bytes: * @handle: A pointer to an RNG handle. Handle is set to NULL on failure. * @buffer: A buffer into which to write random data. * @buffer_size: Number of bytes to write into buffer. * @error: Set on error. * * Returns: FALSE on failure and sets @error, TRUE on success. * * Extracts bytes from an RNG handle. */ gboolean mono_rand_try_get_bytes (gpointer *handle, guchar *buffer, gint buffer_size, MonoError *error) { HCRYPTPROV provider; mono_error_init (error); g_assert (handle); provider = (HCRYPTPROV) *handle; if (!CryptGenRandom (provider, buffer_size, buffer)) { CryptReleaseContext (provider, 0); /* we may have lost our context with CryptoAPI, but all hope isn't lost yet! */ provider = (HCRYPTPROV) mono_rand_init (NULL, 0); if (!CryptGenRandom (provider, buffer_size, buffer)) { /* exception will be thrown in managed code */ CryptReleaseContext (provider, 0); *handle = 0; mono_error_set_execution_engine (error, "Failed to gen random bytes (%d)", GetLastError ()); return FALSE; } } return TRUE; }
static gpointer rand_create (void) { mono_rand_open (); return mono_rand_init (NULL, 0); }