Sese Framework  3.0.0
A cross-platform framework
Loading...
Searching...
No Matches
Async.h
Go to the documentation of this file.
1// Copyright 2024 libsese
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
19
20#pragma once
21
23
24#include <coroutine>
25
26namespace sese {
27
29public:
31 public:
33 std::suspend_never initial_suspend() { return {}; }
34 std::suspend_never final_suspend() noexcept { return {}; }
36 void return_void() {}
37 };
38};
39
40class UseCoroutine {};
41
42template<class T>
44public:
45 explicit FutureAwaiter(std::shared_future<T> future) : future(future) {}
46
47 [[nodiscard]] bool await_ready() noexcept {
48 return future.wait_for(std::chrono::seconds(0)) == std::future_status::ready;
49 }
50
51 void await_suspend(std::coroutine_handle<> handle) noexcept {
52 future.wait();
53 handle.resume();
54 }
55
56 T await_resume() noexcept {
57 return future.get();
58 }
59
60private:
61 std::shared_future<T> future;
62};
63
68template<class RETURN_TYPE>
69std::shared_future<RETURN_TYPE> async(const std::function<RETURN_TYPE()> &task) noexcept;
70
75template<class RETURN_TYPE>
76auto async(UseCoroutine, const std::function<RETURN_TYPE()> &task) noexcept {
77 return FutureAwaiter(async<>(task));
78}
79
85template<class RETURN_TYPE>
86std::shared_future<RETURN_TYPE> async(ThreadPool &pool, const std::function<RETURN_TYPE()> &task) noexcept;
87
93template<class RETURN_TYPE>
94auto async(UseCoroutine, ThreadPool &pool, const std::function<RETURN_TYPE()> &task) noexcept {
95 return FutureAwaiter(async(pool, task));
96}
97
102template<class RETURN_TYPE>
103std::shared_future<RETURN_TYPE> asyncWithGlobalPool(const std::function<RETURN_TYPE()> &task) noexcept;
104
109template<class RETURN_TYPE>
110auto asyncWithGlobalPool(UseCoroutine, const std::function<RETURN_TYPE()> &task) noexcept {
112}
113
114} // namespace sese
115
116template<class RETURN_TYPE>
117std::shared_future<RETURN_TYPE> sese::async(const std::function<RETURN_TYPE()> &task) noexcept {
118 std::packaged_task<RETURN_TYPE()> packaged_task(task);
119 std::shared_future<RETURN_TYPE> future(packaged_task.get_future());
120
121 std::thread(
122 [&](std::packaged_task<RETURN_TYPE()> task) {
123 task();
124 },
125 std::move(packaged_task)
126 )
127 .detach();
128
129 return future;
130}
131
132template<class RETURN_TYPE>
133std::shared_future<RETURN_TYPE> sese::async(ThreadPool &pool, const std::function<RETURN_TYPE()> &task) noexcept {
134 return pool.postTask<RETURN_TYPE>(task);
135}
136
137template<class RETURN_TYPE>
138std::shared_future<RETURN_TYPE> sese::asyncWithGlobalPool(const std::function<RETURN_TYPE()> &task) noexcept {
139 return GlobalThreadPool::postTask<RETURN_TYPE>(task);
140}