VTK  9.3.1
vtkSMPToolsAPI.h
Go to the documentation of this file.
1 // SPDX-FileCopyrightText: Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
2 // SPDX-License-Identifier: BSD-3-Clause
3 
4 #ifndef vtkSMPToolsAPI_h
5 #define vtkSMPToolsAPI_h
6 
7 #include "vtkCommonCoreModule.h" // For export macro
8 #include "vtkNew.h"
9 #include "vtkObject.h"
10 #include "vtkSMP.h"
11 
12 #include <memory>
13 
15 #if VTK_SMP_ENABLE_SEQUENTIAL
16 #include "SMP/Sequential/vtkSMPToolsImpl.txx"
17 #endif
18 #if VTK_SMP_ENABLE_STDTHREAD
19 #include "SMP/STDThread/vtkSMPToolsImpl.txx"
20 #endif
21 #if VTK_SMP_ENABLE_TBB
22 #include "SMP/TBB/vtkSMPToolsImpl.txx"
23 #endif
24 #if VTK_SMP_ENABLE_OPENMP
25 #include "SMP/OpenMP/vtkSMPToolsImpl.txx"
26 #endif
27 
28 namespace vtk
29 {
30 namespace detail
31 {
32 namespace smp
33 {
34 VTK_ABI_NAMESPACE_BEGIN
35 
37 
38 class VTKCOMMONCORE_EXPORT vtkSMPToolsAPI
39 {
40 public:
41  //--------------------------------------------------------------------------------
42  static vtkSMPToolsAPI& GetInstance();
43 
44  //--------------------------------------------------------------------------------
45  BackendType GetBackendType();
46 
47  //--------------------------------------------------------------------------------
48  const char* GetBackend();
49 
50  //--------------------------------------------------------------------------------
51  bool SetBackend(const char* type);
52 
53  //--------------------------------------------------------------------------------
54  void Initialize(int numThreads = 0);
55 
56  //--------------------------------------------------------------------------------
57  int GetEstimatedNumberOfThreads();
58 
59  //------------------------------------------------------------------------------
60  void SetNestedParallelism(bool isNested);
61 
62  //--------------------------------------------------------------------------------
63  bool GetNestedParallelism();
64 
65  //--------------------------------------------------------------------------------
66  bool IsParallelScope();
67 
68  //--------------------------------------------------------------------------------
69  bool GetSingleThread();
70 
71  //--------------------------------------------------------------------------------
72  int GetInternalDesiredNumberOfThread() { return this->DesiredNumberOfThread; }
73 
74  //------------------------------------------------------------------------------
75  template <typename Config, typename T>
76  void LocalScope(Config const& config, T&& lambda)
77  {
78  const Config oldConfig(*this);
79  *this << config;
80  try
81  {
82  lambda();
83  }
84  catch (...)
85  {
86  *this << oldConfig;
87  throw;
88  }
89  *this << oldConfig;
90  }
91 
92  //--------------------------------------------------------------------------------
93  template <typename FunctorInternal>
94  void For(vtkIdType first, vtkIdType last, vtkIdType grain, FunctorInternal& fi)
95  {
96  switch (this->ActivatedBackend)
97  {
99  this->SequentialBackend->For(first, last, grain, fi);
100  break;
102  this->STDThreadBackend->For(first, last, grain, fi);
103  break;
104  case BackendType::TBB:
105  this->TBBBackend->For(first, last, grain, fi);
106  break;
107  case BackendType::OpenMP:
108  this->OpenMPBackend->For(first, last, grain, fi);
109  break;
110  }
111  }
112 
113  //--------------------------------------------------------------------------------
114  template <typename InputIt, typename OutputIt, typename Functor>
115  void Transform(InputIt inBegin, InputIt inEnd, OutputIt outBegin, Functor& transform)
116  {
117  switch (this->ActivatedBackend)
118  {
120  this->SequentialBackend->Transform(inBegin, inEnd, outBegin, transform);
121  break;
123  this->STDThreadBackend->Transform(inBegin, inEnd, outBegin, transform);
124  break;
125  case BackendType::TBB:
126  this->TBBBackend->Transform(inBegin, inEnd, outBegin, transform);
127  break;
128  case BackendType::OpenMP:
129  this->OpenMPBackend->Transform(inBegin, inEnd, outBegin, transform);
130  break;
131  }
132  }
133 
134  //--------------------------------------------------------------------------------
135  template <typename InputIt1, typename InputIt2, typename OutputIt, typename Functor>
136  void Transform(
137  InputIt1 inBegin1, InputIt1 inEnd, InputIt2 inBegin2, OutputIt outBegin, Functor& transform)
138  {
139  switch (this->ActivatedBackend)
140  {
142  this->SequentialBackend->Transform(inBegin1, inEnd, inBegin2, outBegin, transform);
143  break;
145  this->STDThreadBackend->Transform(inBegin1, inEnd, inBegin2, outBegin, transform);
146  break;
147  case BackendType::TBB:
148  this->TBBBackend->Transform(inBegin1, inEnd, inBegin2, outBegin, transform);
149  break;
150  case BackendType::OpenMP:
151  this->OpenMPBackend->Transform(inBegin1, inEnd, inBegin2, outBegin, transform);
152  break;
153  }
154  }
155 
156  //--------------------------------------------------------------------------------
157  template <typename Iterator, typename T>
158  void Fill(Iterator begin, Iterator end, const T& value)
159  {
160  switch (this->ActivatedBackend)
161  {
163  this->SequentialBackend->Fill(begin, end, value);
164  break;
166  this->STDThreadBackend->Fill(begin, end, value);
167  break;
168  case BackendType::TBB:
169  this->TBBBackend->Fill(begin, end, value);
170  break;
171  case BackendType::OpenMP:
172  this->OpenMPBackend->Fill(begin, end, value);
173  break;
174  }
175  }
176 
177  //--------------------------------------------------------------------------------
178  template <typename RandomAccessIterator>
179  void Sort(RandomAccessIterator begin, RandomAccessIterator end)
180  {
181  switch (this->ActivatedBackend)
182  {
184  this->SequentialBackend->Sort(begin, end);
185  break;
187  this->STDThreadBackend->Sort(begin, end);
188  break;
189  case BackendType::TBB:
190  this->TBBBackend->Sort(begin, end);
191  break;
192  case BackendType::OpenMP:
193  this->OpenMPBackend->Sort(begin, end);
194  break;
195  }
196  }
197 
198  //--------------------------------------------------------------------------------
199  template <typename RandomAccessIterator, typename Compare>
200  void Sort(RandomAccessIterator begin, RandomAccessIterator end, Compare comp)
201  {
202  switch (this->ActivatedBackend)
203  {
205  this->SequentialBackend->Sort(begin, end, comp);
206  break;
208  this->STDThreadBackend->Sort(begin, end, comp);
209  break;
210  case BackendType::TBB:
211  this->TBBBackend->Sort(begin, end, comp);
212  break;
213  case BackendType::OpenMP:
214  this->OpenMPBackend->Sort(begin, end, comp);
215  break;
216  }
217  }
218 
219  // disable copying
220  vtkSMPToolsAPI(vtkSMPToolsAPI const&) = delete;
221  void operator=(vtkSMPToolsAPI const&) = delete;
222 
223 private:
224  //--------------------------------------------------------------------------------
225  vtkSMPToolsAPI();
226 
227  //--------------------------------------------------------------------------------
228  void RefreshNumberOfThread();
229 
230  //--------------------------------------------------------------------------------
231  // This operator overload is used to unpack Config parameters and set them
232  // in vtkSMPToolsAPI (e.g `*this << config;`)
233  template <typename Config>
234  vtkSMPToolsAPI& operator<<(Config const& config)
235  {
236  this->Initialize(config.MaxNumberOfThreads);
237  this->SetBackend(config.Backend.c_str());
238  this->SetNestedParallelism(config.NestedParallelism);
239  return *this;
240  }
241 
245  BackendType ActivatedBackend = DefaultBackend;
246 
250  int DesiredNumberOfThread = 0;
251 
255 #if VTK_SMP_ENABLE_SEQUENTIAL
256  std::unique_ptr<vtkSMPToolsImpl<BackendType::Sequential>> SequentialBackend;
257 #else
258  std::unique_ptr<vtkSMPToolsDefaultImpl> SequentialBackend;
259 #endif
260 
264 #if VTK_SMP_ENABLE_STDTHREAD
265  std::unique_ptr<vtkSMPToolsImpl<BackendType::STDThread>> STDThreadBackend;
266 #else
267  std::unique_ptr<vtkSMPToolsDefaultImpl> STDThreadBackend;
268 #endif
269 
273 #if VTK_SMP_ENABLE_TBB
274  std::unique_ptr<vtkSMPToolsImpl<BackendType::TBB>> TBBBackend;
275 #else
276  std::unique_ptr<vtkSMPToolsDefaultImpl> TBBBackend;
277 #endif
278 
282 #if VTK_SMP_ENABLE_OPENMP
283  std::unique_ptr<vtkSMPToolsImpl<BackendType::OpenMP>> OpenMPBackend;
284 #else
285  std::unique_ptr<vtkSMPToolsDefaultImpl> OpenMPBackend;
286 #endif
287 };
288 
289 VTK_ABI_NAMESPACE_END
290 } // namespace smp
291 } // namespace detail
292 } // namespace vtk
293 
294 #endif
295 /* VTK-HeaderTest-Exclude: vtkSMPToolsAPI.h */
void Transform(InputIt inBegin, InputIt inEnd, OutputIt outBegin, Functor &transform)
void Sort(RandomAccessIterator begin, RandomAccessIterator end, Compare comp)
Specialization of tuple ranges and iterators for vtkAOSDataArrayTemplate.
int vtkIdType
Definition: vtkType.h:315
void For(vtkIdType first, vtkIdType last, vtkIdType grain, FunctorInternal &fi)
void Transform(InputIt1 inBegin1, InputIt1 inEnd, InputIt2 inBegin2, OutputIt outBegin, Functor &transform)
void LocalScope(Config const &config, T &&lambda)
void Sort(RandomAccessIterator begin, RandomAccessIterator end)
VTKCOMMONCORE_EXPORT ostream & operator<<(ostream &os, const vtkIndent &o)
void Fill(Iterator begin, Iterator end, const T &value)