[issue27266] Always use getrandom() in os.random() on Linux and add block=False parameter to os.urandom()

Larry Hastings report at bugs.python.org
Wed Jun 8 20:24:47 EDT 2016


Larry Hastings added the comment:

> I'd also *STRONGLY* request that we avoid adding any new APIs in relation to this that mean "Use os.urandom" is no longer the preferred option to obtain cryptographically strong random numbers in Python.

According to the documentation, os.urandom() does not actually *guarantee* cryptographically strong random numbers in Python.  Indeed, it has never guaranteed this; you can check the 2.6 documentation, it says the same thing.

There are debates among cryptographers about how strong the numbers are.  The paper cited by Mr. Ts'o shows that the numbers can be pretty awful under Linux when the entropy pool is empty.

The only way of fixing this this is by using a different API, which can block in an unbounded fashion.  It's simply unreasonable to change to this API by default, because on Linux /dev/urandom is guaranteed to never block.

I don't see it as an improvement to add a block= parameter to os.urandom(); the parameter behaves differently on different platforms (currently ignored on most platforms) and if implemented would make the underlying implementation and behavior far more difficult to predict and reason about.

Mr. Ts'o had exactly the same problem on Linux.  /dev/urandom was the preferred way of obtaining cryptographically strong random numbers.  But it didn't produce them in all cases, and in order to produce them he really had to block.  Instead of changing /dev/urandom so it would sometimes block, he added a new kernel API (getrandom()) which is permitted to block, and he basically left /dev/urandom alone.  I see Python as facing the same problem, and I think it should solve the problem in the same way: leave os.urandom() alone and add a new function getrandom() where possible.

I would support a new function in 3.6, something like random.get_cprng_bytes(n) (probably a bad name), which always returns cryptographically strong PRNG bits and is permitted to block in an unbounded fashion.  The complication here is I'm not sure we can provide it on every platform; the quality of bits available from /dev/random on OS X is apparently highly debatable.  (OTOH, what aspect of cryptography is not highly, endlessly, debatable? *sigh*)

----------

_______________________________________
Python tracker <report at bugs.python.org>
<http://bugs.python.org/issue27266>
_______________________________________


More information about the Python-bugs-list mailing list