summaryrefslogtreecommitdiff
path: root/random.c
diff options
context:
space:
mode:
authorkosaki <kosaki@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2015-11-30 20:31:31 +0000
committerkosaki <kosaki@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2015-11-30 20:31:31 +0000
commit99c05fb38e8dc6d96a59c074de7b9aa39b1df31e (patch)
treeac347ea9c12887161257d9f2dd1fad0b3b469f26 /random.c
parent052535be3e082d9c2d6b7650ff9430479036bab5 (diff)
* random.c (Init_RandomSeed): move all Random::DEFAULT
construction bits to Init_RandomSeed2. Random::DEFAULT and Ruby internal hashes are no longer shared their seed. * random.c (Init_RandomSeed2): ditto. And, kill evil rb_obj_reveal() stuff. * random.c (init_hashseed): add MT argument. * random.c: (init_siphash): ditto. * test/ruby/test_rand.rb (TestRand#test_default_seed): new test for Random::DEFAULT::seed. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@52815 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'random.c')
-rw-r--r--random.c62
1 files changed, 33 insertions, 29 deletions
diff --git a/random.c b/random.c
index 11b7a3febe..8a9ef3a5f5 100644
--- a/random.c
+++ b/random.c
@@ -1452,24 +1452,9 @@ static union {
uint32_t u32[(16 * sizeof(uint8_t) - 1) / sizeof(uint32_t)];
} sipseed;
-static VALUE
-init_randomseed(struct MT *mt)
-{
- uint32_t initial[DEFAULT_SEED_CNT];
- VALUE seed;
-
- fill_random_seed(initial);
- init_by_array(mt, initial, DEFAULT_SEED_CNT);
- seed = make_seed_value(initial);
- explicit_bzero(initial, DEFAULT_SEED_LEN);
- return seed;
-}
-
static void
-init_hashseed(void)
+init_hashseed(struct MT *mt)
{
- struct MT *mt = default_mt();
-
hashseed = genrand_int32(mt);
#if SIZEOF_ST_INDEX_T*CHAR_BIT > 4*8
hashseed <<= 32;
@@ -1486,9 +1471,8 @@ init_hashseed(void)
}
static void
-init_siphash(void)
+init_siphash(struct MT *mt)
{
- struct MT *mt = default_mt();
int i;
for (i = 0; i < numberof(sipseed.u32); ++i)
@@ -1512,28 +1496,48 @@ rb_memhash(const void *ptr, long len)
#endif
}
+/* Initialize Ruby internal seeds */
void
Init_RandomSeed(void)
{
- rb_random_t *r = &default_rand;
- struct MT *mt = &r->mt;
- VALUE seed = init_randomseed(mt);
+ /*
+ Don't reuse this MT for Random::DEFAULT. Random::DEFAULT::seed shouldn't
+ provide a hint that an attacker guess siphash's seed.
+ */
+ struct MT mt;
+ uint32_t initial_seed[DEFAULT_SEED_CNT];
- init_hashseed();
- init_siphash();
+ fill_random_seed(initial_seed);
+ init_by_array(&mt, initial_seed, DEFAULT_SEED_CNT);
- rb_global_variable(&r->seed);
- r->seed = seed;
+ init_hashseed(&mt);
+ init_siphash(&mt);
+
+ explicit_bzero(initial_seed, DEFAULT_SEED_LEN);
+}
+
+static VALUE
+init_randomseed(struct MT *mt)
+{
+ uint32_t initial[DEFAULT_SEED_CNT];
+ VALUE seed;
+
+ fill_random_seed(initial);
+ init_by_array(mt, initial, DEFAULT_SEED_CNT);
+ seed = make_seed_value(initial);
+ explicit_bzero(initial, DEFAULT_SEED_LEN);
+ return seed;
}
+/* construct Random::DEFAULT bits */
static void
Init_RandomSeed2(void)
{
- VALUE seed = default_rand.seed;
+ rb_random_t *r = &default_rand;
+ struct MT *mt = &r->mt;
- if (RB_TYPE_P(seed, T_BIGNUM)) {
- rb_obj_reveal(seed, rb_cBignum);
- }
+ r->seed = init_randomseed(mt);
+ rb_global_variable(&r->seed);
}
void