Intel(R) Threading Building Blocks Doxygen Documentation  version 4.2.3
tbb_misc.h
Go to the documentation of this file.
1 /*
2  Copyright (c) 2005-2019 Intel Corporation
3 
4  Licensed under the Apache License, Version 2.0 (the "License");
5  you may not use this file except in compliance with the License.
6  You may obtain a copy of the License at
7 
8  http://www.apache.org/licenses/LICENSE-2.0
9 
10  Unless required by applicable law or agreed to in writing, software
11  distributed under the License is distributed on an "AS IS" BASIS,
12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  See the License for the specific language governing permissions and
14  limitations under the License.
15 */
16 
17 #ifndef _TBB_tbb_misc_H
18 #define _TBB_tbb_misc_H
19 
20 #include "tbb/tbb_stddef.h"
21 #include "tbb/tbb_machine.h"
22 #include "tbb/atomic.h" // For atomic_xxx definitions
23 
24 #if __linux__ || __FreeBSD__
25 #include <sys/param.h> // __FreeBSD_version
26 #if __FreeBSD_version >= 701000
27 #include <sys/cpuset.h>
28 #endif
29 #endif
30 
31 // Does the operating system have a system call to pin a thread to a set of OS processors?
32 #define __TBB_OS_AFFINITY_SYSCALL_PRESENT ((__linux__ && !__ANDROID__) || (__FreeBSD_version >= 701000))
33 // On IBM* Blue Gene* CNK nodes, the affinity API has restrictions that prevent its usability for TBB,
34 // and also sysconf(_SC_NPROCESSORS_ONLN) already takes process affinity into account.
35 #define __TBB_USE_OS_AFFINITY_SYSCALL (__TBB_OS_AFFINITY_SYSCALL_PRESENT && !__bg__)
36 
37 namespace tbb {
38 namespace internal {
39 
40 const size_t MByte = 1024*1024;
41 
42 #if __TBB_WIN8UI_SUPPORT && (_WIN32_WINNT < 0x0A00)
43 // In Win8UI mode (Windows 8 Store* applications), TBB uses a thread creation API
44 // that does not allow to specify the stack size.
45 // Still, the thread stack size value, either explicit or default, is used by the scheduler.
46 // So here we set the default value to match the platform's default of 1MB.
47 const size_t ThreadStackSize = 1*MByte;
48 #else
49 const size_t ThreadStackSize = (sizeof(uintptr_t) <= 4 ? 2 : 4 )*MByte;
50 #endif
51 
52 #ifndef __TBB_HardwareConcurrency
53 
56 
57 #else
58 
59 inline int AvailableHwConcurrency() {
60  int n = __TBB_HardwareConcurrency();
61  return n > 0 ? n : 1; // Fail safety strap
62 }
63 #endif /* __TBB_HardwareConcurrency */
64 
65 
66 #if _WIN32||_WIN64
67 
69 
70 int NumberOfProcessorGroups();
71 
73 int FindProcessorGroupIndex ( int processorIndex );
74 
76 void MoveThreadIntoProcessorGroup( void* hThread, int groupIndex );
77 
78 #endif /* _WIN32||_WIN64 */
79 
81 void handle_win_error( int error_code );
82 
84 void PrintVersion();
85 
87 void PrintExtraVersionInfo( const char* category, const char* format, ... );
88 
90 void PrintRMLVersionInfo( void* arg, const char* server_info );
91 
92 // For TBB compilation only; not to be used in public headers
93 #if defined(min) || defined(max)
94 #undef min
95 #undef max
96 #endif
97 
99 
102 template<typename T>
103 T min ( const T& val1, const T& val2 ) {
104  return val1 < val2 ? val1 : val2;
105 }
106 
108 
111 template<typename T>
112 T max ( const T& val1, const T& val2 ) {
113  return val1 < val2 ? val2 : val1;
114 }
115 
117 template<int > struct int_to_type {};
118 
119 //------------------------------------------------------------------------
120 // FastRandom
121 //------------------------------------------------------------------------
122 
124 unsigned GetPrime ( unsigned seed );
125 
127 
128 class FastRandom {
129 private:
130 #if __TBB_OLD_PRIMES_RNG
131  unsigned x, a;
132  static const unsigned c = 1;
133 #else
134  unsigned x, c;
135  static const unsigned a = 0x9e3779b1; // a big prime number
136 #endif //__TBB_OLD_PRIMES_RNG
137 public:
139  unsigned short get() {
140  return get(x);
141  }
143  unsigned short get( unsigned& seed ) {
144  unsigned short r = (unsigned short)(seed>>16);
145  __TBB_ASSERT(c&1, "c must be odd for big rng period");
146  seed = seed*a+c;
147  return r;
148  }
150  FastRandom( void* unique_ptr ) { init(uintptr_t(unique_ptr)); }
151  FastRandom( uint32_t seed) { init(seed); }
152  FastRandom( uint64_t seed) { init(seed); }
153  template <typename T>
154  void init( T seed ) {
155  init(seed,int_to_type<sizeof(seed)>());
156  }
157  void init( uint64_t seed , int_to_type<8> ) {
158  init(uint32_t((seed>>32)+seed), int_to_type<4>());
159  }
160  void init( uint32_t seed, int_to_type<4> ) {
161 #if __TBB_OLD_PRIMES_RNG
162  x = seed;
163  a = GetPrime( seed );
164 #else
165  // threads use different seeds for unique sequences
166  c = (seed|1)*0xba5703f5; // c must be odd, shuffle by a prime number
167  x = c^(seed>>1); // also shuffle x for the first get() invocation
168 #endif
169  }
170 };
171 
172 //------------------------------------------------------------------------
173 // Atomic extensions
174 //------------------------------------------------------------------------
175 
177 
178 template<typename T1, typename T2, class Pred>
179 T1 atomic_update ( tbb::atomic<T1>& dst, T2 newValue, Pred compare ) {
180  T1 oldValue = dst;
181  while ( compare(oldValue, newValue) ) {
182  if ( dst.compare_and_swap((T1)newValue, oldValue) == oldValue )
183  break;
184  oldValue = dst;
185  }
186  return oldValue;
187 }
188 
195 };
196 
198 
205 template <typename F>
206 void atomic_do_once ( const F& initializer, atomic<do_once_state>& state ) {
207  // tbb::atomic provides necessary acquire and release fences.
208  // The loop in the implementation is necessary to avoid race when thread T2
209  // that arrived in the middle of initialization attempt by another thread T1
210  // has just made initialization possible.
211  // In such a case T2 has to rely on T1 to initialize, but T1 may already be past
212  // the point where it can recognize the changed conditions.
213  while ( state != do_once_executed ) {
214  if( state == do_once_uninitialized ) {
216  run_initializer( initializer, state );
217  break;
218  }
219  }
221  }
222 }
223 
224 // Run the initializer which can not fail
225 inline void run_initializer( void (*f)(), atomic<do_once_state>& state ) {
226  f();
227  state = do_once_executed;
228 }
229 
230 // Run the initializer which can require repeated call
231 inline void run_initializer( bool (*f)(), atomic<do_once_state>& state ) {
232  state = f() ? do_once_executed : do_once_uninitialized;
233 }
234 
235 #if __TBB_USE_OS_AFFINITY_SYSCALL
236  #if __linux__
237  typedef cpu_set_t basic_mask_t;
238  #elif __FreeBSD_version >= 701000
239  typedef cpuset_t basic_mask_t;
240  #else
241  #error affinity_helper is not implemented in this OS
242  #endif
243  class affinity_helper : no_copy {
244  basic_mask_t* threadMask;
245  int is_changed;
246  public:
247  affinity_helper() : threadMask(NULL), is_changed(0) {}
248  ~affinity_helper();
249  void protect_affinity_mask( bool restore_process_mask );
250  void dismiss();
251  };
252  void destroy_process_mask();
253 #else
255  public:
256  void protect_affinity_mask( bool ) {}
257  void dismiss() {}
258  };
259  inline void destroy_process_mask(){}
260 #endif /* __TBB_USE_OS_AFFINITY_SYSCALL */
261 
262 bool cpu_has_speculation();
264 void fix_broken_rethrow();
265 
266 } // namespace internal
267 } // namespace tbb
268 
269 #endif /* _TBB_tbb_misc_H */
const size_t ThreadStackSize
Definition: tbb_misc.h:49
static const unsigned a
Definition: tbb_misc.h:135
A fast random number generator.
Definition: tbb_misc.h:128
Primary template for atomic.
Definition: atomic.h:403
FastRandom(uint64_t seed)
Definition: tbb_misc.h:152
T1 atomic_update(tbb::atomic< T1 > &dst, T2 newValue, Pred compare)
Atomically replaces value of dst with newValue if they satisfy condition of compare predicate.
Definition: tbb_misc.h:179
A thread is executing associated do-once routine.
Definition: tbb_misc.h:192
void atomic_do_once(const F &initializer, atomic< do_once_state > &state)
One-time initialization function.
Definition: tbb_misc.h:206
Base class for types that should not be copied or assigned.
Definition: tbb_stddef.h:331
#define __TBB_ASSERT(predicate, comment)
No-op version of __TBB_ASSERT.
Definition: tbb_stddef.h:165
unsigned short get(unsigned &seed)
Get a random number for the given seed; update the seed for next use.
Definition: tbb_misc.h:143
void PrintVersion()
Prints TBB version information on stderr.
Definition: tbb_misc.cpp:193
void run_initializer(void(*f)(), atomic< do_once_state > &state)
Definition: tbb_misc.h:225
The graph class.
Utility helper structure to ease overload resolution.
Definition: tbb_misc.h:117
#define __TBB_HardwareConcurrency()
Definition: macos_common.h:39
void init(uint64_t seed, int_to_type< 8 >)
Definition: tbb_misc.h:157
void destroy_process_mask()
Definition: tbb_misc.h:259
T min(const T &val1, const T &val2)
Utility template function returning lesser of the two values.
Definition: tbb_misc.h:103
void init(uint32_t seed, int_to_type< 4 >)
Definition: tbb_misc.h:160
FastRandom(void *unique_ptr)
Construct a random number generator.
Definition: tbb_misc.h:150
unsigned short get()
Get a random number.
Definition: tbb_misc.h:139
do_once_state
One-time initialization states.
Definition: tbb_misc.h:190
void PrintRMLVersionInfo(void *arg, const char *server_info)
A callback routine to print RML version information on stderr.
Definition: tbb_misc.cpp:209
void spin_wait_while_eq(const volatile T &location, U value)
Spin WHILE the value of the variable is equal to a given value.
Definition: tbb_machine.h:391
T max(const T &val1, const T &val2)
Utility template function returning greater of the two values.
Definition: tbb_misc.h:112
Do-once routine has been executed.
Definition: tbb_misc.h:193
void fix_broken_rethrow()
Definition: tbb_misc.cpp:184
FastRandom(uint32_t seed)
Definition: tbb_misc.h:151
void handle_win_error(int error_code)
Throws std::runtime_error with what() returning error_code description prefixed with aux_info.
bool cpu_has_speculation()
check for transaction support.
Definition: tbb_misc.cpp:217
void PrintExtraVersionInfo(const char *category, const char *format,...)
Prints arbitrary extra TBB version information on stderr.
Definition: tbb_misc.cpp:198
No execution attempts have been undertaken yet.
Definition: tbb_misc.h:191
bool gcc_rethrow_exception_broken()
Definition: tbb_misc.cpp:185
int AvailableHwConcurrency()
Returns maximal parallelism level supported by the current OS configuration.
value_type compare_and_swap(value_type value, value_type comparand)
Definition: atomic.h:285
unsigned GetPrime(unsigned seed)
const size_t MByte
Definition: tbb_misc.h:40

Copyright © 2005-2019 Intel Corporation. All Rights Reserved.

Intel, Pentium, Intel Xeon, Itanium, Intel XScale and VTune are registered trademarks or trademarks of Intel Corporation or its subsidiaries in the United States and other countries.

* Other names and brands may be claimed as the property of others.