random.hh revision 9235:5aa4896ed55a
12623SN/A/* 22623SN/A * Copyright (c) 2003-2005 The Regents of The University of Michigan 32623SN/A * All rights reserved. 42623SN/A * 52623SN/A * Redistribution and use in source and binary forms, with or without 62623SN/A * modification, are permitted provided that the following conditions are 72623SN/A * met: redistributions of source code must retain the above copyright 82623SN/A * notice, this list of conditions and the following disclaimer; 92623SN/A * redistributions in binary form must reproduce the above copyright 102623SN/A * notice, this list of conditions and the following disclaimer in the 112623SN/A * documentation and/or other materials provided with the distribution; 122623SN/A * neither the name of the copyright holders nor the names of its 132623SN/A * contributors may be used to endorse or promote products derived from 142623SN/A * this software without specific prior written permission. 152623SN/A * 162623SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 172623SN/A * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 182623SN/A * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 192623SN/A * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 202623SN/A * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 212623SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 222623SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 232623SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 242623SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 252623SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 262623SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 272665Ssaidi@eecs.umich.edu * 282665Ssaidi@eecs.umich.edu * Authors: Nathan Binkert 292623SN/A * Ali Saidi 302623SN/A */ 312623SN/A 322623SN/A/* 332623SN/A * Mersenne Twister random number generator has a period of 342623SN/A * 2^19937-1. 352623SN/A * 365529Snate@binkert.org * The actual math is in its own file to keep the license clear. 375529Snate@binkert.org */ 382623SN/A 392623SN/A#ifndef __BASE_RANDOM_HH__ 402623SN/A#define __BASE_RANDOM_HH__ 412623SN/A 425529Snate@binkert.org#include <ios> 432623SN/A#include <string> 442623SN/A 452623SN/A#include "base/types.hh" 462623SN/A 472623SN/Aclass Checkpoint; 482839Sktlim@umich.edu 492798Sktlim@umich.educlass Random 502623SN/A{ 512623SN/A protected: 522623SN/A static const int N = 624; 532623SN/A static const int M = 397; 542623SN/A static const uint32_t MATRIX_A = (uint32_t)0x9908b0df; 552623SN/A static const uint32_t UPPER_MASK = (uint32_t)0x80000000; 562948Ssaidi@eecs.umich.edu static const uint32_t LOWER_MASK = (uint32_t)0x7fffffff; 572623SN/A 582623SN/A uint32_t mt[N]; 592623SN/A int mti; 602948Ssaidi@eecs.umich.edu 613401Sktlim@umich.edu uint32_t genrand(); 622623SN/A uint32_t genrand(uint32_t max); 632623SN/A uint64_t genrand(uint64_t max); 643647Srdreslin@umich.edu 653647Srdreslin@umich.edu void 662623SN/A _random(int8_t &value) 672623SN/A { 683349Sbinkertn@umich.edu value = genrand() & (int8_t)-1; 692623SN/A } 703349Sbinkertn@umich.edu 712623SN/A void 722623SN/A _random(int16_t &value) 732623SN/A { 742623SN/A value = genrand() & (int16_t)-1; 754475Sstever@eecs.umich.edu } 764475Sstever@eecs.umich.edu 772948Ssaidi@eecs.umich.edu void 782948Ssaidi@eecs.umich.edu _random(int32_t &value) 792948Ssaidi@eecs.umich.edu { 803349Sbinkertn@umich.edu value = (int32_t)genrand(); 812948Ssaidi@eecs.umich.edu } 822948Ssaidi@eecs.umich.edu 835606Snate@binkert.org void 845336Shines@cs.fsu.edu _random(int64_t &value) 853349Sbinkertn@umich.edu { 862948Ssaidi@eecs.umich.edu value = (int64_t)genrand() << 32 | (int64_t)genrand(); 872948Ssaidi@eecs.umich.edu } 882623SN/A 892623SN/A void 902623SN/A _random(uint8_t &value) 912623SN/A { 922623SN/A value = genrand() & (uint8_t)-1; 932623SN/A } 942948Ssaidi@eecs.umich.edu 952948Ssaidi@eecs.umich.edu void 962623SN/A _random(uint16_t &value) 972623SN/A { 982623SN/A value = genrand() & (uint16_t)-1; 992623SN/A } 1003349Sbinkertn@umich.edu 1012623SN/A void 1022657Ssaidi@eecs.umich.edu _random(uint32_t &value) 1032948Ssaidi@eecs.umich.edu { 1042948Ssaidi@eecs.umich.edu value = genrand(); 1052948Ssaidi@eecs.umich.edu } 1062948Ssaidi@eecs.umich.edu 1072948Ssaidi@eecs.umich.edu void 1082948Ssaidi@eecs.umich.edu _random(uint64_t &value) 1092948Ssaidi@eecs.umich.edu { 1105336Shines@cs.fsu.edu value = (uint64_t)genrand() << 32 | (uint64_t)genrand(); 1112948Ssaidi@eecs.umich.edu } 1122948Ssaidi@eecs.umich.edu 1132948Ssaidi@eecs.umich.edu // [0,1] 1142948Ssaidi@eecs.umich.edu void 1152623SN/A _random(float &value) 1162623SN/A { 1172623SN/A // ieee floats have 23 bits of mantissa 1182623SN/A value = (genrand() >> 9) / 8388608.0; 1192623SN/A } 1202623SN/A 1212948Ssaidi@eecs.umich.edu // [0,1] 1222948Ssaidi@eecs.umich.edu void 1232623SN/A _random(double &value) 1242623SN/A { 1254192Sktlim@umich.edu double number = genrand() * 2097152.0 + (genrand() >> 11); 1264192Sktlim@umich.edu value = number / 9007199254740992.0; 1272623SN/A } 1282623SN/A 1293349Sbinkertn@umich.edu 1302623SN/A // Range based versions of the random number generator 1312657Ssaidi@eecs.umich.edu int8_t 1322948Ssaidi@eecs.umich.edu _random(int8_t min, int8_t max) 1332948Ssaidi@eecs.umich.edu { 1342948Ssaidi@eecs.umich.edu uint32_t diff = max - min; 1352948Ssaidi@eecs.umich.edu return static_cast<int8_t>(min + genrand(diff)); 1362948Ssaidi@eecs.umich.edu } 1372948Ssaidi@eecs.umich.edu 1385336Shines@cs.fsu.edu int16_t 1392948Ssaidi@eecs.umich.edu _random(int16_t min, int16_t max) 1402948Ssaidi@eecs.umich.edu { 1412948Ssaidi@eecs.umich.edu uint32_t diff = max - min; 1422948Ssaidi@eecs.umich.edu return static_cast<int16_t>(min + genrand(diff)); 1432623SN/A } 1442623SN/A 1452623SN/A int32_t 1462623SN/A _random(int32_t min, int32_t max) 1472623SN/A { 1483349Sbinkertn@umich.edu uint32_t diff = max - min; 1493349Sbinkertn@umich.edu return static_cast<int32_t>(min + genrand(diff)); 1502623SN/A } 1513222Sktlim@umich.edu 1523170Sstever@eecs.umich.edu int64_t 1532623SN/A _random(int64_t min, int64_t max) 1542623SN/A { 1552856Srdreslin@umich.edu uint64_t diff = max - min; 1562856Srdreslin@umich.edu return static_cast<int64_t>(min + genrand(diff)); 1572623SN/A } 1582623SN/A 1592623SN/A uint8_t 1602901Ssaidi@eecs.umich.edu _random(uint8_t min, uint8_t max) 1612798Sktlim@umich.edu { 1622798Sktlim@umich.edu uint32_t diff = max - min; 1632798Sktlim@umich.edu return static_cast<uint8_t>(min + genrand(diff)); 1642623SN/A } 1652623SN/A 1662623SN/A uint16_t 1672623SN/A _random(uint16_t min, uint16_t max) 1682623SN/A { 1692623SN/A uint32_t diff = max - min; 1702623SN/A return static_cast<uint16_t>(min + genrand(diff)); 1712623SN/A } 1725177Sgblack@eecs.umich.edu 1735177Sgblack@eecs.umich.edu uint32_t 1745177Sgblack@eecs.umich.edu _random(uint32_t min, uint32_t max) 1752623SN/A { 1762623SN/A uint32_t diff = max - min; 1772623SN/A return static_cast<uint32_t>(min + genrand(diff)); 1785177Sgblack@eecs.umich.edu } 1795177Sgblack@eecs.umich.edu 1805177Sgblack@eecs.umich.edu uint64_t 1812623SN/A _random(uint64_t min, uint64_t max) 1823349Sbinkertn@umich.edu { 1833349Sbinkertn@umich.edu uint64_t diff = max - min; 1842644Sstever@eecs.umich.edu return static_cast<uint64_t>(min + genrand(diff)); 1854471Sstever@eecs.umich.edu } 1865315Sstever@gmail.com 1875315Sstever@gmail.com public: 1885315Sstever@gmail.com Random(); 1895315Sstever@gmail.com Random(uint32_t s); 1905315Sstever@gmail.com Random(uint32_t init_key[], int key_length); 1915315Sstever@gmail.com ~Random(); 1922798Sktlim@umich.edu 1934471Sstever@eecs.umich.edu void init(uint32_t s); 1944471Sstever@eecs.umich.edu void init(uint32_t init_key[], int key_length); 1954471Sstever@eecs.umich.edu 1964471Sstever@eecs.umich.edu template <typename T> 1975103Ssaidi@eecs.umich.edu T 1985103Ssaidi@eecs.umich.edu random() 1995103Ssaidi@eecs.umich.edu { 2005103Ssaidi@eecs.umich.edu T value; 2015103Ssaidi@eecs.umich.edu _random(value); 2025336Shines@cs.fsu.edu return value; 2035103Ssaidi@eecs.umich.edu } 2045103Ssaidi@eecs.umich.edu 2052839Sktlim@umich.edu template <typename T> 2062623SN/A T 2072623SN/A random(T min, T max) 2082623SN/A { 209 return _random(min, max); 210 } 211 212 // [0,1] 213 double 214 gen_real1() 215 { 216 return genrand() / 4294967296.0; 217 } 218 219 // [0,1) 220 double 221 gen_real2() 222 { 223 return genrand() / 4294967295.0; 224 } 225 226 // (0,1) 227 double 228 gen_real3() 229 { 230 return ((double)genrand() + 0.5) / 4294967296.0; 231 } 232 233 public: 234 void serialize(const std::string &base, std::ostream &os); 235 void unserialize(const std::string &base, Checkpoint *cp, 236 const std::string §ion); 237}; 238 239extern Random random_mt; 240 241#endif // __BASE_RANDOM_HH__ 242