executors / futures

A proposal for a futures programming model for ISO C++
22 stars 7 forks source link

Interoperation with interrupt tokens `std::thread`/`std::jthread` (P0660) #118

Open josuttis opened 6 years ago

josuttis commented 6 years ago

http://wg21.link/p0660 introduces interrupt tokens (cancellation tokens) to the standard for threads. They should be reused here.

brycelelbach commented 6 years ago

This morning I tried to mock up an example of how to do this - specifically, how to build a new async that uses a std_thread_executor, std::execution:;semi_future<> and std::execution::make_promise_contract. At first the only incompatiblity appeared to be the difference in what the cancellation notifiers look like (in Nico's proposal, they aren't callables, but things with an interrupt method).

I quickly realized it was more complicated than that, so I think we will need to think about this.

Let's try to aim to resolve this by Rapperswil, as it's good to have proposals in flight interoperate with each other (or at least understand how to).

LeeHowes commented 6 years ago

If we added a call_if_interrupted operation on the future then it could be made to work. It'd be a slightly higher cost version of what we have now, though, because we couldn't include the size of that callback in construction of the future/promise pair.

Beyond that I don't really see a lot of alignment. This is about a token to pass around - in the future model we are explicitly talking about something that is called when the downstream task is cancelled.

I do think there is value to aligning the concepts. We could allow for a given future to support an optional interrupt-promise interface, to interrupt/cancel the future. I think the terminology would be confusing, though - maybe cancellation is a better term in both cases rather than interruption.

josuttis commented 6 years ago

we don't have to align a lot. but we definitely should use the same interrupt token type

Am 7. Mai 2018 17:51:24 MESZ schrieb LeeHowes notifications@github.com:

If we added a call_if_interrupted operation on the future then it could be made to work. It'd be a slightly higher cost version of what we have now, though, because we couldn't include the size of that callback in construction of the future/promise pair.

Beyond that I don't really see a lot of alignment. This is about a token to pass around - in the future model we are explicitly talking about something that is called when the downstream task is cancelled.

I do think there is value to aligning the concepts. We could allow for a given future to support an optional interrupt-promise interface, to interrupt/cancel the future. I think the terminology would be confusing, though - maybe cancellation is a better term in both cases rather than interruption.

-- You are receiving this because you were assigned. Reply to this email directly or view it on GitHub: https://github.com/executors/futures/issues/118#issuecomment-387110336


Diese Nachricht wurde von meinem Fairphone2 mit K-9 Mail gesendet.

LeeHowes commented 6 years ago

The problem is that I'm not sure that makes sense. Interrupt tokens provide: a) a means to check if an interrupt request has been made b) a mechanism to throw an exception

What we need is a hook to propagate a cancellation request through a chain.

Now, we clearly could achieve this by a combination of adding a "call on interrupt" operation to the interrupt future, and passing the promise into the downstream promise constructor. Packaging that callback will then be made more expensive because we can't construct the whole thing at once including the callback.

If we can package the callback into the interrupt promise, then we achieve the same thing as we have now, excepting that we don't need the token or future at all.

The problem is that the goals are different. For the interrupt token you want to interrupt a running task, and you want to be able to pass these tokens around dynamically. For futures all we want is a single reverse promise/future pair constructed at the same time as the one in the direction of the flow of data.

That might mean we can usefully share the interface, or that we modify the definition of interrupt tokens such that the promise is constructed with a callback, and one thing that callback can do is to signal a copyable token, which provides the equivalent of a shared_future on the cancellation end. If not that then at least a consistent concept: but then we have to be careful because future cancellation really doesn't have much to do with interrupting individual tasks, while for thread interruption that's the entire goal.