Skip to content

nvexec let_value et al assumes sender returned from lambda is a stream sender #1059

Open
@ericniebler

Description

@ericniebler

nvexec's customization of let_value calls the lambda and constructs the result sender in temporary storage (good), but it unconditionally attaches a propagate_receiver_t. If that sender is not a stream sender, and if it completes with reference(s) to objects in host memory (say, if it passes to propagate_receiver_t's set_value references to temporaries that live on the host caller's stack, then when device code accesses the values, the process will crash because host memory is inaccessible.

E.g., this crashes:

nvexec::stream_context ctx;

auto snd = stdexec::schedule( ctx.get_scheduler() )
         | stdexec::let_value( [] {
             // this sender will complete with an rvalue reference to
             // an integer in host memory:
             return stdexec::just() | stdexec::then( [] { return 42; } );
           })
           // This sender's receiver, wrapped in `propagate_receiver_t`,
           // will accept the reference to host memory and pass it into
           // a kernel that calls this lambda, causing an access violation.
         | stdexec::then( [] (int i) { ... } );

stdexec::sync_wait( std::move(snd) );

The stream scheduler's let_value customization must assume, if the result sender is not a stream sender, that any values/errors it may complete with are kept in host memory and defensively copy them into device memory.

Metadata

Metadata

Assignees

No one assigned

    Labels

    P1bugSomething isn't workingcudarequires CUDA expertise

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions