| Index: src/v8.cc
|
| ===================================================================
|
| --- src/v8.cc (revision 8480)
|
| +++ src/v8.cc (working copy)
|
| @@ -100,42 +100,36 @@
|
| }
|
|
|
|
|
| -static uint32_t random_seed() {
|
| - if (FLAG_random_seed == 0) {
|
| - return random();
|
| +static void seed_random(uint32_t* state) {
|
| + for (int i = 0; i < 4; ++i) {
|
| + state[i] = FLAG_random_seed;
|
| + while (state[i] == 0) {
|
| + state[i] = random();
|
| + }
|
| }
|
| - return FLAG_random_seed;
|
| }
|
|
|
|
|
| -typedef struct {
|
| - uint32_t hi;
|
| - uint32_t lo;
|
| -} random_state;
|
| -
|
| -
|
| // Random number generator using George Marsaglia's MWC algorithm.
|
| -static uint32_t random_base(random_state *state) {
|
| - // Initialize seed using the system random(). If one of the seeds
|
| - // should ever become zero again, or if random() returns zero, we
|
| - // avoid getting stuck with zero bits in hi or lo by re-initializing
|
| - // them on demand.
|
| - if (state->hi == 0) state->hi = random_seed();
|
| - if (state->lo == 0) state->lo = random_seed();
|
| +static uint32_t random_base(uint32_t* state) {
|
| + // Initialize seed using the system random().
|
| + // No non-zero seed will ever become zero again.
|
| + if (state[0] == 0) seed_random(state);
|
|
|
| - // Mix the bits.
|
| - state->hi = 36969 * (state->hi & 0xFFFF) + (state->hi >> 16);
|
| - state->lo = 18273 * (state->lo & 0xFFFF) + (state->lo >> 16);
|
| - return (state->hi << 16) + (state->lo & 0xFFFF);
|
| + // Mix the bits. Never replaces state[i] with 0 if it is nonzero.
|
| + state[0] = 18273 * (state[0] & 0xFFFF) + (state[0] >> 16);
|
| + state[1] = 36969 * (state[1] & 0xFFFF) + (state[1] >> 16);
|
| + state[2] = 23208 * (state[2] & 0xFFFF) + (state[2] >> 16);
|
| + state[3] = 27753 * (state[3] & 0xFFFF) + (state[3] >> 16);
|
| +
|
| + return ((state[2] ^ state[3]) << 16) + ((state[0] ^ state[1]) & 0xFFFF);
|
| }
|
|
|
|
|
| // Used by JavaScript APIs
|
| uint32_t V8::Random(Isolate* isolate) {
|
| ASSERT(isolate == Isolate::Current());
|
| - // TODO(isolates): move lo and hi to isolate
|
| - static random_state state = {0, 0};
|
| - return random_base(&state);
|
| + return random_base(isolate->random_seed());
|
| }
|
|
|
|
|
| @@ -144,9 +138,7 @@
|
| // leaks that could be used in an exploit.
|
| uint32_t V8::RandomPrivate(Isolate* isolate) {
|
| ASSERT(isolate == Isolate::Current());
|
| - // TODO(isolates): move lo and hi to isolate
|
| - static random_state state = {0, 0};
|
| - return random_base(&state);
|
| + return random_base(isolate->private_random_seed());
|
| }
|
|
|
|
|
|
|