Added the zend framework 2 library, the path is specified in line no.26 in zend_modul...
[openemr.git] / interface / modules / zend_modules / library / Zend / Math / Rand.php
blob95b71cde8246d6de60e816560d8a1a37b5488b60
1 <?php
2 /**
3 * Zend Framework (http://framework.zend.com/)
5 * @link http://github.com/zendframework/zf2 for the canonical source repository
6 * @copyright Copyright (c) 2005-2013 Zend Technologies USA Inc. (http://www.zend.com)
7 * @license http://framework.zend.com/license/new-bsd New BSD License
8 */
10 namespace Zend\Math;
12 use RandomLib;
14 /**
15 * Pseudorandom number generator (PRNG)
17 abstract class Rand
20 /**
21 * Alternative random byte generator using RandomLib
23 * @var RandomLib\Generator
25 protected static $generator = null;
27 /**
28 * Generate random bytes using OpenSSL or Mcrypt and mt_rand() as fallback
30 * @param int $length
31 * @param bool $strong true if you need a strong random generator (cryptography)
32 * @return string
33 * @throws Exception\RuntimeException
35 public static function getBytes($length, $strong = false)
37 if ($length <= 0) {
38 return false;
40 $bytes = '';
41 if (function_exists('openssl_random_pseudo_bytes')
42 && (version_compare(PHP_VERSION, '5.3.4') >= 0
43 || strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN')
44 ) {
45 $bytes = openssl_random_pseudo_bytes($length, $usable);
46 if (true === $usable) {
47 return $bytes;
50 if (function_exists('mcrypt_create_iv')
51 && (version_compare(PHP_VERSION, '5.3.7') >= 0
52 || strtoupper(substr(PHP_OS, 0, 3)) !== 'WIN')
53 ) {
54 $bytes = mcrypt_create_iv($length, MCRYPT_DEV_URANDOM);
55 if ($bytes !== false && strlen($bytes) === $length) {
56 return $bytes;
59 $checkAlternatives = (file_exists('/dev/urandom') && is_readable('/dev/urandom'))
60 || class_exists('\\COM', false);
61 if (true === $strong && false === $checkAlternatives) {
62 throw new Exception\RuntimeException (
63 'This PHP environment doesn\'t support secure random number generation. ' .
64 'Please consider installing the OpenSSL and/or Mcrypt extensions'
67 $generator = self::getAlternativeGenerator();
68 return $generator->generate($length);
71 /**
72 * Retrieve a fallback/alternative RNG generator
74 * @return RandomLib\Generator
76 public static function getAlternativeGenerator()
78 if (!is_null(static::$generator)) {
79 return static::$generator;
81 if (!class_exists('RandomLib\\Factory')) {
82 throw new Exception\RuntimeException(
83 'The RandomLib fallback pseudorandom number generator (PRNG) '
84 . ' must be installed in the absence of the OpenSSL and '
85 . 'Mcrypt extensions'
88 $factory = new RandomLib\Factory;
89 $factory->registerSource(
90 'HashTiming',
91 'Zend\Math\Source\HashTiming'
93 static::$generator = $factory->getMediumStrengthGenerator();
94 return static::$generator;
97 /**
98 * Generate random boolean
100 * @param bool $strong true if you need a strong random generator (cryptography)
101 * @return bool
103 public static function getBoolean($strong = false)
105 $byte = static::getBytes(1, $strong);
106 return (bool) (ord($byte) % 2);
110 * Generate a random integer between $min and $max
112 * @param int $min
113 * @param int $max
114 * @param bool $strong true if you need a strong random generator (cryptography)
115 * @return int
116 * @throws Exception\DomainException
118 public static function getInteger($min, $max, $strong = false)
120 if ($min > $max) {
121 throw new Exception\DomainException(
122 'The min parameter must be lower than max parameter'
125 $range = $max - $min;
126 if ($range == 0) {
127 return $max;
128 } elseif ($range > PHP_INT_MAX || is_float($range)) {
129 throw new Exception\DomainException(
130 'The supplied range is too great to generate'
133 $log = log($range, 2);
134 $bytes = (int) ($log / 8) + 1;
135 $bits = (int) $log + 1;
136 $filter = (int) (1 << $bits) - 1;
137 do {
138 $rnd = hexdec(bin2hex(self::getBytes($bytes, $strong)));
139 $rnd = $rnd & $filter;
140 } while ($rnd > $range);
142 return ($min + $rnd);
146 * Generate random float (0..1)
147 * This function generates floats with platform-dependent precision
149 * PHP uses double precision floating-point format (64-bit) which has
150 * 52-bits of significand precision. We gather 7 bytes of random data,
151 * and we fix the exponent to the bias (1023). In this way we generate
152 * a float of 1.mantissa.
154 * @param bool $strong true if you need a strong random generator (cryptography)
155 * @return float
157 public static function getFloat($strong = false)
159 $bytes = static::getBytes(7, $strong);
160 $bytes[6] = $bytes[6] | chr(0xF0);
161 $bytes .= chr(63); // exponent bias (1023)
162 list(, $float) = unpack('d', $bytes);
164 return ($float - 1);
168 * Generate a random string of specified length.
170 * Uses supplied character list for generating the new string.
171 * If no character list provided - uses Base 64 character set.
173 * @param int $length
174 * @param string|null $charlist
175 * @param bool $strong true if you need a strong random generator (cryptography)
176 * @return string
177 * @throws Exception\DomainException
179 public static function getString($length, $charlist = null, $strong = false)
181 if ($length < 1) {
182 throw new Exception\DomainException('Length should be >= 1');
185 // charlist is empty or not provided
186 if (empty($charlist)) {
187 $numBytes = ceil($length * 0.75);
188 $bytes = static::getBytes($numBytes, $strong);
189 return substr(rtrim(base64_encode($bytes), '='), 0, $length);
192 $listLen = strlen($charlist);
194 if ($listLen == 1) {
195 return str_repeat($charlist, $length);
198 $bytes = static::getBytes($length, $strong);
199 $pos = 0;
200 $result = '';
201 for ($i = 0; $i < $length; $i++) {
202 $pos = ($pos + ord($bytes[$i])) % $listLen;
203 $result .= $charlist[$pos];
206 return $result;