Use crypto.getRandomValues for RNG if available

window.crypto.random is really old and depreciated.  Should use
crypto.getRandomValues instead.  If we are able to generate entropy from
crypto.getRandomValues, we should not add entropy from Math.random, as
it may be unreliable.
Use better entropy generation methods

Using time to generate entropy is not optimal, as time is predictible
and not random.  This change prefers crypto.getRandomValues, falls back
to using mouse movement, and ultimately if enough entropy is not
generated by the time we need a key, it will fall back to Math.random.