VulkanRaytracingCycles 0.0.0
Cycles Render Engine With VulkanRaytracingShaderModules. ( Experiment , in progress)
harness_defs.h
Go to the documentation of this file.
1#pragma once
2/*
3 Copyright (c) 2005-2020 Intel Corporation
4
5 Licensed under the Apache License, Version 2.0 (the "License");
6 you may not use this file except in compliance with the License.
7 You may obtain a copy of the License at
8
9 http://www.apache.org/licenses/LICENSE-2.0
10
11 Unless required by applicable law or agreed to in writing, software
12 distributed under the License is distributed on an "AS IS" BASIS,
13 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 See the License for the specific language governing permissions and
15 limitations under the License.
16*/
17
18#ifndef __TBB_harness_defs_H
19#define __TBB_harness_defs_H
20
21#include "tbb/tbb_config.h"
22#if __FreeBSD__
23#include <sys/param.h> // for __FreeBSD_version
24#endif
25
26#if __TBB_TEST_PIC && !__PIC__
27#define __TBB_TEST_SKIP_PIC_MODE 1
28#else
29#define __TBB_TEST_SKIP_PIC_MODE 0
30#endif
31
32// no need to test GCC builtins mode on ICC
33#define __TBB_TEST_SKIP_GCC_BUILTINS_MODE ( __TBB_TEST_BUILTINS && (!__TBB_GCC_BUILTIN_ATOMICS_PRESENT || __INTEL_COMPILER) )
34
35#define __TBB_TEST_SKIP_ICC_BUILTINS_MODE ( __TBB_TEST_BUILTINS && !__TBB_ICC_BUILTIN_ATOMICS_PRESENT )
36
37#ifndef TBB_USE_GCC_BUILTINS
38 // Force TBB to use GCC intrinsics port, but not on ICC, as no need
39#define TBB_USE_GCC_BUILTINS ( __TBB_TEST_BUILTINS && __TBB_GCC_BUILTIN_ATOMICS_PRESENT && !__INTEL_COMPILER )
40#endif
41
42#ifndef TBB_USE_ICC_BUILTINS
43 // Force TBB to use ICC c++11 style intrinsics port
44#define TBB_USE_ICC_BUILTINS ( __TBB_TEST_BUILTINS && __TBB_ICC_BUILTIN_ATOMICS_PRESENT )
45#endif
46
47#if (_WIN32 && !__TBB_WIN8UI_SUPPORT) || (__linux__ && !__ANDROID__ && !__bg__) || __FreeBSD_version >= 701000
48#define __TBB_TEST_SKIP_AFFINITY 0
49#else
50#define __TBB_TEST_SKIP_AFFINITY 1
51#endif
52
53#if __INTEL_COMPILER
54#define __TBB_CPP11_REFERENCE_WRAPPER_PRESENT ( __INTEL_CXX11_MODE__ && __INTEL_COMPILER >= 1200 && \
55 ( _MSC_VER >= 1600 || __TBB_GLIBCXX_VERSION >= 40400 || ( _LIBCPP_VERSION && __cplusplus >= 201103L ) ) )
56#define __TBB_RANGE_BASED_FOR_PRESENT ( __INTEL_CXX11_MODE__ && __INTEL_COMPILER >= 1300 )
57#define __TBB_SCOPED_ENUM_PRESENT ( __INTEL_CXX11_MODE__ && __INTEL_COMPILER > 1100 )
58#elif __clang__
59#define __TBB_CPP11_REFERENCE_WRAPPER_PRESENT ( __cplusplus >= 201103L && (__TBB_GLIBCXX_VERSION >= 40400 || _LIBCPP_VERSION) )
60#define __TBB_RANGE_BASED_FOR_PRESENT ( __has_feature(__cxx_range_for) )
61#define __TBB_SCOPED_ENUM_PRESENT ( __has_feature(cxx_strong_enums) )
62#elif __GNUC__
63#define __TBB_CPP11_REFERENCE_WRAPPER_PRESENT ( __GXX_EXPERIMENTAL_CXX0X__ && __TBB_GCC_VERSION >= 40400 )
64#define __TBB_RANGE_BASED_FOR_PRESENT ( __GXX_EXPERIMENTAL_CXX0X__ && __TBB_GCC_VERSION >= 40500 )
65#define __TBB_SCOPED_ENUM_PRESENT ( __GXX_EXPERIMENTAL_CXX0X__ && __TBB_GCC_VERSION >= 40400 )
66#define __TBB_GCC_WARNING_IGNORED_ATTRIBUTES_PRESENT (__TBB_GCC_VERSION >= 60100)
67#elif _MSC_VER
68#define __TBB_CPP11_REFERENCE_WRAPPER_PRESENT ( _MSC_VER >= 1600 )
69#define __TBB_RANGE_BASED_FOR_PRESENT ( _MSC_VER >= 1700 )
70#define __TBB_SCOPED_ENUM_PRESENT ( _MSC_VER >= 1700 )
71#endif
72
73#define __TBB_CPP14_GENERIC_LAMBDAS_PRESENT (__cpp_generic_lambdas >= 201304 )
74
75#define __TBB_TEST_SKIP_LAMBDA (__TBB_ICC_13_0_CPP11_STDLIB_SUPPORT_BROKEN || !__TBB_CPP11_LAMBDAS_PRESENT)
76
77#if __GNUC__ && __ANDROID__
78// On Android* OS, GCC does not support _thread keyword
79#define __TBB_THREAD_LOCAL_VARIABLES_PRESENT 0
80#else
81#define __TBB_THREAD_LOCAL_VARIABLES_PRESENT 1
82#endif
83
84// ICC has a bug in assumptions of the modifications made via atomic pointer
85#define __TBB_ICC_BUILTIN_ATOMICS_POINTER_ALIASING_BROKEN (TBB_USE_ICC_BUILTINS && __INTEL_COMPILER < 1400 && __INTEL_COMPILER > 1200)
86
87// clang on Android/IA-32 fails on exception thrown from static move constructor
88#define __TBB_CPP11_EXCEPTION_IN_STATIC_TEST_BROKEN (__ANDROID__ && __SIZEOF_POINTER__==4 && __clang__)
89
90// MSVC 2013 is unable to properly resolve call to overloaded operator= with std::initializer_list argument for std::pair list elements
91// clang on Android/IA-32 fails on "std::vector<std::pair<int,int>> vd{{1,1},{1,1},{1,1}};" line in release mode
92#define __TBB_CPP11_INIT_LIST_TEST_BROKEN (_MSC_VER <= 1800 && _MSC_VER && !__INTEL_COMPILER) || (__ANDROID__ && __TBB_x86_32 && __clang__)
93// MSVC 2013 is unable to manage lifetime of temporary objects passed to a std::initializer_list constructor properly
94#define __TBB_CPP11_INIT_LIST_TEMP_OBJS_LIFETIME_BROKEN (_MSC_FULL_VER < 180030501 && _MSC_VER && !__INTEL_COMPILER)
95
96// Implementation of C++11 std::placeholders in libstdc++ coming with GCC prior to 4.5 reveals bug in Intel(R) C++ Compiler 13 causing "multiple definition" link errors.
97#define __TBB_CPP11_STD_PLACEHOLDERS_LINKAGE_BROKEN ((__INTEL_COMPILER == 1300 || __INTEL_COMPILER == 1310) && __GXX_EXPERIMENTAL_CXX0X__ && __GLIBCXX__ && __TBB_GLIBCXX_VERSION < 40500)
98
99// Intel C++ Compiler has an issue when a scoped enum with a specified underlying type has negative values.
100#define __TBB_ICC_SCOPED_ENUM_WITH_UNDERLYING_TYPE_NEGATIVE_VALUE_BROKEN ( _MSC_VER && !__TBB_DEBUG && __INTEL_COMPILER && __INTEL_COMPILER <= 1500 )
101// Intel C++ Compiler has an issue with __atomic_load_explicit from a scoped enum with a specified underlying type.
102#define __TBB_ICC_SCOPED_ENUM_WITH_UNDERLYING_TYPE_ATOMIC_LOAD_BROKEN ( TBB_USE_ICC_BUILTINS && !__TBB_DEBUG && __INTEL_COMPILER && __INTEL_COMPILER <= 1500 )
103
104// Unable to use constexpr member functions to initialize compile time constants
105#define __TBB_CONSTEXPR_MEMBER_FUNCTION_BROKEN (__INTEL_COMPILER == 1500)
106// Some versions of MSVC do not do compile-time initialization of static variables with constexpr constructors in debug mode
107#define __TBB_STATIC_CONSTEXPR_INIT_BROKEN (_MSC_VER >= 1900 && _MSC_VER <= 1914 && !__INTEL_COMPILER && _DEBUG)
108
109#if __GNUC__ && __ANDROID__
110#define __TBB_EXCEPTION_TYPE_INFO_BROKEN ( __TBB_GCC_VERSION < 40600 )
111#elif _MSC_VER
112#define __TBB_EXCEPTION_TYPE_INFO_BROKEN ( _MSC_VER < 1400 )
113#else
114#define __TBB_EXCEPTION_TYPE_INFO_BROKEN 0
115#endif
116
117// a function ptr cannot be converted to const T& template argument without explicit cast
118#define __TBB_FUNC_PTR_AS_TEMPL_PARAM_BROKEN ( ((__linux__ || __APPLE__) && __INTEL_COMPILER && __INTEL_COMPILER < 1100) || __SUNPRO_CC )
119
120#define __TBB_UNQUALIFIED_CALL_OF_DTOR_BROKEN (__GNUC__==3 && __GNUC_MINOR__<=3)
121
122#define __TBB_CAS_8_CODEGEN_BROKEN (__TBB_x86_32 && __PIC__ && __TBB_GCC_VERSION == 40102 && !__INTEL_COMPILER)
123
124#define __TBB_THROW_FROM_DTOR_BROKEN (__clang__ && __apple_build_version__ && __apple_build_version__ < 5000279)
125
126// std::uncaught_exception is broken on some version of stdlibc++ (it returns true with no active exception)
127#define __TBB_STD_UNCAUGHT_EXCEPTION_BROKEN (__TBB_GLIBCXX_VERSION == 40407)
128
129#if __TBB_LIBSTDCPP_EXCEPTION_HEADERS_BROKEN
130#define _EXCEPTION_PTR_H /* prevents exception_ptr.h inclusion */
131#define _GLIBCXX_NESTED_EXCEPTION_H /* prevents nested_exception.h inclusion */
132#endif
133
134// TODO: Investigate the cases that require this macro.
135#define __TBB_COMPLICATED_ADL_BROKEN ( __GNUC__ && __TBB_GCC_VERSION < 40400 )
136
137// Intel C++ Compiler fails to compile the comparison of tuples in some cases
138#if __INTEL_COMPILER && __INTEL_COMPILER < 1700
139#define __TBB_TUPLE_COMPARISON_COMPILATION_BROKEN (__TBB_GLIBCXX_VERSION >= 40800 || __MIC__)
140#endif
141
142// Intel C++ Compiler fails to compile std::reference in some cases
143#if __INTEL_COMPILER && __INTEL_COMPILER < 1600 || __INTEL_COMPILER == 1600 && __INTEL_COMPILER_UPDATE <= 1
144#define __TBB_REFERENCE_WRAPPER_COMPILATION_BROKEN (__TBB_GLIBCXX_VERSION >= 40800 && __TBB_GLIBCXX_VERSION <= 50101 || __MIC__)
145#endif
146
147// Intel C++ Compiler fails to generate non-throwing move members for a class inherited from template
148#define __TBB_NOTHROW_MOVE_MEMBERS_IMPLICIT_GENERATION_BROKEN \
149 (__INTEL_COMPILER>=1600 && __INTEL_COMPILER<=1900 || __INTEL_COMPILER==1500 && __INTEL_COMPILER_UPDATE>3)
150
151// std::is_copy_constructible<T>::value returns 'true' for non copyable type when MSVC compiler is used.
152#define __TBB_IS_COPY_CONSTRUCTIBLE_BROKEN ( _MSC_VER && (_MSC_VER <= 1700 || _MSC_VER <= 1800 && !__INTEL_COMPILER) )
153
154// GCC 4.7 and 4.8 might fail to take an address of overloaded template function (bug 57043)
155#if __GNUC__ && !__INTEL_COMPILER && !__clang__
156#define __TBB_GCC_OVERLOADED_TEMPLATE_FUNCTION_ADDRESS_BROKEN \
157 (__TBB_GCC_VERSION>=40700 && __TBB_GCC_VERSION<40704 || __TBB_GCC_VERSION>=40800 && __TBB_GCC_VERSION<40803 )
158#endif
159
160// Swapping of scoped_allocator_adaptors is broken on GCC 4.9 and lower and on Android for Windows
161// Allocator propagation into std::pair is broken for Apple clang, lower then 9.0
162// Compilation of <scoped_allocator> header is broken for Visual Studio 2017 with ICC 17.8
163#define __TBB_SCOPED_ALLOCATOR_BROKEN (__TBB_GCC_VERSION <= 50100 || (__APPLE__ && __TBB_CLANG_VERSION < 90000) || \
164 (__FreeBSD__ && __TBB_CLANG_VERSION <= 60000) || \
165 (__ANDROID__ && (_WIN32 || _WIN64)) || \
166 (_MSC_VER && _MSC_VER == 1912 && __INTEL_COMPILER == 1700))
167
168
169
170// The tuple-based tests with more inputs take a long time to compile. If changes
171// are made to the tuple implementation or any switch that controls it, or if testing
172// with a new platform implementation of std::tuple, the test should be compiled with
173// MAX_TUPLE_TEST_SIZE >= 10 (or the largest number of elements supported) to ensure
174// all tuple sizes are tested. Expect a very long compile time.
175#ifndef MAX_TUPLE_TEST_SIZE
176#if TBB_USE_DEBUG
177#define MAX_TUPLE_TEST_SIZE 3
178#else
179#define MAX_TUPLE_TEST_SIZE 5
180#endif
181#else
182#if _MSC_VER
183// test sizes <= 8 don't get "decorated name length exceeded" errors. (disable : 4503)
184#if MAX_TUPLE_TEST_SIZE > 8
185#undef MAX_TUPLE_TEST_SIZE
186#define MAX_TUPLE_TEST_SIZE 8
187#endif
188#endif
189#if MAX_TUPLE_TEST_SIZE > __TBB_VARIADIC_MAX
190#undef MAX_TUPLE_TEST_SIZE
191#define MAX_TUPLE_TEST_SIZE __TBB_VARIADIC_MAX
192#endif
193#endif
194
195#if __TBB_CPF_BUILD
196#ifndef TBB_PREVIEW_FLOW_GRAPH_FEATURES
197#define TBB_PREVIEW_FLOW_GRAPH_FEATURES 1
198#endif
199#ifndef TBB_PREVIEW_FLOW_GRAPH_TRACE
200#define TBB_PREVIEW_FLOW_GRAPH_TRACE 1
201#endif
202#ifndef TBB_PREVIEW_ALGORITHM_TRACE
203#define TBB_PREVIEW_ALGORITHM_TRACE 1
204#endif
205#ifndef TBB_DEPRECATED_LIMITER_NODE_CONSTRUCTOR
206#define TBB_DEPRECATED_LIMITER_NODE_CONSTRUCTOR 1
207#endif
208#endif
209
210
211
212#ifndef harness_assert_H
213#define harness_assert_H
214
215/*
216void ReportError(const char* filename, int line, const char* expression, const char* message);
217void ReportWarning(const char* filename, int line, const char* expression, const char* message);
218
219#define ASSERT_CUSTOM(p,message,file,line) ((p)?(void)0:ReportError(file,line,#p,message))
220#define ASSERT(p,message) ASSERT_CUSTOM(p,message,__FILE__,__LINE__)
221#define ASSERT_WARNING(p,message) ((p)?(void)0:ReportWarning(__FILE__,__LINE__,#p,message))
222*/
223
224#define ASSERT_CUSTOM(p,message,file,line)
225#define ASSERT(p,message)
226#define ASSERT_WARNING(p,message)
227
229template<typename T>
230void AssertSameType(const T& /*x*/, const T& /*y*/) {}
231
232#endif
233
234
235/*
236 Copyright (c) 2005-2020 Intel Corporation
237
238 Licensed under the Apache License, Version 2.0 (the "License");
239 you may not use this file except in compliance with the License.
240 You may obtain a copy of the License at
241
242 http://www.apache.org/licenses/LICENSE-2.0
243
244 Unless required by applicable law or agreed to in writing, software
245 distributed under the License is distributed on an "AS IS" BASIS,
246 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
247 See the License for the specific language governing permissions and
248 limitations under the License.
249*/
250
251// Just the tracing portion of the harness.
252//
253// This header defines TRACE and TRACENL macros, which use REPORT like syntax and
254// are useful for duplicating trace output to the standard debug output on Windows.
255// It is possible to add the ability of automatic extending messages with additional
256// info (file, line, function, time, thread ID, ...).
257//
258// Macros output nothing when test app runs in non-verbose mode (default).
259//
260
261#ifndef tbb_tests_harness_report_H
262#define tbb_tests_harness_report_H
263
264#if defined(MAX_TRACE_SIZE) && MAX_TRACE_SIZE < 1024
265#undef MAX_TRACE_SIZE
266#endif
267#ifndef MAX_TRACE_SIZE
268#define MAX_TRACE_SIZE 1024
269#endif
270
271#if __SUNPRO_CC
272#include <stdio.h>
273#else
274#include <cstdio>
275#endif
276
277#include <cstdarg>
278
279// Need to include "tbb/tbb_config.h" to obtain the definition of __TBB_DEFINE_MIC.
280#include "tbb/tbb_config.h"
281
282#if __TBB_DEFINE_MIC
283#include "harness_mic.h"
284#endif
285
286#ifdef HARNESS_INCOMPLETE_SOURCES
287#error Source files are not complete. Check the build environment
288#endif
289
290#if _MSC_VER
291#define snprintf _snprintf
292#if _MSC_VER<=1400
293#define vsnprintf _vsnprintf
294#endif
295#endif
296
297namespace Harness {
298 namespace internal {
299
300#ifndef TbbHarnessReporter
302 void Report(const char* msg) {
303 printf("%s", msg);
304 fflush(stdout);
305#ifdef _WINDOWS_
306 OutputDebugStringA(msg);
307#endif
308 }
309 }; // struct TbbHarnessReporter
310#endif /* !TbbHarnessReporter */
311
312 class Tracer {
313 int m_flags;
314 const char* m_file;
315 const char* m_func;
316 size_t m_line;
317
318 TbbHarnessReporter m_reporter;
319
320 public:
321 enum {
323 need_lf = 2
324 };
325
326 Tracer() : m_flags(0), m_file(NULL), m_func(NULL), m_line(0) {}
327
328 Tracer* set_trace_info(int flags, const char* file, size_t line, const char* func) {
329 m_flags = flags;
330 m_line = line;
331 m_file = file;
332 m_func = func;
333 return this;
334 }
335
336 void trace(const char* fmt, ...) {
337 char msg[MAX_TRACE_SIZE];
338 char msg_fmt_buf[MAX_TRACE_SIZE];
339 const char* msg_fmt = fmt;
340 if (m_flags & prefix) {
341 snprintf(msg_fmt_buf, MAX_TRACE_SIZE, "[%s] %s", m_func, fmt);
342 msg_fmt = msg_fmt_buf;
343 }
344 std::va_list argptr;
345 va_start(argptr, fmt);
346 int len = vsnprintf(msg, MAX_TRACE_SIZE, msg_fmt, argptr);
347 va_end(argptr);
348 if (m_flags & need_lf &&
349 len < MAX_TRACE_SIZE - 1 && msg_fmt[len - 1] != '\n')
350 {
351 msg[len] = '\n';
352 msg[len + 1] = 0;
353 }
354 m_reporter.Report(msg);
355 }
356 }; // class Tracer
357
358 static Tracer tracer;
359
360 template<int>
362 static bool first_call = false;
363 bool res = first_call;
364 first_call = true;
365 return res;
366 }
367
368 } // namespace internal
369} // namespace Harness
370
371#if defined(_MSC_VER) && _MSC_VER >= 1300 || defined(__GNUC__) || defined(__GNUG__)
372#define HARNESS_TRACE_ORIG_INFO __FILE__, __LINE__, __FUNCTION__
373#else
374#define HARNESS_TRACE_ORIG_INFO __FILE__, __LINE__, ""
375#define __FUNCTION__ ""
376#endif
377
378
380
381#define TRACE Harness::internal::tracer.set_trace_info(Harness::internal::Tracer::need_lf, HARNESS_TRACE_ORIG_INFO)->trace
382
384#define TRACENL Harness::internal::tracer.set_trace_info(0, HARNESS_TRACE_ORIG_INFO)->trace
385
387#define TRACEP Harness::internal::tracer.set_trace_info(Harness::internal::Tracer::prefix | \
388 Harness::internal::Tracer::need_lf, HARNESS_TRACE_ORIG_INFO)->trace
389
391
392#define REMARK !Verbose ? (void)0 : TRACENL
393
395
397#define REMARK_ONCE (!Verbose || Harness::internal::not_the_first_call<__LINE__>()) ? (void)0 : TRACE
398
400
401#define REPORT TRACENL
402
404
406#define REPORT_ONCE (Harness::internal::not_the_first_call<__LINE__>()) ? (void)0 : TRACENL
407
408#endif /* tbb_tests_harness_report_H */
409
410#define HARNESS_NO_ASSERT 1
411namespace Harness {
413 template<typename T> void suppress_unused_warning(const T&) {}
414
415 //TODO: unify with one in tbb::internal
417 template<int > struct int_to_type {};
418}
419
420const unsigned MByte = 1024 * 1024;
421
422
423
424
425#if !HARNESS_NO_ASSERT
426#include <exception> //for set_terminate
427
428#if TEST_USES_TBB
429#include <tbb/tbb_stddef.h> /*set_assertion_handler*/
430#endif
431
432struct InitReporter {
433 void (*default_terminate_handler)();
434 InitReporter() : default_terminate_handler(NULL) {
435#if TEST_USES_TBB
436#if TBB_USE_ASSERT
437 tbb::set_assertion_handler(ReportError);
438#endif
439 ASSERT_WARNING(TBB_INTERFACE_VERSION <= tbb::TBB_runtime_interface_version(), "runtime version mismatch");
440#endif
441#if TBB_USE_EXCEPTIONS
442 default_terminate_handler = std::set_terminate(handle_terminate);
443#endif
444 }
445 static void handle_terminate();
446};
447static InitReporter InitReportError;
448
449void InitReporter::handle_terminate() {
450 REPORT("std::terminate called.\n");
451 print_call_stack();
452 if (InitReportError.default_terminate_handler) {
453 InitReportError.default_terminate_handler();
454 }
455}
456
457typedef void (*test_error_extra_t)(void);
458static test_error_extra_t ErrorExtraCall;
460void SetHarnessErrorProcessing(test_error_extra_t extra_call) {
461 ErrorExtraCall = extra_call;
462}
463
465void ReportError(const char* filename, int line, const char* expression, const char* message) {
466 print_call_stack();
467#if __TBB_ICL_11_1_CODE_GEN_BROKEN
468 printf("%s:%d, assertion %s: %s\n", filename, line, expression, message ? message : "failed");
469#else
470 REPORT_FATAL_ERROR("%s:%d, assertion %s: %s\n", filename, line, expression, message ? message : "failed");
471#endif
472
473 if (ErrorExtraCall)
474 (*ErrorExtraCall)();
475 fflush(stdout); fflush(stderr);
476#if HARNESS_TERMINATE_ON_ASSERT
477 TerminateProcess(GetCurrentProcess(), 1);
478#elif HARNESS_EXIT_ON_ASSERT
479 exit(1);
480#elif HARNESS_CONTINUE_ON_ASSERT
481 // continue testing
482#elif _MSC_VER && _DEBUG
483 // aligned with tbb_assert_impl.h behavior
484 if (1 == _CrtDbgReport(_CRT_ASSERT, filename, line, NULL, "%s\r\n%s", expression, message ? message : ""))
485 _CrtDbgBreak();
486#else
487 abort();
488#endif /* HARNESS_EXIT_ON_ASSERT */
489}
491void ReportWarning(const char* filename, int line, const char* expression, const char* message) {
492 REPORT("Warning: %s:%d, assertion %s: %s\n", filename, line, expression, message ? message : "failed");
493}
494
495#else /* !HARNESS_NO_ASSERT */
496#ifndef ASSERT
497#define ASSERT(p,msg) (Harness::suppress_unused_warning(p), (void)0)
498#define ASSERT_WARNING(p,msg) (Harness::suppress_unused_warning(p), (void)0)
499#endif
500#endif /* !HARNESS_NO_ASSERT */
502class NoAssign {
503public:
504 void operator=(const NoAssign&) = delete;
505 NoAssign(const NoAssign&) = default;
506 NoAssign() = default;
507};
508
511public:
512 NoCopy(const NoCopy&) = delete;
513 NoCopy() = default;
514};
515
516
518template<typename Index, typename Body>
520public:
521 NativeParallelForTask(Index index_, const Body& body_) :
522 index(index_),
523 body(body_)
524 {}
525
527 void start() {
528#if _WIN32||_WIN64
529 unsigned thread_id;
530#if __TBB_WIN8UI_SUPPORT
531 std::thread* thread_tmp = new std::thread(thread_function, this);
532 thread_handle = thread_tmp->native_handle();
533 thread_id = 0;
534#else
535 unsigned stack_size = 0;
536#if HARNESS_THREAD_STACK_SIZE
537 stack_size = HARNESS_THREAD_STACK_SIZE;
538#endif
539 thread_handle = (HANDLE)_beginthreadex(NULL, stack_size, thread_function, this, 0, &thread_id);
540#endif
541 ASSERT(thread_handle != 0, "NativeParallelFor: _beginthreadex failed");
542#else
543#if __ICC==1100
544#pragma warning (push)
545#pragma warning (disable: 2193)
546#endif /* __ICC==1100 */
547 // Some machines may have very large hard stack limit. When the test is
548 // launched by make, the default stack size is set to the hard limit, and
549 // calls to pthread_create fail with out-of-memory error.
550 // Therefore we set the stack size explicitly (as for TBB worker threads).
551#if !defined(HARNESS_THREAD_STACK_SIZE)
552#if __i386__||__i386||__arm__
553 const size_t stack_size = 1 * MByte;
554#elif __x86_64__
555 const size_t stack_size = 2 * MByte;
556#else
557 const size_t stack_size = 4 * MByte;
558#endif
559#else
560 const size_t stack_size = HARNESS_THREAD_STACK_SIZE;
561#endif /* HARNESS_THREAD_STACK_SIZE */
562 pthread_attr_t attr_stack;
563 int status = pthread_attr_init(&attr_stack);
564 ASSERT(0 == status, "NativeParallelFor: pthread_attr_init failed");
565 status = pthread_attr_setstacksize(&attr_stack, stack_size);
566 ASSERT(0 == status, "NativeParallelFor: pthread_attr_setstacksize failed");
567 status = pthread_create(&thread_id, &attr_stack, thread_function, this);
568 ASSERT(0 == status, "NativeParallelFor: pthread_create failed");
569 pthread_attr_destroy(&attr_stack);
570#if __ICC==1100
571#pragma warning (pop)
572#endif
573#endif /* _WIN32||_WIN64 */
574 }
575
578#if _WIN32||_WIN64
579 DWORD status = WaitForSingleObjectEx(thread_handle, INFINITE, FALSE);
580 ASSERT(status != WAIT_FAILED, "WaitForSingleObject failed");
581 CloseHandle(thread_handle);
582#else
583 int status = pthread_join(thread_id, NULL);
584 ASSERT(!status, "pthread_join failed");
585#endif
586#if HARNESS_NO_ASSERT
587 (void)status;
588#endif
589 }
590
591private:
592#if _WIN32||_WIN64
593 HANDLE thread_handle;
594#else
595 pthread_t thread_id;
596#endif
597
599 const Index index;
600
602 const Body body;
603
604#if _WIN32||_WIN64
605 static unsigned __stdcall thread_function(void* object)
606#else
607 static void* thread_function(void* object)
608#endif
609 {
610 NativeParallelForTask& self = *static_cast<NativeParallelForTask*>(object);
611 (self.body)(self.index);
612#if HARNESS_TBBMALLOC_THREAD_SHUTDOWN && __TBB_SOURCE_DIRECTLY_INCLUDED && (_WIN32||_WIN64)
613 // in those cases can't release per-thread cache automatically,
614 // so do it manually
615 // TODO: investigate less-intrusive way to do it, for example via FLS keys
616 __TBB_mallocThreadShutdownNotification();
617#endif
618 return 0;
619 }
620};
621
622template<typename Index, typename Body>
623void NativeParallelFor(Index n, const Body& body) {
625
626 if (n > 0) {
627 // Allocate array to hold the tasks
628 task* array = static_cast<task*>(operator new(n * sizeof(task)));
629
630 // Construct the tasks
631 for (Index i = 0; i != n; ++i)
632 new(&array[i]) task(i, body);
633
634 // Start the tasks
635 for (Index i = 0; i != n; ++i)
636 array[i].start();
637
638 // Wait for the tasks to finish and destroy each one.
639 for (Index i = n; i; --i) {
640 array[i - 1].wait_to_finish();
641 array[i - 1].~task();
642 }
643
644 // Deallocate the task array
645 operator delete(array);
646 }
647}
648
649#endif /* __TBB_harness_defs_H */
Tracer * set_trace_info(int flags, const char *file, size_t line, const char *func)
Definition: harness_defs.h:328
void trace(const char *fmt,...)
Definition: harness_defs.h:336
For internal use by template function NativeParallelFor.
Definition: harness_defs.h:519
NativeParallelForTask(Index index_, const Body &body_)
Definition: harness_defs.h:521
void start()
Start task.
Definition: harness_defs.h:527
void wait_to_finish()
Wait for task to finish.
Definition: harness_defs.h:577
Base class for types that should not be assigned.
Definition: harness_defs.h:502
NoAssign()=default
void operator=(const NoAssign &)=delete
NoAssign(const NoAssign &)=default
Base class for types that should not be copied or assigned.
Definition: harness_defs.h:510
NoCopy()=default
NoCopy(const NoCopy &)=delete
#define MAX_TRACE_SIZE
Definition: harness_defs.h:268
void AssertSameType(const T &, const T &)
Compile-time error if x and y have different types.
Definition: harness_defs.h:230
#define ASSERT(p, message)
Definition: harness_defs.h:225
const unsigned MByte
Definition: harness_defs.h:420
#define REPORT
printf style reporting macro
Definition: harness_defs.h:401
#define ASSERT_WARNING(p, message)
Definition: harness_defs.h:226
void NativeParallelFor(Index n, const Body &body)
Definition: harness_defs.h:623
bool not_the_first_call()
Definition: harness_defs.h:361
void suppress_unused_warning(const T &)
Utility template function to prevent "unused" warnings by various compilers.
Definition: harness_defs.h:413
Utility helper structure to ease overload resolution.
Definition: harness_defs.h:417