diff --git a/doc/configuration.dox b/doc/configuration.dox index 64e588d..ce7fb15 100644 --- a/doc/configuration.dox +++ b/doc/configuration.dox @@ -30,9 +30,10 @@ in order to change the libraries behaviour: | Preprocessor definition | Consequence | | ----------------------------------------- | --------------- | -| `CONTINUABLE_WITH_NO_EXCEPTIONS` | Exceptions are disabled and `std::error_condition` is used as \ref error_type . See \ref tutorial-chaining-continuables-fail for details. | +| `CONTINUABLE_WITH_NO_EXCEPTIONS` | Exceptions are disabled and `std::error_condition` is used as \ref error_type . See \ref tutorial-chaining-continuables-fail for details. | | `CONTINUABLE_WITH_CUSTOM_ERROR_TYPE` | Exceptions are disabled and the type defined by `CONTINUABLE_WITH_CUSTOM_ERROR_TYPE` is used as \ref error_type . See \ref tutorial-chaining-continuables-fail for details. | | `CONTINUABLE_WITH_UNHANDLED_EXCEPTIONS` | Allows unhandled exceptions in asynchronous call hierarchies. See \ref tutorial-chaining-continuables-fail for details. | +| `CONTINUABLE_WITH_CUSTOM_FINAL_CALLBACK` | Allows to customize the final callback which can be used to implement custom unhandled asynchronous exception handlers. | | `CONTINUABLE_WITH_EXPERIMENTAL_COROUTINE` | Enables support for experimental coroutines and `co_await` expressions. See \ref continuable_base::operator co_await() for details. | */ diff --git a/include/continuable/continuable-base.hpp b/include/continuable/continuable-base.hpp index 222ab39..9f88907 100644 --- a/include/continuable/continuable-base.hpp +++ b/include/continuable/continuable-base.hpp @@ -582,7 +582,7 @@ public: /// /// \since 1.0.0 void done() && { - detail::base::finalize_continuation(std::move(*this)); + detail::base::finalize_continuation(std::move(*this).finish()); } /// Materializes the continuation expression template and finishes diff --git a/include/continuable/detail/core/base.hpp b/include/continuable/detail/core/base.hpp index a9a10a1..3ac5c10 100644 --- a/include/continuable/detail/core/base.hpp +++ b/include/continuable/detail/core/base.hpp @@ -641,11 +641,9 @@ auto make_callback(Callback&& callback, Executor&& executor, std::forward(next_callback)}; } -// TODO fixate the args -/// Once this was a workaround for GCC bug: -/// https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64095 +/// Represents the last callback in the asynchronous continuation chain +template struct final_callback : util::non_copyable { - template void operator()(Args... /*args*/) && { } @@ -670,7 +668,6 @@ struct final_callback : util::non_copyable { #endif // CONTINUABLE_WITH_UNHANDLED_EXCEPTIONS } - template void set_value(Args... args) { std::move (*this)(std::forward(args)...); } @@ -876,10 +873,16 @@ auto chain_continuation(Continuation&& continuation, Callback&& callback, /// /// For example given: /// - Continuation: continuation<[](auto&& callback) { callback("hi"); }> -template -void finalize_continuation(Continuation&& continuation) { - invoke_continuation(std::forward(continuation), - callbacks::final_callback{}); +template +void finalize_continuation( + continuable_base>&& continuation) noexcept { +#ifdef CONTINUABLE_WITH_CUSTOM_FINAL_CALLBACK + invoke_continuation(std::move(continuation), + CONTINUABLE_WITH_CUSTOM_FINAL_CALLBACK{}); +#else // CONTINUABLE_WITH_CUSTOM_FINAL_CALLBACK + invoke_continuation(std::move(continuation), + callbacks::final_callback{}); +#endif // CONTINUABLE_WITH_CUSTOM_FINAL_CALLBACK } /// Deduces to a true type if the given callable data can be wrapped @@ -889,7 +892,8 @@ struct can_accept_continuation : std::false_type {}; template struct can_accept_continuation, Continuation> : traits::conjunction< - traits::is_invocable, + traits::is_invocable>, std::is_convertible< proxy_continuable, Continuation>, Data>> {};