The TAESPRNG class is implemented as such:

  • It would gather entropy using dedicated OS API, i.e. the CryptGenRandom API under Windows or /dev/urandom - /dev/random on Linux/POSIX systems; and since we are paranoid, we XOR some entropy hash (retrieved e.g. directly from RDTSC and other system variables) to those OS values - so even if the API is compromised, we try to have some changing input;
  • This entropy (256 bytes of password, 16 bytes of salt) would be hashed using safe PBKDF2-HMAC-SHA256 key derivation function (256 iterations by default) to setup the secret key of an AES-256 cypher, and set a counter (CTR) initial value by applying this AES-256 to the salt;
  • Each time some output is to be generated, AES-256 is applied to the CTR to produce 16 bytes (2^128 bits) of pseudorandom data;
  • The CTR is incremented after each 16-byte block; AES being a block cipher, it is a permutation of the space of block values: as such, it won't ever output twice the same 16-byte block, so you can generate 2^128 blocks, i.e. 2^132 bytes before the CTR overflows;
  • The AES-256 cypher is re-seeded from entropy on a regular basis (after some bytes are generated), to avoid potential attacks on backward or forward security;
  • The implementation is thread-safe, a shared TAESPRNG.Main instance is available, but you can create your own TAESPRNG instance, with tuned parameters (number of PBKDF2 counts or automatic re-seeding number of bytes);
  • The level of security would be the same on all platforms, since OS is used only for entropy, but an unique CSPRNG algorithm would actually generate the data - even a compromised system (older CryptGenRandomAPI had known weaknesses, or you could imagine some plot-based undocumented backdoor) may produce safe enough output;
  • It would use AES-NI or Padlock hardware acceleration, if available.

You may use it in your projects by calling TAESPRNG.Main.FillRandom() overloaded methods or TAESPRNG.Main.FillRandomBytes().

See the class documentation.

The main idea of a CSPRNG is that its output is as safe as the cypher it is based on.
Using AES-256, and initial PBKDF2 key derivation of OS-gathered entropy, implements a very good randomness extractor.
Last but not least, especially if your CPU supports AES-NI (which is very likely on a server), performance would be very high.
Just use TAESPRNG when you need random input. Then go back to your own code.

Feedback is welcome on our forum, as usual!