PHPize Online / SQLize Online  /  SQLtest Online

A A A
Share      Blog   Popular
Copy Format Clear
Copy Clear
Copy Format Clear
<?php /** * La classe RandomBinary ha lo scopo di generare una stringa binaria * (128-bit string) casuale di livello crittografico della lunghezza * ricevuta in argomento. Non sono previste conversioni verso altre basi. * * La generazione della stringa avviene partendo dalle funzioni predefinite * di PHP o attraverso la prima estensione installata con maggiore grado * di affidabilità fino al caso limite della costruzione con entropia scarsa * poiché non si basa su quella pura. * * Categoria: Cryptographically Secure Pseudo-Random Number Generator (CSPRNG) * Eseguibile anche da qui: * https://paiza.io/projects/iUD0HLm_YdTWSSBUqtrfGw */ interface IRandomBinary { /** * Riporta una stringa binaria casuale crittografica di lunghezza data * * @param int $len * @return string * @throws RandomBinaryException */ static function generate($len); } /** * Eccezioni personalizzate della classe */ class RandomBinaryException extends Exception {} class RandomBinary implements IRandomBinary { /** * Il seme crittografico * * @var string */ private static $_salt = '$%~V\L.hxpLbOqDAv)~ESb8}[w'; /** * Riporta una stringa binaria casuale crittografica * di lunghezza data. * Cercherà di richiamare nell'ordine: random_bytes, * "/dev/urandom", "mcrypt_create_iv", * "openssl_random_pseudo_bytes", "COM" (per le piattaforme Windows) * oppure "/dev/random". Se nessuna di queste è disponibile * genererà una stringa pseudo-casuale attingendo da più fonti. * * @param int $len * @return string * @throws RandomBinaryException */ public static function generate($len) { // Verifica consistenza della lunghezza richiesta if(!is_int($len) || $len < 1) { throw new RandomBinaryException( "l'argomento deve essere intero e positivo" ); } // Estrae dei byte binari crittografici if(is_callable('random_bytes')) {// Per PHP7+ return random_bytes($len); } if(is_readable('/dev/urandom') && ($fh = fopen('/dev/urandom', 'rb')) !== FALSE) { stream_set_read_buffer($fh, $len); $i = 0; do { if(++ $i == 5) {// Troppi casi falliti throw new RandomBinaryException( "unable to get {$len} binary bytes" ); } $bytes = fread($fh, $len); } while($bytes === FALSE || mb_strlen($bytes, '8bit') != $len); fclose($fh); // Closing handle return $bytes; } if(is_callable('mcrypt_create_iv')) { // Per PHP5- return mcrypt_create_iv($len, MCRYPT_DEV_URANDOM); } if(extension_loaded("openssl") && is_callable("openssl_random_pseudo_bytes")) { // Se non trova una stringa valida ripete la ricerca $j = 0; do { if(++ $j == 5) { // Troppi casi falliti throw new RandomBinaryException("troppi tentativi falliti"); } $bytes = openssl_random_pseudo_bytes($len, $cstrong); } while((!$bytes || !$cstrong)); return $bytes; } if(class_exists('COM')) { // MS-Windows platform // http://msdn.microsoft.com/en-us/library/aa388176(VS.85).aspx try { $CAPI_Util = new COM('CAPICOM.Utilities.1'); $bytes = $CAPI_Util->GetRandom($len,0); // if we ask for binary data PHP munges it, so we // request base64 return value. We squeeze out the // redundancy and useless ==CRLF by hashing... #if ($pr_bits) { $pr_bits = md5($pr_bits,TRUE); } } catch (Exception $ex) { // echo 'Exception: ' . $ex->getMessage(); } return $bytes; } if(is_readable('/dev/random') && ($fh = fopen('/dev/random', 'rb')) !== FALSE) { // Generatore di caratteri casuali bloccante stream_set_read_buffer($fh, $len); $bytes = fread($fh, $len); if ($bytes === FALSE || mb_strlen($bytes, '8bit') != $len) { throw new RandomBinaryException("unable to get {$len} bytes"); } fclose($fh); // Closing handle. return $bytes; } // Caso disperato // La stringa binaria desiderata $binary = ""; // Cerca di fare un'ulteriore stringa casuale partendo // dall'IP address del client e della porta se disponibili if(isset($_SERVER['REMOTE_ADDR'], $_SERVER['REMOTE_PORT'])) { $client = $_SERVER['REMOTE_ADDR'] .":". $_SERVER['REMOTE_PORT']; } elseif(isset($_SERVER['REMOTE_ADDR'])) { $client = $_SERVER['REMOTE_ADDR']; } elseif(isset($_SERVER['REMOTE_PORT'])) { $client = $_SERVER['REMOTE_PORT']; } else { $client = str_shuffle(chr(mt_rand(32, 126)) . self::$_salt . uniqid("", TRUE) . $binary . $client . sprintf("%.022f", microtime(TRUE))); } if(count(hash_algos())) { // Si costruisce una stringa che verrà sottoposta a tutte // le funzioni di hash disponibili nel server trasformandole // in binario base 128-bit che verranno appese a quelle // già ricavate nelle interazioni precedenti finché // non si raggiunge la lunghezza desiderata do { $bin = "";// Contiene la stringa binaria generata dal ciclo // Produce una stringa cercando di coinvolgere più sorgenti $str = str_shuffle(chr(mt_rand(32, 126)) . self::$_salt . uniqid("", TRUE) . $binary . $client . sprintf("%.022f", microtime(TRUE))); // Genera tutti gli hash disponibili sul server della stringa $str quindi trova quella binaria corrispondente ed infine la concatena foreach(hash_algos() as $algo) { $bin .= pack("H*", hash($algo, $str)); } // Aggiunge la porzione di stringa binaria a quella già ottenuta $binary = str_shuffle(mb_substr($binary . $bin, 0, $len, "8bit")); // Per evitare di avere lo stesso tempo di questo ciclo usleep(rand(10, 1000)); } while(mb_strlen($binary, "8bit") != $len); } else { // Caso talmente disperato che è ultima spiaggia fa uso // esclusivamente delle funzionalità minime del sistema // che non soddisfano i requisiti CSPRNG partendo dollo // spazio di caratteri appartenenti alla classe GRAPH $keyspace = '0123456789abcdefghijklmnopqrstuvwxyz' . 'ABCDEFGHIJKLMNOPQRSTUVWXYZ!"#$%&\'()' . '*+,\-./:;<=>?@[]^_`{|}~'; $charactersLength = strlen($keyspace) - 1; $binary = ""; do { $randomString = ''; for ($i = 0, $length = 10 * $len; $i < $length; $i++) { $randomString .= $keyspace[rand(0, $charactersLength)]; } $binary = $this->str2byte(str_shuffle($randomString)); } while(mb_strlen($binary, "8bit") != $len); } return $binary; } /** * Produce una stringa di testo in tipo binario. * Nota fa uso della funzione "str_shuffle" * * @param string $string * @return string * @link: https://stackoverflow.com/a/35878424 */ private function str2byte($string) { $hexstr = unpack('H*', $string); return str_shuffle(pack("H*", array_shift($hexstr))); } } // Esempio d'uso: $str = RandomBinary::generate(7); echo $str;
Show:  
Copy Clear