7#ifndef PXR_BASE_WORK_LOOPS_H
8#define PXR_BASE_WORK_LOOPS_H
12#include "pxr/base/work/api.h"
15#include "pxr/base/work/impl.h"
20PXR_NAMESPACE_OPEN_SCOPE
23using Work_ErrorTransports = tbb::concurrent_vector<TfErrorTransport>;
26class Work_ErrorTransportTaskWrapper
29 Work_ErrorTransportTaskWrapper(
31 Work_ErrorTransports *errors)
35 template <
typename ... Args>
36 void operator()(Args&&... args)
const {
38 _callback(std::forward<Args>(args)...);
41 _errors->grow_by(1)->
swap(transport);
47 Work_ErrorTransports *_errors;
51class Work_ErrorTransportForEachTaskWrapper
54 Work_ErrorTransportForEachTaskWrapper(
56 Work_ErrorTransports *errors)
60 template <
typename Arg>
61 void operator()( Arg&& arg)
const {
63 _callback(std::forward<Arg>(arg));
66 _errors->grow_by(1)->
swap(transport);
72 Work_ErrorTransports *_errors;
91 std::forward<Fn>(fn)(0, n);
109template <
typename Fn>
118 PXR_WORK_IMPL_NAMESPACE_USING_DIRECTIVE;
119 Work_ErrorTransports errorTransports;
120 Work_ErrorTransportTaskWrapper<Fn> task(std::forward<Fn>(callback),
122 WorkImpl_ParallelForN(n, task, grainSize);
123 for (
auto &et: errorTransports) {
143template <
typename Fn>
163template <
typename RangeType,
typename Fn>
169 PXR_WORK_IMPL_NAMESPACE_USING_DIRECTIVE;
173#if defined WORK_IMPL_HAS_PARALLEL_FOR_TBB_RANGE
174 Work_ErrorTransports errorTransports;
175 Work_ErrorTransportTaskWrapper<Fn> task(std::forward<Fn>(callback),
177 WorkImpl_ParallelForTBBRange(range, task);
178 for (
auto &et: errorTransports) {
191 : _dispatcher(dispatcher)
192 , _range(std::move(range))
193 , _callback(callback) {}
195 void operator()()
const {
198 RangeType &leftRange = _range;
199 while (leftRange.is_divisible()) {
200 RangeType rightRange(leftRange, tbb::split());
201 _dispatcher.Run(_RangeTask(
202 _dispatcher, std::move(rightRange), _callback));
207 if (!leftRange.empty()) {
208 std::invoke(_callback, leftRange);
214 mutable RangeType _range;
219 RangeType range = range;
220 dispatcher.Run(_RangeTask(
221 dispatcher, range, std::forward<Fn>(callback)));
225 std::forward<Fn>(callback)(range);
241template <
typename InputIterator,
typename Fn>
244 InputIterator first, InputIterator last, Fn &&fn)
247 PXR_WORK_IMPL_NAMESPACE_USING_DIRECTIVE;
248 Work_ErrorTransports errorTransports;
249 Work_ErrorTransportForEachTaskWrapper<Fn>
250 task(std::forward<Fn>(fn), &errorTransports);
251 WorkImpl_ParallelForEach(first, last, task);
252 for (
auto &et: errorTransports) {
256 std::for_each(first, last, std::forward<Fn>(fn));
260PXR_NAMESPACE_CLOSE_SCOPE
Class used to record the end of the error-list.
TfErrorTransport Transport() const
Remove all errors in this mark fom the error system and return them in a TfErrorTransport.
bool IsClean() const
Return true if no new errors were posted in this thread since the last call to SetMark(),...
A facility for transporting errors from thread to thread.
void swap(TfErrorTransport &other)
Swap this TfErrorTransport's content with other.
A work dispatcher runs concurrent tasks.
void WorkParallelForTBBRange(const RangeType &range, Fn &&callback)
WorkParallelForTBBRange(const RangeType &r, Fn &&callback)
void WorkParallelForEach(InputIterator first, InputIterator last, Fn &&fn)
WorkParallelForEach(Iterator first, Iterator last, CallbackType callback)
void WorkParallelForN(size_t n, Fn &&callback, size_t grainSize)
WorkParallelForN(size_t n, CallbackType callback, size_t grainSize = 1)
void WorkSerialForN(size_t n, Fn &&fn)
WorkSerialForN(size_t n, CallbackType callback)
WORK_API bool WorkHasConcurrency()
Return true if WorkGetPhysicalConcurrencyLimit() returns a number greater than 1 and PXR_WORK_THREAD_...