diff --git a/include/exec/function.hpp b/include/exec/function.hpp index f0ba12fd4..b4144bc0e 100644 --- a/include/exec/function.hpp +++ b/include/exec/function.hpp @@ -141,14 +141,14 @@ namespace experimental::execution using __receiver_t = __receiver_wrapper<__any_receiver_ref<_Sigs, _Queries>>; using __prop_t = __receiver_t::__prop_t; using __stop_token_t = stop_token_of_t>; - using __adaptee_t = decltype(__choose_frame_allocator(__declval<_Receiver const &>())); + using __adaptee_t = __result_of<__choose_frame_allocator, env_of_t<_Receiver>>; __memory_resource_adaptor_t<__adaptee_t> __resource_; __prop_t __env_; _any::_state<_Receiver, __stop_token_t> __rcvr_; explicit __opstate_base(_Receiver __rcvr) - : __resource_(__choose_frame_allocator(std::as_const(__rcvr))) + : __resource_(__choose_frame_allocator(STDEXEC::get_env(__rcvr))) , __env_(__make_env()) , __rcvr_(static_cast<_Receiver &&>(__rcvr)) {} diff --git a/test/exec/test_function.cpp b/test/exec/test_function.cpp index dad3f443d..c5543e6f1 100644 --- a/test/exec/test_function.cpp +++ b/test/exec/test_function.cpp @@ -21,7 +21,9 @@ #include +#include #include +#include namespace ex = STDEXEC; @@ -247,20 +249,44 @@ namespace #endif // !STDEXEC_NO_STDCPP_EXCEPTIONS() } + struct counting_resource : std::pmr::memory_resource + { + std::size_t count = 0; + + void *do_allocate(std::size_t bytes, std::size_t alignment) override + { + ++count; + return std::pmr::get_default_resource()->allocate(bytes, alignment); + } + + void do_deallocate(void *p, std::size_t bytes, std::size_t alignment) override + { + std::pmr::get_default_resource()->deallocate(p, bytes, alignment); + } + + bool do_is_equal(std::pmr::memory_resource const &other) const noexcept override + { + return &other == this; + } + }; + TEST_CASE("exec::function forwards get_frame_allocator", "[types][function]") { + counting_resource res; exec::function sndr( - []() noexcept + [&res]() noexcept { return ex::read_env(exec::get_frame_allocator) | ex::then( - [](auto alloc) noexcept + [&res](auto alloc) noexcept { - return std::same_as, decltype(alloc)>; + auto count = res.count; + alloc.deallocate(alloc.allocate(16), 16); + return res.count > count; }); }); - std::pmr::polymorphic_allocator alloc; + std::pmr::polymorphic_allocator alloc{&res}; auto [ret] = ex::sync_wait(std::move(sndr) | ex::write_env(ex::prop(exec::get_frame_allocator, alloc)))