diff options
author | John Firebaugh <john.firebaugh@gmail.com> | 2016-09-02 16:52:25 -0700 |
---|---|---|
committer | John Firebaugh <john.firebaugh@gmail.com> | 2016-09-08 16:36:47 -0700 |
commit | e4995e8d3a38dfd2ed64337e712ecf701af37454 (patch) | |
tree | 234490c1f4e93afb99738d6790be46ea1fe9c1c8 /include/mbgl/util/run_loop.hpp | |
parent | a85f7540c7f4ac289abba1dc3aa71058bc820b05 (diff) | |
download | qtlocation-mapboxgl-e4995e8d3a38dfd2ed64337e712ecf701af37454.tar.gz |
[core] Extract WorkTaskImpl from run_loop.hpp
Diffstat (limited to 'include/mbgl/util/run_loop.hpp')
-rw-r--r-- | include/mbgl/util/run_loop.hpp | 88 |
1 files changed, 5 insertions, 83 deletions
diff --git a/include/mbgl/util/run_loop.hpp b/include/mbgl/util/run_loop.hpp index 25f07c0312..af1053dfdc 100644 --- a/include/mbgl/util/run_loop.hpp +++ b/include/mbgl/util/run_loop.hpp @@ -47,11 +47,7 @@ public: // Invoke fn(args...) on this RunLoop. template <class Fn, class... Args> void invoke(Fn&& fn, Args&&... args) { - auto tuple = std::make_tuple(std::move(args)...); - auto task = std::make_shared<Invoker<Fn, decltype(tuple)>>( - std::move(fn), - std::move(tuple)); - + std::shared_ptr<WorkTask> task = WorkTask::make(std::forward<Fn>(fn), std::forward<Args>(args)...); push(task); } @@ -59,17 +55,8 @@ public: template <class Fn, class... Args> std::unique_ptr<AsyncRequest> invokeCancellable(Fn&& fn, Args&&... args) { - auto flag = std::make_shared<std::atomic<bool>>(); - *flag = false; - - auto tuple = std::make_tuple(std::move(args)...); - auto task = std::make_shared<Invoker<Fn, decltype(tuple)>>( - std::move(fn), - std::move(tuple), - flag); - + std::shared_ptr<WorkTask> task = WorkTask::make(std::forward<Fn>(fn), std::forward<Args>(args)...); push(task); - return std::make_unique<WorkRequest>(task); } @@ -77,32 +64,8 @@ public: template <class Fn, class Cb, class... Args> std::unique_ptr<AsyncRequest> invokeWithCallback(Fn&& fn, Cb&& callback, Args&&... args) { - auto flag = std::make_shared<std::atomic<bool>>(); - *flag = false; - - // Create a lambda L1 that invokes another lambda L2 on the current RunLoop R, that calls - // the callback C. Both lambdas check the flag before proceeding. L1 needs to check the flag - // because if the request was cancelled, then R might have been destroyed. L2 needs to check - // the flag because the request may have been cancelled after L2 was invoked but before it - // began executing. - auto after = [flag, current = RunLoop::Get(), callback1 = std::move(callback)] (auto&&... results1) { - if (!*flag) { - current->invoke([flag, callback2 = std::move(callback1)] (auto&&... results2) { - if (!*flag) { - callback2(std::move(results2)...); - } - }, std::move(results1)...); - } - }; - - auto tuple = std::make_tuple(std::move(args)..., after); - auto task = std::make_shared<Invoker<Fn, decltype(tuple)>>( - std::move(fn), - std::move(tuple), - flag); - + std::shared_ptr<WorkTask> task = WorkTask::makeWithCallback(std::forward<Fn>(fn), std::forward<Cb>(callback), std::forward<Args>(args)...); push(task); - return std::make_unique<WorkRequest>(task); } @@ -111,49 +74,6 @@ public: private: MBGL_STORE_THREAD(tid) - template <class F, class P> - class Invoker : public WorkTask { - public: - Invoker(F&& f, P&& p, std::shared_ptr<std::atomic<bool>> canceled_ = nullptr) - : canceled(std::move(canceled_)), - func(std::move(f)), - params(std::move(p)) { - } - - void operator()() override { - // Lock the mutex while processing so that cancel() will block. - std::lock_guard<std::recursive_mutex> lock(mutex); - if (!canceled || !*canceled) { - invoke(std::make_index_sequence<std::tuple_size<P>::value>{}); - } - } - - // If the task has not yet begun, this will cancel it. - // If the task is in progress, this will block until it completed. (Currently - // necessary because of shared state, but should be removed.) It will also - // cancel the after callback. - // If the task has completed, but the after callback has not executed, this - // will cancel the after callback. - // If the task has completed and the after callback has executed, this will - // do nothing. - void cancel() override { - std::lock_guard<std::recursive_mutex> lock(mutex); - *canceled = true; - } - - private: - template <std::size_t... I> - void invoke(std::index_sequence<I...>) { - func(std::move(std::get<I>(std::forward<P>(params)))...); - } - - std::recursive_mutex mutex; - std::shared_ptr<std::atomic<bool>> canceled; - - F func; - P params; - }; - using Queue = std::queue<std::shared_ptr<WorkTask>>; void push(std::shared_ptr<WorkTask>); @@ -181,3 +101,5 @@ private: } // namespace util } // namespace mbgl + +#include <mbgl/util/work_task_impl.hpp> |