gnss-sim/3rdparty/boost/cobalt/wait_group.hpp

105 lines
2.9 KiB
C++
Raw Normal View History

2024-12-24 16:15:51 +00:00
// Copyright (c) 2022 Klemens D. Morgenstern
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
#ifndef BOOST_COBALT_WAIT_GROUP_HPP
#define BOOST_COBALT_WAIT_GROUP_HPP
#include <boost/cobalt/detail/wait_group.hpp>
namespace boost::cobalt
{
// tag::outline[]
struct wait_group
{
// create a wait_group
explicit
wait_group(asio::cancellation_type normal_cancel = asio::cancellation_type::none,
asio::cancellation_type exception_cancel = asio::cancellation_type::all);
// insert a task into the group
void push_back(promise<void> p);
// the number of tasks in the group
std::size_t size() const;
// remove completed tasks without waiting (i.e. zombie tasks)
std::size_t reap();
// cancel all tasks
void cancel(asio::cancellation_type ct = asio::cancellation_type::all);
// end::outline[]
/* tag::outline[]
// wait for one task to complete.
__wait_one_op__ wait_one();
// wait for all tasks to complete
__wait_op__ wait();
// wait for all tasks to complete
__wait_op__ operator co_await ();
// when used with `with` , this will receive the exception
// and wait for the completion
// if `ep` is set, this will use the `exception_cancel` level,
// otherwise the `normal_cancel` to cancel all promises.
__wait_op__ await_exit(std::exception_ptr ep);
end::outline[] */
auto wait_one() -> detail::race_wrapper
{
return detail::race_wrapper(waitables_);
}
detail::gather_wrapper wait()
{
return detail::gather_wrapper(waitables_);
}
detail::gather_wrapper::awaitable_type operator co_await ()
{
return detail::gather_wrapper(waitables_).operator co_await();
}
// swallow the exception here.
detail::gather_wrapper await_exit(std::exception_ptr ep)
{
auto ct = ep ? ct_except_ : ct_normal_;
if (ct != asio::cancellation_type::none)
for (auto & w : waitables_)
w.cancel(ct);
return detail::gather_wrapper(waitables_);
}
private:
std::list<promise<void>> waitables_;
asio::cancellation_type ct_normal_, ct_except_;
// tag::outline[]
};
// end::outline[]
inline wait_group::wait_group(
asio::cancellation_type normal_cancel,
asio::cancellation_type exception_cancel)
: ct_normal_(normal_cancel), ct_except_(exception_cancel) {}
inline
std::size_t wait_group::size() const {return waitables_.size();}
inline
std::size_t wait_group::reap()
{
return erase_if(waitables_, [](promise<void> & p) { return p.ready() && p;});
}
inline
void wait_group::cancel(asio::cancellation_type ct)
{
for (auto & w : waitables_)
w.cancel(ct);
}
inline
void wait_group::push_back(promise<void> p) { waitables_.push_back(std::move(p));}
}
#endif //BOOST_COBALT_WAIT_GROUP_HPP