template<typename... Types>
class AlgAudio::Relay< Types >
The Relay is a helper class for creating functions that cannot return their value imediatelly. It can create a LateReturn to be given to the caller, as well as return the value when it is ready, or throw a late exception.
Example usage:
LateReturn<int> GetProcessExitCode(Process& p){
Relay<int> r;
p.CallThisFuncWhenExitted([r,p](){
int exitcode = p.Status();
r.Return(exitcode);
});
return r;
}
When writing a LateReturning function, the first step is to create a relay. The template types must match the types of LateReturn this function returns. This does not have to be a single type, a Relay can return multiple values.
The return statement in the above example implicitly converts the relay to a corresponding LateReturn object. The parent called will then define when action should be called when the Relay's value is ready.
Also note how the lambda captures r by-value. It makes little sense to capture it by-reference, since r will no longer exist once GetProcessExitCode returns. When capturing it by-value, the copy-constructed clone of r that is stored with the function will be linked to the same LateReturn as the original r. Thus storing relays by-value should give desired results.
When calling Return() you pass a returned value as argument (or not, if the Relay has no types, i.e. the function returns LateReturn<>). If the corresponding continuation function has been already set, calling Return will also invoke that function. Notice that while logical stack goes down (we are returning a value), the actual stack goes up (we call function Return which in turn calls some other function that needs our return value).
Do not throw C++ exceptions in a LateReturning function. Because of how the stack is inverted, the exception would propagate in the wrong direction. It is often not obvious who called the code of a latereturning function or an embedded lambda. Where the exception should be passed is upwards, to a corresponding LateReturn, so that whoever called this function can define a handler. To do this, use LateThrow<Type>(constuction args), which will correctly pass the exception to the LateReturn's user-defined exception handler.