Skip to content

when_all_with_variant with a sender with multiple value completions won't compile #1988

@dkolsen-pgi

Description

@dkolsen-pgi

I am running into compilation errors when sync_wait takes a when_all_with_variant that has a sender with multiple value completions. The code is creating an object of type tuple<T&&> instead of tuple<T>, and that leads to errors trying to initialize a variant that expects a tuple<T>. (Multiple value completions is the whole point of when_all_with_variant, so this bug makes that adapter kind of useless.)

#include <stdexec/execution.hpp>
#include <exec/any_sender_of.hpp>

int main() {
  using any_sender =
    exec::any_sender<exec::any_receiver<stdexec::completion_signatures<
      stdexec::set_value_t(int), stdexec::set_value_t(double)>>>;
  stdexec::sync_wait(
      stdexec::when_all_with_variant(
        any_sender{stdexec::just(1)}));
}

When compiled with nvc++, the error is right at the top and is easy enough to figure out. Note the "argument types are: (std::tuple<int &&>)".

"/proj/cuda/stdexec/main/include/stdexec/__detail/__into_variant.hpp", line 86: error: no instance of constructor "std::variant<_Types...>::variant [with _Types=<std::tuple<double>, std::tuple<int>>]" matches the argument list
            argument types are: (std::tuple<int &&>)
                                 __variant_t{
                                            ^

When compiled with g++, the real cause of the error is much harder to find, but I think it's the same error. Note the "with _Tp = std::tuple<int&&>&&;" in there.

/usr/include/c++/15/variant:1499:9: note: candidate 5: ‘template<class _Tp, class, class, class _Tj, class> constexpr std::variant< <template-parameter-1-1> >::variant(_Tp&&) [with <template-parameter-2-2> = _Tp; _Tj = <template-parameter-1-2>; _Types = {std::tuple<double>, std::tuple<int>}]’
 1499 |         variant(_Tp&& __t)
      |         ^~~~~~~
/usr/include/c++/15/variant:1499:9: note: template argument deduction/substitution failed:
/usr/include/c++/15/variant: In substitution of ‘template<class ... _Types> template<class _Tp, class> using std::variant< <template-parameter-1-1> >::__accepted_type = std::variant< <template-parameter-1-1> >::__to_type<((long unsigned int)__accepted_index<_Tp>)> [with _Tp = std::tuple<int&&>&&; <template-parameter-2-2> = void; _Types = {std::tuple<double>, std::tuple<int>}]’:

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions