Skip to content

Commit 515fd33

Browse files
committed
Improve test stability
Signed-off-by: Isaev, Ilya <[email protected]>
1 parent 9d507ca commit 515fd33

File tree

1 file changed

+67
-31
lines changed

1 file changed

+67
-31
lines changed

test/tbb/test_parallel_phase.cpp

+67-31
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,8 @@
1616

1717
#define TBB_PREVIEW_PARALLEL_PHASE 1
1818

19+
#include <chrono>
20+
1921
#include "common/test.h"
2022
#include "common/utils.h"
2123
#include "common/utils_concurrency_limit.h"
@@ -24,6 +26,15 @@
2426
#include "tbb/task_arena.h"
2527
#include "tbb/parallel_for.h"
2628

29+
void active_wait_for(std::chrono::microseconds duration) {
30+
for (auto t1 = std::chrono::steady_clock::now(), t2 = t1;
31+
std::chrono::duration_cast<std::chrono::microseconds>(t2 - t1) < duration;
32+
t2 = std::chrono::steady_clock::now())
33+
{
34+
utils::doDummyWork(100);
35+
}
36+
}
37+
2738
struct dummy_func {
2839
void operator()() const {
2940
}
@@ -66,7 +77,7 @@ std::size_t measure_median_start_time(tbb::task_arena* ta, const F1& start = F1{
6677
} else {
6778
work();
6879
}
69-
utils::doDummyWork(i*250);
80+
active_wait_for(std::chrono::microseconds(i));
7081
}
7182
return utils::median(longest_start_times.begin(), longest_start_times.end());
7283
}
@@ -101,7 +112,7 @@ class start_time_collection : public start_time_collection_base<start_time_colle
101112

102113
std::size_t measure_impl() {
103114
return measure_median_start_time(arena);
104-
};
115+
}
105116
};
106117

107118
class start_time_collection_phase_wrapped
@@ -116,7 +127,7 @@ class start_time_collection_phase_wrapped
116127
auto median_start_time = measure_median_start_time(arena);
117128
arena->end_parallel_phase(/*with_fast_leave*/true);
118129
return median_start_time;
119-
};
130+
}
120131
};
121132

122133
class start_time_collection_scoped_phase_wrapped
@@ -130,7 +141,7 @@ class start_time_collection_scoped_phase_wrapped
130141
tbb::task_arena::scoped_parallel_phase phase{*arena};
131142
auto median_start_time = measure_median_start_time(arena);
132143
return median_start_time;
133-
};
144+
}
134145
};
135146

136147
class start_time_collection_sequenced_phases
@@ -143,17 +154,35 @@ class start_time_collection_sequenced_phases
143154

144155
std::size_t measure_impl() {
145156
std::size_t median_start_time;
157+
utils::SpinBarrier barrier;
158+
auto body = [&] (std::size_t) {
159+
barrier.wait();
160+
};
146161
if (arena) {
162+
barrier.initialize(arena->max_concurrency());
147163
median_start_time = measure_median_start_time(arena,
148-
[this] { arena->start_parallel_phase(); },
149-
[this] { arena->end_parallel_phase(with_fast_leave); });
164+
[&] {
165+
std::size_t num_threads = arena->max_concurrency();
166+
arena->start_parallel_phase();
167+
arena->execute([&] {
168+
tbb::parallel_for(std::size_t(0), num_threads, body, tbb::static_partitioner{});
169+
});
170+
arena->end_parallel_phase(with_fast_leave);
171+
}
172+
);
150173
} else {
174+
barrier.initialize(tbb::this_task_arena::max_concurrency());
151175
median_start_time = measure_median_start_time(arena,
152-
[] { tbb::this_task_arena::start_parallel_phase(); },
153-
[this] { tbb::this_task_arena::end_parallel_phase(with_fast_leave); });
176+
[&] {
177+
std::size_t num_threads = tbb::this_task_arena::max_concurrency();
178+
tbb::this_task_arena::start_parallel_phase();
179+
tbb::parallel_for(std::size_t(0), num_threads, body, tbb::static_partitioner{});
180+
tbb::this_task_arena::end_parallel_phase(with_fast_leave);
181+
}
182+
);
154183
}
155184
return median_start_time;
156-
};
185+
}
157186

158187
public:
159188
start_time_collection_sequenced_phases(tbb::task_arena& ta, std::size_t ntrials, bool fast_leave = false) :
@@ -168,31 +197,38 @@ class start_time_collection_sequenced_phases
168197
class start_time_collection_sequenced_scoped_phases
169198
: public start_time_collection_base<start_time_collection_sequenced_scoped_phases>
170199
{
171-
using base = start_time_collection_base<start_time_collection_sequenced_scoped_phases>;
172-
friend base;
173-
174-
bool with_fast_leave;
175-
176-
std::size_t measure_impl() {
177-
tbb::task_arena::scoped_parallel_phase* phase = nullptr;
178-
auto median_start_time = measure_median_start_time(arena,
179-
[this, &phase] {
180-
phase = new tbb::task_arena::scoped_parallel_phase{*arena, with_fast_leave};
181-
},
182-
[&phase] {
183-
delete phase;
184-
});
185-
return median_start_time;
186-
};
200+
using base = start_time_collection_base<start_time_collection_sequenced_scoped_phases>;
201+
friend base;
202+
203+
bool with_fast_leave;
204+
205+
std::size_t measure_impl() {
206+
utils::SpinBarrier barrier{static_cast<std::size_t>(arena->max_concurrency())};
207+
auto body = [&] (std::size_t) {
208+
barrier.wait();
209+
};
210+
auto median_start_time = measure_median_start_time(arena,
211+
[&] {
212+
std::size_t num_threads = arena->max_concurrency();
213+
{
214+
tbb::task_arena::scoped_parallel_phase phase{*arena, with_fast_leave};
215+
arena->execute([&] {
216+
tbb::parallel_for(std::size_t(0), num_threads, body, tbb::static_partitioner{});
217+
});
218+
}
219+
}
220+
);
221+
return median_start_time;
222+
}
187223

188224
public:
189-
start_time_collection_sequenced_scoped_phases(tbb::task_arena& ta, std::size_t ntrials, bool fast_leave = false) :
190-
base(ta, ntrials), with_fast_leave(fast_leave)
191-
{}
225+
start_time_collection_sequenced_scoped_phases(tbb::task_arena& ta, std::size_t ntrials, bool fast_leave = false) :
226+
base(ta, ntrials), with_fast_leave(fast_leave)
227+
{}
192228

193-
explicit start_time_collection_sequenced_scoped_phases(std::size_t ntrials, bool fast_leave = false) :
194-
base(ntrials), with_fast_leave(fast_leave)
195-
{}
229+
explicit start_time_collection_sequenced_scoped_phases(std::size_t ntrials, bool fast_leave = false) :
230+
base(ntrials), with_fast_leave(fast_leave)
231+
{}
196232
};
197233

198234
//! \brief \ref interface \ref requirement

0 commit comments

Comments
 (0)