diff options
author | glass <glass@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2014-08-08 11:00:47 +0000 |
---|---|---|
committer | glass <glass@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2014-08-08 11:00:47 +0000 |
commit | 0a22f4c168d197734a79a34c36b837d6e117e7e7 (patch) | |
tree | e7a0ffda03cc2bd69973ca3e0bbf73a0ad1f0a1b /lib/securerandom.rb | |
parent | d6f0bd2b8423807755bae05a388625a8ef6e7e04 (diff) | |
download | ruby-0a22f4c168d197734a79a34c36b837d6e117e7e7.tar.gz |
* lib/securerandom.rb: use OpenSSL::BN for performance improvement.
* benchmark/bm_securerandom.rb: benchmark script.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@47104 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'lib/securerandom.rb')
-rw-r--r-- | lib/securerandom.rb | 34 |
1 files changed, 21 insertions, 13 deletions
diff --git a/lib/securerandom.rb b/lib/securerandom.rb index 3ff5075023..29368ee431 100644 --- a/lib/securerandom.rb +++ b/lib/securerandom.rb @@ -214,21 +214,29 @@ module SecureRandom # def self.random_number(n=0) if 0 < n - hex = n.to_s(16) - hex = '0' + hex if (hex.length & 1) == 1 - bin = [hex].pack("H*") - mask = bin[0].ord - mask |= mask >> 1 - mask |= mask >> 2 - mask |= mask >> 4 - begin - rnd = SecureRandom.random_bytes(bin.length) - rnd[0] = (rnd[0].ord & mask).chr - end until rnd < bin - rnd.unpack("H*")[0].hex + if defined? OpenSSL::BN + OpenSSL::BN.rand_range(n).to_i + else + hex = n.to_s(16) + hex = '0' + hex if (hex.length & 1) == 1 + bin = [hex].pack("H*") + mask = bin[0].ord + mask |= mask >> 1 + mask |= mask >> 2 + mask |= mask >> 4 + begin + rnd = SecureRandom.random_bytes(bin.length) + rnd[0] = (rnd[0].ord & mask).chr + end until rnd < bin + rnd.unpack("H*")[0].hex + end else # assumption: Float::MANT_DIG <= 64 - i64 = SecureRandom.random_bytes(8).unpack("Q")[0] + if defined? OpenSSL::BN + i64 = OpenSSL::BN.rand(64, -1).to_i + else + i64 = SecureRandom.random_bytes(8).unpack("Q")[0] + end Math.ldexp(i64 >> (64-Float::MANT_DIG), -Float::MANT_DIG) end end |