msvcrt: Reimplement rand() and srand() to use per-thread data for the
random seed.
This commit is contained in:
parent
2ec3b96135
commit
ad8cb6133e
|
@ -38,12 +38,26 @@ void _beep( unsigned int freq, unsigned int duration)
|
||||||
Beep(freq, duration);
|
Beep(freq, duration);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*********************************************************************
|
||||||
|
* srand (MSVCRT.@)
|
||||||
|
*/
|
||||||
|
void MSVCRT_srand( unsigned int seed )
|
||||||
|
{
|
||||||
|
thread_data_t *data = msvcrt_get_thread_data();
|
||||||
|
data->random_seed = seed;
|
||||||
|
}
|
||||||
|
|
||||||
/*********************************************************************
|
/*********************************************************************
|
||||||
* rand (MSVCRT.@)
|
* rand (MSVCRT.@)
|
||||||
*/
|
*/
|
||||||
int MSVCRT_rand(void)
|
int MSVCRT_rand(void)
|
||||||
{
|
{
|
||||||
return (rand() & 0x7fff);
|
thread_data_t *data = msvcrt_get_thread_data();
|
||||||
|
|
||||||
|
/* this is the algorithm used by MSVC, according to
|
||||||
|
* http://en.wikipedia.org/wiki/List_of_pseudorandom_number_generators */
|
||||||
|
data->random_seed = data->random_seed * 214013 + 2531011;
|
||||||
|
return (data->random_seed >> 16) & MSVCRT_RAND_MAX;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*********************************************************************
|
/*********************************************************************
|
||||||
|
|
|
@ -93,6 +93,7 @@ extern DWORD msvcrt_tls_index;
|
||||||
struct __thread_data {
|
struct __thread_data {
|
||||||
int thread_errno;
|
int thread_errno;
|
||||||
unsigned long thread_doserrno;
|
unsigned long thread_doserrno;
|
||||||
|
unsigned int random_seed; /* seed for rand() */
|
||||||
char *strtok_next; /* next ptr for strtok() */
|
char *strtok_next; /* next ptr for strtok() */
|
||||||
unsigned char *mbstok_next; /* next ptr for mbstok() */
|
unsigned char *mbstok_next; /* next ptr for mbstok() */
|
||||||
MSVCRT_wchar_t *wcstok_next; /* next ptr for wcstok() */
|
MSVCRT_wchar_t *wcstok_next; /* next ptr for wcstok() */
|
||||||
|
@ -375,6 +376,7 @@ struct MSVCRT__stati64 {
|
||||||
#define MSVCRT_WEOF (MSVCRT_wint_t)(0xFFFF)
|
#define MSVCRT_WEOF (MSVCRT_wint_t)(0xFFFF)
|
||||||
#define MSVCRT_EOF (-1)
|
#define MSVCRT_EOF (-1)
|
||||||
#define MSVCRT_TMP_MAX 0x7fff
|
#define MSVCRT_TMP_MAX 0x7fff
|
||||||
|
#define MSVCRT_RAND_MAX 0x7fff
|
||||||
#define MSVCRT_BUFSIZ 512
|
#define MSVCRT_BUFSIZ 512
|
||||||
|
|
||||||
#define MSVCRT_STDIN_FILENO 0
|
#define MSVCRT_STDIN_FILENO 0
|
||||||
|
|
|
@ -695,7 +695,7 @@
|
||||||
@ cdecl sinh(double)
|
@ cdecl sinh(double)
|
||||||
@ varargs sprintf(ptr str) MSVCRT_sprintf
|
@ varargs sprintf(ptr str) MSVCRT_sprintf
|
||||||
@ cdecl sqrt(double)
|
@ cdecl sqrt(double)
|
||||||
@ cdecl srand(long)
|
@ cdecl srand(long) MSVCRT_srand
|
||||||
@ varargs sscanf(str str) MSVCRT_sscanf
|
@ varargs sscanf(str str) MSVCRT_sscanf
|
||||||
@ cdecl strcat(str str)
|
@ cdecl strcat(str str)
|
||||||
@ cdecl strchr(str long)
|
@ cdecl strchr(str long)
|
||||||
|
|
|
@ -303,6 +303,7 @@ static void test_defines(void)
|
||||||
CHECK_DEF(WEOF);
|
CHECK_DEF(WEOF);
|
||||||
CHECK_DEF(EOF);
|
CHECK_DEF(EOF);
|
||||||
CHECK_DEF(TMP_MAX);
|
CHECK_DEF(TMP_MAX);
|
||||||
|
CHECK_DEF(RAND_MAX);
|
||||||
CHECK_DEF(BUFSIZ);
|
CHECK_DEF(BUFSIZ);
|
||||||
CHECK_DEF(STDIN_FILENO);
|
CHECK_DEF(STDIN_FILENO);
|
||||||
CHECK_DEF(STDOUT_FILENO);
|
CHECK_DEF(STDOUT_FILENO);
|
||||||
|
|
|
@ -44,6 +44,7 @@ thread_data_t *msvcrt_get_thread_data(void)
|
||||||
if (!(ptr = HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*ptr) )))
|
if (!(ptr = HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*ptr) )))
|
||||||
_amsg_exit( _RT_THREAD );
|
_amsg_exit( _RT_THREAD );
|
||||||
if (!TlsSetValue( msvcrt_tls_index, ptr )) _amsg_exit( _RT_THREAD );
|
if (!TlsSetValue( msvcrt_tls_index, ptr )) _amsg_exit( _RT_THREAD );
|
||||||
|
ptr->random_seed = 1;
|
||||||
}
|
}
|
||||||
SetLastError( err );
|
SetLastError( err );
|
||||||
return ptr;
|
return ptr;
|
||||||
|
|
Loading…
Reference in New Issue