Move all enum types definitions to types.h
[stockfish] / src / rkiss.h
1 /*
2   Stockfish, a UCI chess playing engine derived from Glaurung 2.1
3   Copyright (C) 2004-2008 Tord Romstad (Glaurung author)
4   Copyright (C) 2008-2010 Marco Costalba, Joona Kiiski, Tord Romstad
5
6   Stockfish is free software: you can redistribute it and/or modify
7   it under the terms of the GNU General Public License as published by
8   the Free Software Foundation, either version 3 of the License, or
9   (at your option) any later version.
10
11   Stockfish is distributed in the hope that it will be useful,
12   but WITHOUT ANY WARRANTY; without even the implied warranty of
13   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14   GNU General Public License for more details.
15
16   You should have received a copy of the GNU General Public License
17   along with this program.  If not, see <http://www.gnu.org/licenses/>.
18
19   This file is based on original code by Heinz van Saanen and is
20   available under the GNU General Public License as published by
21   the Free Software Foundation, either version 3 of the License, or
22   (at your option) any later version.
23
24  ** A small "keep it simple and stupid" RNG with some fancy merits:
25  **
26  ** Quite platform independent
27  ** Passes ALL dieharder tests! Here *nix sys-rand() e.g. fails miserably:-)
28  ** ~12 times faster than my *nix sys-rand()
29  ** ~4 times faster than SSE2-version of Mersenne twister
30  ** Average cycle length: ~2^126
31  ** 64 bit seed
32  ** Return doubles with a full 53 bit mantissa
33  ** Thread safe
34  **
35  ** (c) Heinz van Saanen
36
37 */
38
39 #if !defined(RKISS_H_INCLUDED)
40 #define RKISS_H_INCLUDED
41
42 #include "types.h"
43
44 class RKISS {
45
46   // Keep variables always together
47   struct S { uint64_t a, b, c, d; } s;
48
49   // Return 64 bit unsigned integer in between [0,2^64-1]
50   uint64_t rand64() {
51
52       const uint64_t
53         e = s.a - ((s.b <<  7) | (s.b >> 57));
54       s.a = s.b ^ ((s.c << 13) | (s.c >> 51));
55       s.b = s.c + ((s.d << 37) | (s.d >> 27));
56       s.c = s.d + e;
57       return s.d = e + s.a;
58   }
59
60   // Init seed and scramble a few rounds
61   void raninit() {
62
63       s.a = 0xf1ea5eed;
64       s.b = s.c = s.d = 0xd4e12c77;
65       for (int i = 0; i < 73; i++)
66           rand64();
67   }
68
69 public:
70   RKISS() { raninit(); }
71   template<typename T> T rand() { return T(rand64()); }
72 };
73
74 #endif // !defined(RKISS_H_INCLUDED)