compared with
Key
This line was removed.
This word was removed. This word was added.
This line was added.

Changes (135)

View Page History
{deck:id=Skeletons}

{card:label=Zend_Uuid}
{card:label=Zend_Uuid (ZF 1.10 / 1.11)}
{code}
<?php

class Zend_Uuid_Exception extends Zend_Exception {}

class Zend_Uuid {

const MD5 = 3;
const SHA1 = 5;
const clearVer = 15; // 00001111 Clears all bits of version byte with AND
const clearVar = 63; // 00111111 Clears all relevant bits of variant byte with AND
const varRes = 224; // 11100000 Variant reserved for future use
const varMS = 192; // 11000000 Microsft GUID variant
const varRFC = 128; // 10000000 The RFC 4122 variant (this variant)
const varNCS = 0; // 00000000 The NCS compatibility variant
const version1 = 16; // 00010000
const version3 = 48; // 00110000
const version4 = 64; // 01000000
const version5 = 80; // 01010000
const interval = 0x01b21dd213814000; // Time (in 100ns steps) between the start of the UTC and Unix epochs
const nsDNS = '6ba7b810-9dad-11d1-80b4-00c04fd430c8';
const nsURL = '6ba7b811-9dad-11d1-80b4-00c04fd430c8';
const nsOID = '6ba7b812-9dad-11d1-80b4-00c04fd430c8';
const nsX500 = '6ba7b814-9dad-11d1-80b4-00c04fd430c8';

protected static $randomFunc = 'randomTwister';
protected static $randomSource = NULL;
class Zend_Uuid_Exception extends Zend_Exception {}

class Zend_Uuid {

const MD5 = 3;
const SHA1 = 5;
const clearVer = 15; // 00001111 Clears all bits of version byte with AND
const clearVar = 63; // 00111111 Clears all relevant bits of variant byte with AND
const varRes = 224; // 11100000 Variant reserved for future use
const varMS = 192; // 11000000 Microsft GUID variant
const varRFC = 128; // 10000000 The RFC 4122 variant (this variant)
const varNCS = 0; // 00000000 The NCS compatibility variant
const version1 = 16; // 00010000
const version3 = 48; // 00110000
const version4 = 64; // 01000000
const version5 = 80; // 01010000
const interval = 0x01b21dd213814000; // Time (in 100ns steps) between the start of the UTC and Unix epochs
const nsDNS = '6ba7b810-9dad-11d1-80b4-00c04fd430c8';
const nsURL = '6ba7b811-9dad-11d1-80b4-00c04fd430c8';
const nsOID = '6ba7b812-9dad-11d1-80b4-00c04fd430c8';
const nsX500 = '6ba7b814-9dad-11d1-80b4-00c04fd430c8';

protected static $randomFunc = 'randomTwister';
protected static $randomSource = NULL;

//instance properties
protected $bytes;
protected $bytes; $hex;
protected $hex; $string;
protected $string; $urn;
protected $urn; $version;
protected $version; $variant;
protected $variant; $node;
protected $node; $time;
protected $time;

public static function generate($ver = 1, $node = NULL, $ns = NULL) {
/* Create a new UUID based on provided data. */
switch((int) $ver) {
case 1:
return new self(self::mintTime($node));
case 2:
// Version 2 is not supported
throw new Zend_Uuid_Exception("Version 2 is unsupported.");
case 3:
return new self(self::mintName(self::MD5, $node, $ns));
case 4:
return new self(self::mintRand());
case 5:
return new self(self::mintName(self::SHA1, $node, $ns));
default:
throw new Zend_Uuid_Exception("Selected version is invalid or unsupported.");
}
}

public static function generate($ver = 1, $node = NULL, $ns = NULL) {
/* Create a new UUID based on provided data. */
switch((int) $ver) {
case 1:
return new self(self::mintTime($node));
case 2:
// Version 2 is not supported
throw new Zend_Guid_Exception("Version 2 is unsupported.");
case 3:
return new self(self::mintName(self::MD5, $node, $ns));
case 4:
return new self(self::mintRand());
case 5:
return new self(self::mintName(self::SHA1, $node, $ns));
default:
throw new Zend_Guid_Exception("Selected version is invalid or unsupported.");
public static function import($uuid) {
/* Import an existing UUID. */
return new self(self::makeBin($uuid, 16));
}
}

public static function import($uuid) compare($a, $b) {
/* Import an existing UUID. */
return new self(self::makeBin($uuid, 16));
}

public static function compare($a, $b) {
/* Compares the binary representations of two UUIDs.
The comparison will return true if they are bit-exact,
or if neither is valid. */
if (self::makeBin($a, 16)==self::makeBin($b, 16))
return TRUE;
else
return TRUE; FALSE;
}

public function __toString() {
return $this->string;
}

public function __get($var) {
switch($var) {
case "bytes":
return $this->bytes;
case "hex":
return bin2hex($this->bytes);
case "string":
return $this->__toString();
case "urn":
return "urn:uuid:".$this->__toString();
case "version":
return ord($this->bytes[6]) >> 4;
case "variant":
$byte = ord($this->bytes[8]);
if ($byte >= self::varRes)
return 3;
if ($byte >= self::varMS)
return 2;
if ($byte >= self::varRFC)
return 1;
else
return FALSE; 0;
case "node":
if (ord($this->bytes[6])>>4==1)
return bin2hex(substr($this->bytes,10));
else
return NULL;
case "time":
if (ord($this->bytes[6])>>4==1) {
// Restore contiguous big-endian byte order
$time = bin2hex($this->bytes[6].$this->bytes[7].$this->bytes[4].$this->bytes[5].$this->bytes[0].$this->bytes[1].$this->bytes[2].$this->bytes[3]);
// Clear version flag
$time[0] = "0";
// Do some reverse arithmetic to get a Unix timestamp
$time = (hexdec($time) - self::interval) / 10000000;
return $time;
}

public function __toString() {
return $this->string;
}

public function __get($var) {
switch($var) {
case "bytes": else
return $this->bytes;
case "hex":
return bin2hex($this->bytes);
case "string":
return $this->__toString();
case "urn":
return "urn:uuid:".$this->__toString();
case "version":
return ord($this->bytes[6]) >> 4;
case "variant":
$byte = ord($this->bytes[8]);
if ($byte >= self::varRes)
return 3;
if ($byte >= self::varMS)
return 2;
if ($byte >= self::varRFC)
return 1;
else
return 0;
case "node":
if (ord($this->bytes[6])>>4==1)
return bin2hex(substr($this->bytes,10));
else
return NULL;
case "time": default:
if (ord($this->bytes[6])>>4==1) { return NULL;
// Restore contiguous big-endian byte order
$time = bin2hex($this->bytes[6].$this->bytes[7].$this->bytes[4].$this->bytes[5].$this->bytes[0].$this->bytes[1].$this->bytes[2].$this->bytes[3]);
// Clear version flag
$time[0] = "0";
// Do some reverse arithmetic to get a Unix timestamp
$time = (hexdec($time) - self::interval) / 10000000;
return $time;
}
}

protected function __construct($uuid) {
if (strlen($uuid) != 16)
throw new Zend_Uuid_Exception("Input must be a 128-bit integer.");
$this->bytes = $uuid;
// Optimize the most common use
$this->string =
bin2hex(substr($uuid,0,4))."-". else
return NULL;
default: bin2hex(substr($uuid,4,2))."-".
bin2hex(substr($uuid,6,2))."-". return NULL;
bin2hex(substr($uuid,8,2))."-".
bin2hex(substr($uuid,10,6));
}
}

protected function __construct($uuid) {
if (strlen($uuid) != 16)
throw new Zend_Guid_Exception("Input must be a 128-bit integer.");
$this->bytes = $uuid;
// Optimize the most common use
$this->string =
bin2hex(substr($uuid,0,4))."-".
bin2hex(substr($uuid,4,2))."-".
bin2hex(substr($uuid,6,2))."-".
bin2hex(substr($uuid,8,2))."-".
bin2hex(substr($uuid,10,6));
}

protected static function mintTime($node = NULL) {
/* Generates a Version 1 UUID.
These are derived from the time at which they were generated. */
// Get time since Gregorian calendar reform in 100ns intervals
// This is exceedingly difficult because of PHP's (and pack()'s)
// integer size limits.
// Note that this will never be more accurate than to the microsecond.
$time = microtime(1) * 10000000 + self::interval;
// Convert to a string representation
$time = sprintf("%F", $time);
preg_match("/^\d+/", $time, $time); //strip decimal point
// And now to a 64-bit binary representation
$time = base_convert($time[0], 10, 16);
$time = pack("H*", str_pad($time, 16, "0", STR_PAD_LEFT));
// Reorder bytes to their proper locations in the UUID
$uuid = $time[4].$time[5].$time[6].$time[7].$time[2].$time[3].$time[0].$time[1];
// Generate a random clock sequence
$uuid .= self::randomBytes(2);
// set variant
$uuid[8] = chr(ord($uuid[8]) & self::clearVar | self::varRFC);
// set version
$uuid[6] = chr(ord($uuid[6]) & self::clearVer | self::version1);
// Set the final 'node' parameter, a MAC address
if ($node)
$node = self::makeBin($node, 6);
if (!$node) {
// If no node was provided or if the node was invalid,
// generate a random MAC address and set the multicast bit
$node = self::randomBytes(6);
$node[0] = pack("C", ord($node[0]) | 1);
}
$uuid .= self::randomBytes(2); $node;
// set variant
$uuid[8] = chr(ord($uuid[8]) & self::clearVar | self::varRFC);
// set version
$uuid[6] = chr(ord($uuid[6]) & self::clearVer | self::version1);
// Set the final 'node' parameter, a MAC address
if ($node)
$node = self::makeBin($node, 6);
if (!$node) {
// If no node was provided or if the node was invalid,
// generate a random MAC address and set the multicast bit
$node = self::randomBytes(6);
$node[0] = pack("C", ord($node[0]) | 1);
return $uuid;
}
$uuid .= $node;
return $uuid;
}

protected static function mintRand() {
/* Generate a Version 4 UUID.
These are derived soly from random numbers. */
// generate random fields
$uuid = self::randomBytes(16);
// set variant
$uuid[8] = chr(ord($uuid[8]) & self::clearVar | self::varRFC);
// set variant version
$uuid[8] = chr(ord($uuid[8]) & self::clearVar | self::varRFC);
// set version
$uuid[6] = chr(ord($uuid[6]) & self::clearVer | self::version4);
return $uuid;
}

protected static function mintName($ver, $node, $ns) {
/* Generates a Version 3 or Version 5 UUID.
These are derived from a hash of a name and its namespace, in binary form. */
if (!$node)
throw new Zend_Uuid_Exception("A name-string is required for Version 3 or 5 UUIDs.");
// if the namespace UUID isn't binary, make it so
$ns = self::makeBin($ns, 16);
if (!$node) (!$ns)
throw new Zend_Guid_Exception("A name-string Zend_Uuid_Exception("A binary namespace is required for Version 3 or 5 UUIDs.");
// if the namespace UUID isn't binary, make it so
$ns = self::makeBin($ns, 16);
if (!$ns)
throw new Zend_Uuid_Exception("A binary namespace is required for Version 3 or 5 UUIDs.");
switch($ver) {
case self::MD5:
$version = self::version3;
$uuid = md5($ns.$node,1);
break;
case self::MD5: self::SHA1:
$version = self::version3; self::version5;
$uuid = md5($ns.$node,1); substr(sha1($ns.$node,1),0, 16);
break;
case self::SHA1:
$version = self::version5;
$uuid = substr(sha1($ns.$node,1),0, 16);
break;
}
// set variant
$uuid[8] = chr(ord($uuid[8]) & self::clearVar | self::varRFC);
// set version
$uuid[6] = chr(ord($uuid[6]) & self::clearVer | $version);
return ($uuid);
}
// set variant
$uuid[8] = chr(ord($uuid[8]) & self::clearVar | self::varRFC);
// set version
$uuid[6] = chr(ord($uuid[6]) & self::clearVer | $version);
return ($uuid);
}

protected static function makeBin($str, $len) {
/* Insure that an input string is either binary or hexadecimal.
Returns binary representation, or false on failure. */
if ($str instanceof self)
return $str->bytes;
if (strlen($str)==$len)
return $str->bytes; $str;
if (strlen($str)==$len)
else
$str = preg_replace("/^urn:uuid:/is", "", $str); // strip URN scheme and namespace
$str = preg_replace("/[^a-f0-9]/is", "", $str); // strip non-hex characters
if (strlen($str) != ($len * 2))
return $str; FALSE;
else
$str = preg_replace("/^urn:uuid:/is", "", $str); // strip URN scheme and namespace
$str = preg_replace("/[^a-f0-9]/is", "", $str); // strip non-hex characters
if (strlen($str) != ($len * 2))
return FALSE; pack("H*", $str);
else
return pack("H*", $str);
}

public static function initRandom() {
/* Look for a system-provided source of randomness, which is usually crytographically secure.
/dev/urandom is tried first simply out of bias for Linux systems. */
if (is_readable('/dev/urandom')) {
self::$randomSource = fopen('/dev/urandom', 'rb');
self::$randomFunc = 'randomFRead';
}
else if (class_exists('COM', 0)) {
try {
self::$randomSource = new COM('CAPICOM.Utilities.1'); // See http://msdn.microsoft.com/en-us/library/aa388182(VS.85).aspx
self::$randomFunc = 'randomCOM';
}
catch(Exception $e) {}
}
return self::$randomFunc;
}

public static function randomBytes($bytes) initRandom() {
return call_user_func(array('self', self::$randomFunc), $bytes);
}
/* Look for a system-provided source of randomness, which is usually crytographically secure.
protected static function randomTwister($bytes) {
/* Get the specified number of random bytes, using mt_rand().
Randomness is returned as a string of bytes. */
$rand = "";
for ($a = 0; $a < $bytes; $a++) {
$rand .= chr(mt_rand(0, 255));
/dev/urandom is tried first simply out of bias for Linux systems. */
if (is_readable('/dev/urandom')) {
self::$randomSource = fopen('/dev/urandom', 'rb');
self::$randomFunc = 'randomFRead';
}
else if (class_exists('COM', 0)) {
try {
self::$randomSource = new COM('CAPICOM.Utilities.1'); // See http://msdn.microsoft.com/en-us/library/aa388182(VS.85).aspx
self::$randomFunc = 'randomCOM';
}
catch(Exception $e) {}
}
return $rand; self::$randomFunc;
}

public static function randomBytes($bytes) {
return call_user_func(array('self', self::$randomFunc), $bytes);
}

protected static function randomFRead($bytes) randomTwister($bytes) {
/* Get the specified number of random bytes, using mt_rand().
Randomness is returned as a string of bytes. */
$rand = "";
for ($a = 0; $a < $bytes; $a++) {
$rand .= chr(mt_rand(0, 255));
}
return $rand;
}

protected static function randomFRead($bytes) {
/* Get the specified number of random bytes using a file handle
previously opened with UUID::initRandom().
Randomness is returned as a string of bytes. */
return fread(self::$randomSource, $bytes);
}

protected static function randomCOM($bytes) {
/* Get the specified number of random bytes using Windows'
randomness source via a COM object previously created by UUID::initRandom().
Randomness is returned as a string of bytes. */
return base64_decode(self::$randomSource->GetRandom($bytes,0)); // straight binary mysteriously doesn't work, hence the base64
}
}

{code}
{card}

{card:label=Zend_Uuid (ZF 2.0)}
{code}
<?php
/**
* Zend Framework
*
* LICENSE
*
* This source file is subject to the new BSD license that is bundled
* with this package in the file LICENSE.txt.
* It is also available through the world-wide-web at this URL:
* http://framework.zend.com/license/new-bsd
* If you did not receive a copy of the license and are unable to
* obtain it through the world-wide-web, please send an email
* to license@zend.com so we can send you a copy immediately.
*
* @category Zend
* @package Zend_TimeSync
* @copyright Copyright (c) 2005-2010 Zend Technologies USA Inc. (http://www.zend.com)
* @version $Id$
* @license http://framework.zend.com/license/new-bsd New BSD License
*/
/**
* @namespace
*/
namespace Zend\Uuid;

class Zend_Uuid
{
const MD5 = 3;
const SHA1 = 5;
/**
* 00001111 Clears all bits of version byte with AND
*
* @var int
*/
const clearVer = 15;
/**
* 00111111 Clears all relevant bits of variant byte with AND
*
* @var int
*/
const clearVar = 63;
/**
* 11100000 Variant reserved for future use
*
* @var int
*/
const varRes = 224;
/**
* 11000000 Microsft GUID variant
*
* @var int
*/
const varMS = 192;
/**
* 10000000 The RFC 4122 variant (this variant)
*
* @var int
*/
const varRFC = 128;
/**
* 00000000 The NCS compatibility variant
*
* @var int
*/
const varNCS = 0;
/**
* 00010000
*
* @var int
*/
const version1 = 16;
/**
* 00110000
*
* @var int
*/
const version3 = 48;
/**
* 01000000
*
* @var int
*/
const version4 = 64;
/**
* 01010000
*
* @var int
*/
const version5 = 80;
/**
* Time (in 100ns steps) between the start of the UTC and Unix epochs
*
* @var int
*/
const interval = 0x01b21dd213814000;
/**
* @var string
*/
const nsDNS = '6ba7b810-9dad-11d1-80b4-00c04fd430c8';
/**
* @var string
*/
const nsURL = '6ba7b811-9dad-11d1-80b4-00c04fd430c8';
/**
* @var string
*/
const nsOID = '6ba7b812-9dad-11d1-80b4-00c04fd430c8';
/**
* @var string
*/
const nsX500 = '6ba7b814-9dad-11d1-80b4-00c04fd430c8';
/**
* @var string
*/
protected static $randomFunc = 'randomTwister';
/**
* @var mixed
*/
protected static $randomSource = NULL;
protected $bytes;
protected $hex;
protected $string;
protected $urn;
protected $version;
protected $variant;
protected $node;
protected $time;

/**
* @param string $uuid
* @throws \Zend\Uuid\Exception
*/
protected function __construct ($uuid)
{
if (strlen($uuid) != 16) {
throw new Exception('Input must be a 128-bit integer.');
}

$this->bytes = $uuid;

// Optimize the most common use
$this->string = bin2hex(
substr($uuid, 0, 4)) . "-" . bin2hex(
substr($uuid, 4, 2)) . "-" . bin2hex(
substr($uuid, 6, 2)) . "-" . bin2hex(
substr($uuid, 8, 2)) . "-" . bin2hex(
substr($uuid, 10, 6));
}


/**
* @param int $ver
* @param unknown_type $node
* @param unknown_type $ns
* @return \Zend\Uuid\Zend_Uuid|\Zend\Uuid\Zend_Uuid|\Zend\Uuid\Zend_Uuid|\Zend\Uuid\Zend_Uuid
* @throws \Zend\Uuid\Exception
*/
public static function generate ($ver = 1, $node = NULL, $ns = NULL)
{
/* Create a new UUID based on provided data. */
switch ((int) $ver) {
case 1:
return new self( self::mintTime( $node ) );
case 2:
// Version 2 is not supported
throw new Exception( 'Version 2 is unsupported.' );
case 3:
return new self( self::mintName( self::MD5, $node, $ns ) );
case 4:
return new self( self::mintRand() );
case 5:
return new self( self::mintName( self::SHA1, $node, $ns ) );
default:
throw new Exception( 'Selected version is invalid or unsupported.' );
}
}

/**
* Import an existing UUID
*
* @param string $uuid
* @return \Zend\Uuid\Zend_Uuid
*/
public static function import ($uuid)
{
return new self(self::makeBin($uuid, 16));
}

/**
* Compares the binary representations of two UUIDs.
* The comparison will return true if they are bit-exact,
* or if neither is valid.
*
* @param string $a
* @param string $b
* @return string|string
*/
public static function compare ($a, $b)
{
/* */
if (self::makeBin($a, 16) == self::makeBin($b, 16)) {
return TRUE;
} else {
return FALSE;
}
}

/**
* Echo the uuid
*/
public function __toString ()
{
return $this->string;
}


/**
* @param string $var
* @return string|string|number|number|number|number|number|NULL|number|NULL|NULL
*/
public function __get ($var)
{
switch ($var) {
case "bytes":
return $this->bytes;
case "hex":
return bin2hex($this->bytes);
case "string":
return $this->__toString();
case "urn":
return "urn:uuid:" . $this->__toString();
case "version":
return ord($this->bytes[6]) >> 4;
case "variant":
$byte = ord(
$this->bytes[8]);
if ($byte >= self::varRes) return 3;
if ($byte >= self::varMS) return 2;
if ($byte >= self::varRFC) {
return 1;
} else {
return 0;
}
case "node":
if (ord($this->bytes[6]) >> 4 == 1) {
return bin2hex(substr($this->bytes,10));
} else {
return NULL;
}
case "time":
if (ord($this->bytes[6]) >> 4 == 1) {
// Restore contiguous big-endian byte order
$time = bin2hex( $this->bytes[6] . $this->bytes[7] . $this->bytes[4] . $this->bytes[5] .
$this->bytes[0] . $this->bytes[1] . $this->bytes[2] . $this->bytes[3]);
// Clear version flag
$time[0] = "0";
// Do some reverse arithmetic to get a Unix timestamp
$time = (hexdec($time) - self::interval) / 10000000;
return $time;
} else
return NULL;
default:
return NULL;
}
}

/**
* Generates a Version 1 UUID.
* These are derived from the time at which they were generated.
*
* @param unknown_type $node
* @return unknown
*/
protected static function mintTime ($node = NULL)
{

/** Get time since Gregorian calendar reform in 100ns intervals
* This is exceedingly difficult because of PHP's (and pack()'s)
* integer size limits.
* Note that this will never be more accurate than to the microsecond.
*/
$time = microtime(1) * 10000000 + self::interval;

// Convert to a string representation
$time = sprintf("%F", $time);

//strip decimal point
preg_match("/^\d+/", $time, $time);

// And now to a 64-bit binary representation
$time = base_convert( $time[0], 10, 16);
$time = pack("H*", str_pad($time, 16, "0", STR_PAD_LEFT) );

// Reorder bytes to their proper locations in the UUID
$uuid = $time[4] . $time[5] . $time[6] . $time[7] . $time[2] . $time[3] . $time[0] . $time[1];

// Generate a random clock sequence
$uuid .= self::randomBytes(2);

// set variant
$uuid[8] = chr(ord($uuid[8]) & self::clearVar | self::varRFC);

// set version
$uuid[6] = chr(ord($uuid[6]) & self::clearVer | self::version1);

// Set the final 'node' parameter, a MAC address
if ($node) {
$node = self::makeBin($node, 6);
}


// If no node was provided or if the node was invalid,
// generate a random MAC address and set the multicast bit
if (! $node) {
$node = self::randomBytes(6);
$node[0] = pack("C", ord($node[0]) | 1 );
}
$uuid .= $node;
return $uuid;
}
/**
* Generate a Version 4 UUID.
* These are derived soly from random numbers.
* generate random fields
*
* @return unknown
*/
protected static function mintRand ()
{
$uuid = self::randomBytes(16);
// set variant
$uuid[8] = chr(ord($uuid[8]) & self::clearVar | self::varRFC);
// set version
$uuid[6] = chr(ord($uuid[6]) & self::clearVer | self::version4);
return $uuid;
}
/**
* Generates a Version 3 or Version 5 UUID.
* These are derived from a hash of a name and its namespace, in binary form.
*
* @param unknown_type $ver
* @param unknown_type $node
* @param unknown_type $ns
* @return unknown
* @throws /Zend/Uuid/Exception
*/
protected static function mintName ($ver, $node, $ns)
{
if (! $node) {
throw new Exception('A name-string is required for Version 3 or 5 UUIDs.');
}

// if the namespace UUID isn't binary, make it so
$ns = self::makeBin($ns, 16);
if (! $ns) {
throw new Exception('A binary namespace is required for Version 3 or 5 UUIDs.');
}

switch ($ver) {
case self::MD5:
$version = self::version3;
$uuid = md5($ns . $node, 1);
break;
case self::SHA1:
$version = self::version5;
$uuid = substr(sha1($ns . $node, 1), 0, 16);
break;
}

// set variant
$uuid[8] = chr( ord($uuid[8]) & self::clearVar | self::varRFC);

// set version
$uuid[6] = chr( ord($uuid[6]) & self::clearVer | $version);
return ($uuid);
}
/**
* Insure that an input string is either binary or hexadecimal.
* Returns binary representation, or false on failure.
*
* @param unknown_type $str
* @param unknown_type $len
* @return \Zend\Uuid\Zend_Uuid|string
*/
protected static function makeBin ($str, $len)
{
if ($str instanceof self)
return $str->bytes;
if (strlen($str) == $len) {
return $str;
} else {
// strip URN scheme and namespace
$str = preg_replace('/^urn:uuid:/is', '', $str);
}
// strip non-hex characters
$str = preg_replace('/[^a-f0-9]/is', '', $str);
if (strlen($str) != ($len * 2)) {
return FALSE;
} else {
return pack("H*", $str);
}
}

/**
* Look for a system-provided source of randomness, which is usually crytographically secure.
* /dev/urandom is tried first simply out of bias for Linux systems.
*/
public static function initRandom ()
{
if (is_readable('/dev/urandom')) {
self::$randomSource = fopen( '/dev/urandom', 'rb');
self::$randomFunc = 'randomFRead';
} else
// See http://msdn.microsoft.com/en-us/library/aa388182(VS.85).aspx
if (class_exists('COM', 0)) {
try {
self::$randomSource = new COM('CAPICOM.Utilities.1');
self::$randomFunc = 'randomCOM';
} catch (Exception $e) {
throw new Exception ('Cannot initialize windows random generator');
}
}
return self::$randomFunc;
}

public static function randomBytes ($bytes)
{
return call_user_func(array('self', self::$randomFunc), $bytes);
}
/**
* Get the specified number of random bytes, using mt_rand().
* Randomness is returned as a string of bytes.
*
* @param unknown_type $bytes
* @return string
*/
protected static function randomTwister ($bytes)
{
$rand = "";
for ($a = 0; $a < $bytes; $a ++) {
$rand .= chr(mt_rand(0, 255));
}
return $rand;
}

/**
* Get the specified number of random bytes using a file handle
* previously opened with UUID::initRandom().
* Randomness is returned as a string of bytes.
*
* @param unknown_type $bytes
*/
protected static function randomFRead ($bytes)
{
return fread(self::$randomSource, $bytes);
}
/**
* Get the specified number of random bytes using Windows'
* randomness source via a COM object previously created by UUID::initRandom().
* Randomness is returned as a string of bytes.
*
* Straight binary mysteriously doesn't work, hence the base64
*
* @param unknown_type $bytes
*/
protected static function randomCOM ($bytes)
{
return base64_decode(self::$randomSource->GetRandom($bytes, 0));
}
}

{code}
{card}

{deck}
{zone-data}