summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
Diffstat (limited to 'lib')
-rw-r--r--lib/securerandom.rb34
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