DD4hep - The AIDA detector description toolkit for high energy physics experiments
DD4hep  Rev:Unversioneddirectory
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
Geant4EventSeed.h
Go to the documentation of this file.
1 // $Id: $
2 //==========================================================================
3 // AIDA Detector description implementation for LCD
4 //--------------------------------------------------------------------------
5 // Copyright (C) Organisation europeenne pour la Recherche nucleaire (CERN)
6 // All rights reserved.
7 //
8 // For the licensing terms see $DD4hepINSTALL/LICENSE.
9 // For the list of contributors see $DD4hepINSTALL/doc/CREDITS.
10 //
11 // Author : A.Sailer
12 //
13 //==========================================================================
14 #ifndef DD4HEP_DDG4_GEANT4EVENTSEED_H
15 #define DD4HEP_DDG4_GEANT4EVENTSEED_H
16 
17 // Framework include files
18 #include "DDG4/Geant4RunAction.h"
19 
21 namespace DD4hep {
22 
24  namespace Simulation {
25 
41 
42  protected:
43  unsigned int m_initialSeed;
44  unsigned int m_runID;
45  std::string m_type;
47  public:
49  Geant4EventSeed(Geant4Context*, const std::string& );
51  virtual ~Geant4EventSeed();
53  void begin(const G4Run*);
55  void beginEvent(const G4Event*);
56  };
57 
58  /*
59 
60  Hashing for random seed as used in Marlin EventSeeder processor
61 
62  Original source by Bob Jenkins
63 
64  http://www.burtleburtle.net/bob/hash/doobs.html
65 
66  Hash a variable-length key into a 32-bit value
67 
68  */
69 
70 #define hashsize(n) ( 1U << (n) )
71 #define hashmask(n) ( hashsize ( n ) - 1 )
72 
73 
74  /*
75  --------------------------------------------------------------------
76  mix -- mix 3 32-bit values reversibly.
77  For every delta with one or two bits set, and the deltas of all three
78  high bits or all three low bits, whether the original value of a,b,c
79  is almost all zero or is uniformly distributed,
80  * If mix() is run forward or backward, at least 32 bits in a,b,c
81  have at least 1/4 probability of changing.
82  * If mix() is run forward, every bit of c will change between 1/3 and
83  2/3 of the time. (Well, 22/100 and 78/100 for some 2-bit deltas.)
84  mix() was built out of 36 single-cycle latency instructions in a
85  structure that could supported 2x parallelism, like so:
86  a -= b;
87  a -= c; x = (c>>13);
88  b -= c; a ^= x;
89  b -= a; x = (a<<8);
90  c -= a; b ^= x;
91  c -= b; x = (b>>13);
92  ...
93  Unfortunately, superscalar Pentiums and Sparcs can't take advantage
94  of that parallelism. They've also turned some of those single-cycle
95  latency instructions into multi-cycle latency instructions. Still,
96  this is the fastest good hash I could find. There were about 2^^68
97  to choose from. I only looked at a billion or so.
98  --------------------------------------------------------------------
99  */
100 #define mix(a,b,c) \
101  { \
102  a -= b; a -= c; a ^= (c>>13); \
103  b -= c; b -= a; b ^= (a<<8); \
104  c -= a; c -= b; c ^= (b>>13); \
105  a -= b; a -= c; a ^= (c>>12); \
106  b -= c; b -= a; b ^= (a<<16); \
107  c -= a; c -= b; c ^= (b>>5); \
108  a -= b; a -= c; a ^= (c>>3); \
109  b -= c; b -= a; b ^= (a<<10); \
110  c -= a; c -= b; c ^= (b>>15); \
111  }
112 
113  /*
114  --------------------------------------------------------------------
115  jenkins_hash() -- hash a variable-length key into a 32-bit value
116  k : the key (the unaligned variable-length array of bytes)
117  len : the length of the key, counting by bytes
118  initval : can be any 4-byte value
119  Returns a 32-bit value. Every bit of the key affects every bit of
120  the return value. Every 1-bit and 2-bit delta achieves avalanche.
121  About 6*len+35 instructions.
122 
123  The best hash table sizes are powers of 2. There is no need to do
124  mod a prime (mod is sooo slow!). If you need less than 32 bits,
125  use a bitmask. For example, if you need only 10 bits, do
126  h = (h & hashmask(10));
127  In which case, the hash table should have hashsize(10) elements.
128 
129  If you are hashing n strings (ub1 **)k, do it like this:
130  for (i=0, h=0; i<n; ++i) h = hash( k[i], len[i], h);
131 
132  By Bob Jenkins, 1996. bob_jenkins@burtleburtle.net. You may use this
133  code any way you wish, private, educational, or commercial. It's free.
134 
135  See http://burtleburtle.net/bob/hash/evahash.html
136  Use for hash table lookup, or anything where one collision in 2^^32 is
137  acceptable. Do NOT use for cryptographic purposes.
138  --------------------------------------------------------------------
139  */
140  unsigned jenkins_hash ( unsigned char *k, unsigned length, unsigned initval )
141  {
142  unsigned a, b;
143  unsigned c = initval;
144  unsigned len = length;
145 
146  a = b = 0x9e3779b9;
147 
148  while ( len >= 12 ) {
149  a += ( k[0] + ( (unsigned)k[1] << 8 )
150  + ( (unsigned)k[2] << 16 )
151  + ( (unsigned)k[3] << 24 ) );
152  b += ( k[4] + ( (unsigned)k[5] << 8 )
153  + ( (unsigned)k[6] << 16 )
154  + ( (unsigned)k[7] << 24 ) );
155  c += ( k[8] + ( (unsigned)k[9] << 8 )
156  + ( (unsigned)k[10] << 16 )
157  + ( (unsigned)k[11] << 24 ) );
158 
159  mix ( a, b, c );
160 
161  k += 12;
162  len -= 12;
163  }
164 
165  c += length;
166 
167  switch ( len ) {
168  case 11: c += ( (unsigned)k[10] << 24 );
169  case 10: c += ( (unsigned)k[9] << 16 );
170  case 9 : c += ( (unsigned)k[8] << 8 );
171  /* First byte of c reserved for length */
172  case 8 : b += ( (unsigned)k[7] << 24 );
173  case 7 : b += ( (unsigned)k[6] << 16 );
174  case 6 : b += ( (unsigned)k[5] << 8 );
175  case 5 : b += k[4];
176  case 4 : a += ( (unsigned)k[3] << 24 );
177  case 3 : a += ( (unsigned)k[2] << 16 );
178  case 2 : a += ( (unsigned)k[1] << 8 );
179  case 1 : a += k[0];
180  }
181 
182  mix ( a, b, c );
183 
184  return c;
185  }
186 
188  unsigned int hash( unsigned int initialSeed, unsigned int eventNumber, unsigned int runNumber ){
189  unsigned int seed = 0;
190  unsigned char * c = (unsigned char *) &eventNumber ;
191  seed = jenkins_hash( c, sizeof eventNumber, seed) ;
192 
193  c = (unsigned char *) &runNumber ;
194  seed = jenkins_hash( c, sizeof runNumber, seed) ;
195 
196  c = (unsigned char *) &initialSeed ;
197  seed = jenkins_hash( c, sizeof initialSeed, seed) ;
198 
199  return seed;
200  }
201 
202  } // End namespace Simulation
203 } // End namespace DD4hep
204 
205 #endif // DD4HEP_DDG4_GEANT4EVENTSEED_H
virtual ~Geant4EventSeed()
Default destructor.
void begin(const G4Run *)
begin-of-run callback
#define mix(a, b, c)
Concrete basic implementation of the Geant4 run action base class.
void beginEvent(const G4Event *)
begin-of-event callback
unsigned int hash(unsigned int initialSeed, unsigned int eventNumber, unsigned int runNumber)
calculate hash from initialSeed, eventID and runID
unsigned jenkins_hash(unsigned char *k, unsigned length, unsigned initval)
Geant4EventSeed(Geant4Context *, const std::string &)
Standard constructor with initializing arguments.
Generic context to extend user, run and event information.