summaryrefslogtreecommitdiff
path: root/src/mbgl/util/thread.hpp
diff options
context:
space:
mode:
authorJesse Crocker <jesse@gaiagps.com>2017-03-01 11:15:11 -0700
committerJesse Crocker <jesse@gaiagps.com>2017-03-01 11:15:11 -0700
commit9e8dc9a9e3e86adb9987ae69766cc42c7d9efece (patch)
treef5f0abd4d342c89ad0405d01969f9d6caecc1c90 /src/mbgl/util/thread.hpp
parent16fb0672e64a72b7400c321d55858b73cd5d8c3f (diff)
parentf28d75dccd9bf4a7615df87faccc5cf5eff8df89 (diff)
downloadqtlocation-mapboxgl-9e8dc9a9e3e86adb9987ae69766cc42c7d9efece.tar.gz
Merge remote-tracking branch 'origin/master' into feature/custom-vector-source
Diffstat (limited to 'src/mbgl/util/thread.hpp')
-rw-r--r--src/mbgl/util/thread.hpp45
1 files changed, 45 insertions, 0 deletions
diff --git a/src/mbgl/util/thread.hpp b/src/mbgl/util/thread.hpp
index b03c7f3e7c..184c6a8a12 100644
--- a/src/mbgl/util/thread.hpp
+++ b/src/mbgl/util/thread.hpp
@@ -1,5 +1,6 @@
#pragma once
+#include <cassert>
#include <future>
#include <thread>
#include <atomic>
@@ -9,6 +10,7 @@
#include <mbgl/util/run_loop.hpp>
#include <mbgl/util/thread_context.hpp>
#include <mbgl/util/platform.hpp>
+#include <mbgl/util/util.hpp>
namespace mbgl {
namespace util {
@@ -47,6 +49,8 @@ public:
// Invoke object->fn(args...) asynchronously, but wait for the result.
template <typename Fn, class... Args>
auto invokeSync(Fn fn, Args&&... args) {
+ assert(!paused);
+
using R = std::result_of_t<Fn(Object, Args&&...)>;
std::packaged_task<R ()> task(std::bind(fn, object, args...));
std::future<R> future = task.get_future();
@@ -54,7 +58,39 @@ public:
return future.get();
}
+ void pause() {
+ MBGL_VERIFY_THREAD(tid);
+
+ assert(!paused);
+
+ paused = std::make_unique<std::promise<void>>();
+ resumed = std::make_unique<std::promise<void>>();
+
+ auto pausing = paused->get_future();
+
+ loop->invoke([this] {
+ auto resuming = resumed->get_future();
+ paused->set_value();
+ resuming.get();
+ });
+
+ pausing.get();
+ }
+
+ void resume() {
+ MBGL_VERIFY_THREAD(tid);
+
+ assert(paused);
+
+ resumed->set_value();
+
+ resumed.reset();
+ paused.reset();
+ }
+
private:
+ MBGL_STORE_THREAD(tid);
+
Thread(const Thread&) = delete;
Thread(Thread&&) = delete;
Thread& operator=(const Thread&) = delete;
@@ -73,6 +109,9 @@ private:
std::promise<void> running;
std::promise<void> joinable;
+ std::unique_ptr<std::promise<void>> paused;
+ std::unique_ptr<std::promise<void>> resumed;
+
std::thread thread;
Object* object = nullptr;
@@ -119,6 +158,12 @@ void Thread<Object>::run(P&& params, std::index_sequence<I...>) {
template <class Object>
Thread<Object>::~Thread() {
+ MBGL_VERIFY_THREAD(tid);
+
+ if (paused) {
+ resume();
+ }
+
loop->stop();
joinable.set_value();
thread.join();