a C++ take on Fortuna CSPRNG implementation, as devised by Niels Fergusson and Bruce Schneier in Practical Cryptography 🍀
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
Go to file
surtur d257b4b113
add README.md [skip ci]
3 months ago
lib fmtlib: bump submodule to version 9.1.0 3 months ago
.clang-format clang-format: BinPack{Arguments,Parameters}: false 11 months ago
.clang-tidy chore(clang-tidy): unify flags 12 months ago
.drone.starlark ci: pull dep images in separate steps 9 months ago
.editorconfig add .editorconfig [skip ci] 11 months ago
.gitattributes add .gitattributes file 1 year ago
.gitignore add proper SeedFileManager implementation 11 months ago
.gitmodules feat: use fmt instead of iostreams 1 year ago
.pre-commit-config.yaml chore(.pre-commit-config.yaml): bump hook versions 11 months ago
CMakeLists.txt cmake: add more diagnostic warning flags 10 months ago
LICENSE chore: copyright current year 9 months ago
Makefile makefile: build in tmp when not in CI 11 months ago
README.md add README.md [skip ci] 3 months ago
accumulator.cpp chore: print info msgs to stderr 10 months ago
accumulator.h chore: print info msgs to stderr 10 months ago
do_task.cpp DoTask: timed_mutex -> recursive_timed_mutex 11 months ago
do_task.h DoTask: timed_mutex -> recursive_timed_mutex 11 months ago
entropy_src.h fix: -Wnon-virtual-dtor 10 months ago
event_adder.h fix: -Wnon-virtual-dtor 10 months ago
event_adder_impl.h chore: print info msgs to stderr 10 months ago
fortuna.cpp fortuna: rethrow on error in ctor 10 months ago
fortuna.h fortuna: add moar_random_data() fun 10 months ago
generator.cpp fortuna,generator({fmt}) print with colours 10 months ago
generator.h chore(generator): rm comment [skip ci] 10 months ago
main.cpp main: use moar_random_data() 10 months ago
meson.build meson: add '-DNDEBUG' on release builds 9 months ago
pool.cpp pool: rm event_str remnants 10 months ago
pool.h fix: -Wextra-semi 10 months ago
seed_file_management.cpp fix(SeedFileManager): 6-byte seed file issue 10 months ago
seed_file_management.h sfm: new seed_f_path "/var/tmp/.fortuna.seed" 10 months ago
urandom_entropy_src.cpp fix(-Wuseless-cast) rm a cast in UrandomEntropySrc 10 months ago
urandom_entropy_src.h fix(-Wsuggest-override): override virtual base fun 10 months ago
util.h Util: add de_hex() fun 10 months ago



pre-commit Build Status

this repo contains the sawce of the Fortuna CSPRNG implementation in C++.

adherent to C++20 (best effort).
handles OS signals (SIGINT, SIGTERM, SIGUSR1, SIGUSR2).

the following asciicast shows fortuna provide a 100MiB of pseudo-random data along with useful debug insights on data retrieval times, the reseed_ctr, bytes remaining, and Pool 0 (p0) size: asciicast


to ensure a fundamental soundness of the implementation, fortuna output has been statistically analysed using:

  • dieharder - A Random Number Test Suite (v3.31.1) - on a ~243GiB stream of random material that the program kept producing until dieharder finished testing (log)
    command used:

    ➜ fortuna | dieharder -a -g 200 -k 2 -Y 1

    parameter explanation:

    • -a: runs all available tests (including some from NIST's STS)
    • -g 200: a special mode to read raw data from standard input (where fortuna outputs its stream)
    • -k 2: speed and precision of sample reading, set to slow and precise:

      2 is slower still, but (we hope) accurate to machine precision for any number of psamples up to some as yet unknown numerical upper limit (it has been tested out to at least hundreds of thousands).

    • -Y 1: Xtrategy flag for the "test to failure" mode - set to "resolve ambiguity" (RA)

    dieharder warning:

    NOTE WELL: The assessment(s) for the rngs may, in fact, be completely incorrect or misleading. There are still "bad tests" in dieharder, although we are working to fix and improve them (and try to document them in the test descriptions visible with -g testnumber -h). In particular, 'Weak' pvalues should occur one test in two hundred, and 'Failed' pvalues should occur one test in a million with the default thresholds - that's what p MEANS. Use them at your Own Risk! Be Warned!

    that is, it appears fortuna can withstand this "dieharder battery of tests".

  • ent - A Pseudorandom Number Sequence Test Program - on a sample of 1000MiB of random data ent run


note that this project is a direct continuation of the semestral work originally created for my Applied Cryptography university course, which has since been archived as the course had concluded.

⚠ polite warning: this code is not production-ready and has not been professionally and thoroughly vetted.

be advised that while I do believe the implementation to be correct and valid, I would still recommend AGAINST USING this program to get entropy for any serious purpose, since the code has not undergone proper peer review.

please, be kind. this is my first larger-than-main.cpp C++ effort.

build 🔨

build-time dependencies

  • c++ compiler (note: only tested on fedora 35,36 and archlinux with g++ and clang++ (versions ~12.2.1 and ~14.0.5, respectively)
  • ninja
  • CMake
  • make
  • libc++ (only tested with libcxx)
  • libc
  • libm
  • cryptopp
  • lib{a,l,t,ub}san on fedora, gcc-libs on archlinux
  • {fmt} - this one's also present as a submodule at lib/fmt and automatically used if fmtlib is not already present on the system.
  • ldd - optional
  • git
  • implicitly pkg-conf to look for all the libraries

runtime dependencies

  • libc++
  • libm
  • cryptopp

make targets

there are multiple targets available in the Makefile that allow for a relatively straightforward (definitely room for improvement) development experience without the need to type g++ or (CMake, for that matter) incantations directly:

  • make clean - cleans up build objects, ninja and CMake-generated files
  • make build - a synonym for CMake's debug build (also make debug)
  • make release - builds a release-optimised binary
  • make san - builds a binary with sanitizers
  • make tidy - builds a binary with clang tidy checks
  • make check - checks code using cppcheck and runs make tidy
  • make test - doesn't run actual tests (🙈), instead checks code with make check and then builds a debug binary
  • make distclean - scrapes CMake build files from build directories

the debug/release/san targets each have a clang++ variant available, suffixed _cl, such that, e.g. make debug_cl would build a debug binary with clang++.

code formatting

see .clang-format

➜ clang-format *.cpp *.h


GPL-3.0-or-later (see LICENSE for details).