views:

209

answers:

4

Currently, Boost only implements the random_device class for Linux (maybe *nix) systems. Does anyone know of existing implementations for other OS-es? Ideally, these implementations would be open-source.

If none exist, how should I go about implementing a non-deterministic RNG for Windows as well as Mac OS X? Do API calls exist in either environment that would provide this functionality? Thanks (and sorry for all the questions)!

+1  A: 

Depends on what you want to use you RNG for.

In general terms, you'll feed seed data into a buffer, generate hash values of the buffer, mix a counter into the result and hash it some more. The reason for using a hash function is that good hashes are designed to yield random-looking results from input data that's more structured.

If you want to use it for cryptography, things'll turn a lot hairier. You'll need to jump through more hoops to ensure that your RNG keeps repeating patterns within reasonably safe limits. I can recommend Bruce Schneier's "Practical Cryptography" (for an introduction on RNGs, and a sample implementation). He's also got some RNG-related stuff up about his yarrow RNG.

better to use the platform's cryptographic RNG than implement one yourself
orip
@orip: again depends on the usage. For cryptographic purposes, some platform's RNGs leave something to be desired.
Sometimes (e.g., C) the platform RNG is lousy for just about everything, yet the sequences it produces are frozen forever in standards documents.
Marsh Ray
+2  A: 

On MacOSX, you can use /dev/random (since it's a *nix).

On Windows, you probably want the CryptGenRandom function. I don't know if there's an implementation of boost::random_device that uses it.

Roger Lipscombe
Per frankodwyer, it sounds like /dev/random can be used for Mac. Thanks, all, for your help!
Brian
A: 

If boost relies on /dev/random, chances are it works on MacOS also (as it has that).

On Windows there is CryptoAPI as part of the OS, and that provides a crypto quality RNG.

Also, I believe modern Intel CPUs have a hardware RNG on the chip - however you'd have to figure out how to get at that on each OS. Using the higher level APIs is probably a better bet.

edit: Here's a link to how the Intel RNG works

frankodwyer
A: 

OpenSSL has a decent one.

#include <openssl/rand.h>
...
time_t now = time(NULL);
RAND_seed(&now, sizeof(now)); // before first number you need

int success = RAND_bytes(...);
if (!success) die_loudly();

RAND_cleanup(); // after you don't need any more numbers

Microsoft CryptoAPI has one on Win32. It requires a few more function calls. Not including the details here because there are 2 to 5 args to each of these calls. Be careful, CryptoAPI seems to require the user to have a complete local profile (C:\Documents and Settings\user\Local Settings) correctly set up before it can give you a random number.

CryptAcquireContext // see docs
CryptGenRandom
CryptReleaseContext
Marsh Ray