程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> 網頁編程 >> PHP編程 >> PHP綜合 >> php 使用“/dev/urandom”獲取隨機數

php 使用“/dev/urandom”獲取隨機數

編輯:PHP綜合
首先,說一下偽隨機數,偽隨機數並不是假隨機數,這裡的“偽”是有規律的意思,就是計算機產生的偽隨機數既是隨機的又是有規律的。怎樣理解呢?產生的偽隨機數有時遵守一定的規律,有時不遵守任何規律;偽隨機數有一部分遵守一定的規律;另一部分不遵守任何規律。比如“世上沒有兩片形狀完全相同的樹葉”。
  /dev/random和/dev/urandom是Linux系統中提供的隨機偽設備,這兩個設備的任務,是提供永不為空的隨機字節數據流。很多解密程序與安全應用程序(如SSH Keys,SSL Keys等)需要它們提供的隨機數據流。
  這兩個設備的差異在於:/dev/random的random pool依賴於系統中斷,因此在系統的中斷數不足時,/dev/random設備會一直封鎖,嘗試讀取的進程就會進入等待狀態,直到系統的中斷數充分夠用, /dev/random設備可以保證數據的隨機性。/dev/urandom不依賴系統的中斷,也就不會造成進程忙等待,但是數據的隨機性也不高。

代碼示例

    利用mycrpt

    /*  
     * 通過此方法獲取隨機數,但需要mycrpt支持
     *
     */
    private function GetURandom2($min = 0, $max = 0x7FFFFFFF)
    {/*{{{*/
        $diff = $max - $min;
        if ($diff < 0 || $diff > 0x7FFFFFFF) {
            throw new RuntimeException("Bad range");
        }   

        $bytes = mcrypt_create_iv(4, MCRYPT_DEV_URANDOM);
        if ($bytes === false || strlen($bytes) != 4) {
            throw new RuntimeException("Unable to get 4 bytes");
        }   

        $ary = unpack("Nint", $bytes);
        $val = $ary['int'] & 0x7FFFFFFF;   // 32-bit safe
        $fp = (float) $val / 2147483647.0; // convert to [0,1]

        return round($fp * $diff) + $min;
    }/*}}}*/
}

    使用fread讀取/dev/urandom文件

 /* *
     * php 版本 >= 5.3, 通過讀取"/dev/urandom"實現產生較好隨機數
     *
     * */
    private function GetURandom($min = 0, $max = 0x7FFFFFFF)
    {/*{{{*/
        $diff = $max - $min;
        if ($diff > PHP_INT_MAX) {
            throw new RuntimeException('Bad Range');
        }   

        $fh = fopen('/dev/urandom', 'r');
        stream_set_read_buffer($fh, PHP_INT_SIZE);
        $bytes = fread($fh, PHP_INT_SIZE );
        if ($bytes === false || strlen($bytes) != PHP_INT_SIZE ) {
            //throw new RuntimeException("nable to get". PHP_INT_SIZE . "bytes");
            return 0;
        }   
        fclose($fh);

        if (PHP_INT_SIZE == 8) { // 64-bit versions
            list($higher, $lower) = array_values(unpack('N2', $bytes));
            $value = $higher << 32 | $lower;
        }   
        else { // 32-bit versions
            list($value) = array_values(unpack('Nint', $bytes));

        }   

        $val = $value & PHP_INT_MAX;
        $fp = (float)$val / PHP_INT_MAX; // convert to [0,1]

        return (int)(round($fp * $diff) + $min);
    }/*}}}*/ *
  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved