summaryrefslogtreecommitdiffstats
path: root/crawl-ref/source/stuff.cc
diff options
context:
space:
mode:
authorMikko Juola <mikko.juola@kolumbus.fi>2009-10-01 14:37:49 +0530
committerDarshan Shaligram <dshaligram@users.sourceforge.net>2009-10-01 14:42:06 +0530
commitfb49425915aef7877fedfc58730cef8bcf58aee7 (patch)
tree32a12f676185d673ce1b4091b9aff57e5c22ad83 /crawl-ref/source/stuff.cc
parentf44f2bc6f575f26209d70243fb9ca7a07893bc59 (diff)
downloadcrawl-ref-fb49425915aef7877fedfc58730cef8bcf58aee7.tar.gz
crawl-ref-fb49425915aef7877fedfc58730cef8bcf58aee7.zip
Harden the PRNG for public servers.
Detailed discussion is here: http://www.genodeen.net/index.clua?cwrng Signed-off-by: Darshan Shaligram <dshaligram@users.sourceforge.net>
Diffstat (limited to 'crawl-ref/source/stuff.cc')
-rw-r--r--crawl-ref/source/stuff.cc42
1 files changed, 41 insertions, 1 deletions
diff --git a/crawl-ref/source/stuff.cc b/crawl-ref/source/stuff.cc
index d825f8e5b4..6155572681 100644
--- a/crawl-ref/source/stuff.cc
+++ b/crawl-ref/source/stuff.cc
@@ -45,6 +45,10 @@ REVISION("$Rev$");
#endif
+#ifdef MORE_HARDENED_PRNG
+#include "sha256.h"
+#endif
+
#ifdef DOS
#include <conio.h>
#endif
@@ -470,6 +474,12 @@ unsigned char get_ch()
return gotched;
}
+void seed_rng(unsigned long* seed_key, size_t num_keys)
+{
+ // MT19937 -- see mt19937ar.cc for details/licence
+ init_by_array(seed_key, num_keys);
+}
+
void seed_rng(long seed)
{
// MT19937 -- see mt19937ar.cc for details/licence
@@ -480,17 +490,43 @@ void seed_rng()
{
unsigned long seed = time( NULL );
#ifdef USE_MORE_SECURE_SEED
+
+ /* (at least) 256-bit wide seed */
+ unsigned long seed_key[8];
+
struct tms buf;
seed += times( &buf ) + getpid();
-#endif
+ seed_key[0] = seed;
+
+ /* Try opening from various system provided (hopefully) CSPRNGs */
+ FILE* seed_f = fopen("/dev/urandom", "rb");
+ if (!seed_f)
+ seed_f = fopen("/dev/random", "rb");
+ if (!seed_f)
+ seed_f = fopen("/dev/srandom", "rb");
+ if (!seed_f)
+ seed_f = fopen("/dev/arandom", "rb");
+ if (seed_f)
+ {
+ fread(&seed_key[1], sizeof(unsigned long), 7, seed_f);
+ fclose(seed_f);
+ }
+ seed_rng(seed_key, 8);
+
+#else
seed_rng(seed);
+#endif
}
// MT19937 -- see mt19937ar.cc for details
unsigned long random_int( void )
{
+#ifndef MORE_HARDENED_PRNG
return (genrand_int32());
+#else
+ return (sha256_genrand());
+#endif
}
int random_range(int low, int high)
@@ -586,7 +622,11 @@ int random2(int max)
if (max <= 1)
return (0);
+ #ifdef MORE_HARDENED_PRNG
+ return (static_cast<int>(sha256_genrand() / (0xFFFFFFFFUL / max + 1)));
+ #else
return (static_cast<int>(genrand_int32() / (0xFFFFFFFFUL / max + 1)));
+ #endif
}
bool coinflip(void)