View Source

<ac:macro ac:name="note"><ac:parameter ac:name="title">Updated</ac:parameter><ac:rich-text-body>
<p>This RFC has been recently updated to the new component structure</p></ac:rich-text-body></ac:macro>

<p>This RFC contains a proposal for implementing cryptographicaly strong pseudo-random number generator (RNG) in ZF2. Several components withing current ZF2 reqire strong random number and there is also a possibility for future user-space modules to use this component. So component will be single point of generating strong pseudo-random numbers.</p>

<p>Working prototype is ready. Please see <a href="https://github.com/denixport/zf2/tree/feature/rand/library/Zend/Math/Rand">this feature branch</a> on GitHub.</p>

<h2>Overview</h2>
<p>RNG uses scheme described in <a href="http://tools.ietf.org/html/rfc4086">RFC 4086</a>. Generator collects inital entropy data from varous sources, adds this data to entropy pool and periodically mixes the pool with some complex mixing function. This way even with weak and predictable sources of entropy, generated random value is cryptographicaly strong. <br />
Component is partly based on TrueCrypt RNG.</p>

<h2>Component Structure</h2>
<h3>Zend\Math\Rand\Generator</h3>
<p>Generator is constructed with array of sources of randomness (<code>SourceInterface</code>) and mixing function (<code>MixerInterface</code>). This is the way to create custom generators with custom set of sources and mixing function. <br />
Methods to get random values are:</p>
<ul>
<li><code>generate($length)</code> &ndash; random binary string of <code>$length</code> bytes</li>
<li><code>getBoolean()</code> &ndash; boolean</li>
<li><code>getInt($min = 0, $max = PHP_INT_MAX)</code> &ndash; int within <code>$min</code> &amp; <code>$max</code></li>
<li><code>getFloat()</code> &ndash; floating point number between 0 and 1 with machine's precision</li>
<li><code>getString($length, $charlist)</code> &ndash; generates random ASCII string</li>
</ul>



<h3>Factory (Zend\Math\Rand\GeneratorFactory)</h3>
<p>Factory is a fast way to create generator based on pre-defined strength. Generator supports three levels of strength: low, medium, high. For each level different sources and mixing function is used. <br />
Factory methods are:</p>
<ul>
<li><code>create($options)</code> &ndash; create instance based on provided options</li>
<li><code>createGenerator($strength = Strength::MEDIUM)</code> &ndash; create generator of required strength</li>
</ul>


<h3>Source (Zend\Math\Rand\SourceInterface)</h3>
<p>Different sources of entropy in PHP: openssl, /dev/urandom/, mt_rand() etc. </p>

<ac:macro ac:name="code"><ac:default-parameter>php</ac:default-parameter><ac:plain-text-body><![CDATA[
namespace Zend\Math\Rand\Source;

interface SourceInterface
{
public static function isAvailable();
public static function getStrength();
public function generate($length);
}
]]></ac:plain-text-body></ac:macro>


<h3>Mixer (Zend\Math\Rand\MixerInterface)</h3>
<p>Mixing function. Default mixing function is hash mixer based on SHA-512, RIPEMD, Whirpool</p>

<ac:macro ac:name="code"><ac:default-parameter>php</ac:default-parameter><ac:plain-text-body><![CDATA[
namespace Zend\Math\Rand\Mixer;

interface MixerInterface
{
public static function getStrength();
public function mix($bytes);
}
]]></ac:plain-text-body></ac:macro>


<h2>Questions</h2>
<p>Due to refactoring, some questions are not relevant anymore.</p>

<ul>
<li><em>Should RNG component have it's own namespace Zend\Random or live in Zend\Math, or Zend\Crypt?</em></li>
</ul>


<ul>
<li><span style="text-decoration: line-through;">Should RNG express what kind of algorithm (&quot;cryptographically strong&quot; or week) was used?</span></li>
</ul>


<ul>
<li><span style="text-decoration: line-through;">Should component use adapters or single class is good enough?</span></li>
</ul>


<ul>
<li><span style="text-decoration: line-through;">Should there be a distinction between int/bigint (float/bigfloat)?</span></li>
</ul>


<ul>
<li><span style="text-decoration: line-through;">What other adapters, if any, component should provide?</span></li>
</ul>


<h2>References</h2>
<ul>
<li><a href="http://tools.ietf.org/html/rfc4086">RFC 4086</a></li>
<li><a href="http://www.truecrypt.org/docs/?s=random-number-generator">TrueCrypt RNG</a></li>
</ul>