Skip to content

Commit b06fe4b

Browse files
authored
change __common_domain_t to always check for convertibility to default_domain (#2022)
* change `__common_domain_t` to always check for convertibility to `default_domain`
1 parent efb7e42 commit b06fe4b

4 files changed

Lines changed: 73 additions & 5 deletions

File tree

examples/CMakeLists.txt

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,9 @@ function(def_example example)
2929
split(${example} target source)
3030
add_executable(${target} ${source})
3131
target_compile_options(${target} PUBLIC
32-
$<$<CXX_COMPILER_ID:GNU>:-Wno-maybe-uninitialized>) # warnings being emitted from stdlib headers, why?
32+
$<$<CXX_COMPILER_ID:GNU>:-Wno-maybe-uninitialized> # warnings being emitted from stdlib headers, why?
33+
$<$<CXX_COMPILER_ID:Clang>:-Wno-gnu-line-marker>
34+
)
3335
target_link_libraries(${target}
3436
PRIVATE STDEXEC::stdexec
3537
stdexec_executable_flags

include/stdexec/__detail/__domain.hpp

Lines changed: 17 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -151,10 +151,23 @@ namespace STDEXEC
151151

152152
// Common domain for a set of domains
153153
template <class... _Domains>
154-
struct __common_domain
154+
constexpr auto __common_domain_fn() noexcept
155155
{
156-
using __t = __minvoke<__mtry_catch_q<std::common_type_t, __qq<__make_domain_t>>, _Domains...>;
157-
};
156+
if constexpr (__minvocable_q<std::common_type_t, _Domains...>)
157+
{
158+
return std::common_type_t<_Domains...>{};
159+
}
160+
// NOT TO SPEC: If each domain in Domains... is convertible to default_domain, then
161+
// the common domain is default_domain.
162+
else if constexpr (__minvocable_q<std::common_type_t, default_domain, _Domains...>)
163+
{
164+
return std::common_type_t<default_domain, _Domains...>{};
165+
}
166+
else
167+
{
168+
return __make_domain_t<_Domains...>{};
169+
}
170+
}
158171
} // namespace __detail
159172

160173
////////////////////////////////////////////////////////////////////////////////////////////////
@@ -169,7 +182,7 @@ namespace STDEXEC
169182
using __completion_domain_of_t = __completion_domain_t<_Tag, env_of_t<_Sender>, _Env const &...>;
170183

171184
template <class... _Domains>
172-
using __common_domain_t = __t<__detail::__common_domain<_Domains...>>;
185+
using __common_domain_t = decltype(__detail::__common_domain_fn<_Domains...>());
173186

174187
template <class _Domain>
175188
using __ensure_valid_domain_t = __unless_one_of_t<_Domain, indeterminate_domain<>>;

test/CMakeLists.txt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,7 @@ set(stdexec_test_sources
7070
stdexec/algos/consumers/test_sync_wait.cpp
7171
stdexec/algos/consumers/test_spawn.cpp
7272
stdexec/detail/test_any.cpp
73+
stdexec/detail/test_common_domain.cpp
7374
stdexec/detail/test_completion_signatures.cpp
7475
stdexec/detail/test_demangle.cpp
7576
stdexec/detail/test_utility.cpp
@@ -99,6 +100,7 @@ target_compile_definitions(common_test_settings INTERFACE
99100
target_compile_options(common_test_settings INTERFACE
100101
$<$<CXX_COMPILER_ID:MSVC>:/wd4714> # function marked as __forceinline not inlined
101102
$<$<CXX_COMPILER_ID:GNU>:-Wno-maybe-uninitialized> # warnings being emitted from stdlib headers, why?
103+
$<$<CXX_COMPILER_ID:Clang>:-Wno-gnu-line-marker>
102104
)
103105
target_link_libraries(common_test_settings INTERFACE $<TARGET_NAME_IF_EXISTS:TBB::tbb>)
104106
# target_compile_definitions(
Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
/*
2+
* Copyright (c) 2022 Lucian Radu Teodorescu
3+
*
4+
* Licensed under the Apache License Version 2.0 with LLVM Exceptions
5+
* (the "License"); you may not use this file except in compliance with
6+
* the License. You may obtain a copy of the License at
7+
*
8+
* https://llvm.org/LICENSE.txt
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
#include <catch2/catch_all.hpp>
18+
#include <stdexec/execution.hpp>
19+
20+
#include <test_common/receivers.hpp>
21+
22+
namespace ex = STDEXEC;
23+
24+
namespace
25+
{
26+
struct gpu_domain
27+
{};
28+
29+
struct thread_pool_domain : ex::default_domain
30+
{};
31+
32+
struct parallel_runtime_domain : ex::default_domain
33+
{};
34+
35+
template <class... Domains>
36+
using common_domain_t = ex::__common_domain_t<Domains...>;
37+
38+
TEST_CASE("finding common domains", "[detail][domain]")
39+
{
40+
using common1 = common_domain_t<gpu_domain, gpu_domain>;
41+
STATIC_REQUIRE(std::same_as<common1, gpu_domain>);
42+
43+
using common2 = common_domain_t<thread_pool_domain, parallel_runtime_domain>;
44+
STATIC_REQUIRE(std::same_as<common2, ex::default_domain>);
45+
46+
using common3 = common_domain_t<gpu_domain, thread_pool_domain>;
47+
STATIC_REQUIRE(
48+
std::same_as<common3, ex::indeterminate_domain<gpu_domain, thread_pool_domain>>
49+
|| std::same_as<common3, ex::indeterminate_domain<thread_pool_domain, gpu_domain>>);
50+
}
51+
} // namespace

0 commit comments

Comments
 (0)