From: Braddock Gaskill (braddock_at_[hidden])
Date: 2007-05-01 07:16:26


On Mon, 30 Apr 2007 11:48:31 -0700, Stjepan Rajko wrote:
> I guess the consensus is that there is use for both sync and async aspects,
> and both should be

I personally would suggest looking at how futures can make the async/sync
elements easier.

Imagine I have a function 'rpc' which calls the passed function and arguments
remotely and returns a future<T>, where T is the return type.

Along the lines of:
future<T> rpc(F function, INARG1, ... , INARGN, OUTARG1, ... OUTARGN);

1) Synchronous behavior:
cout << "1+2 = " << rpc(add, 1, 2) << "\n";

2) Async behavior:
future<int> fi = rpc(add, 1, 2);
...doing other things...
cout << "1+2 = " << fi.get() << "\n"; //will block if fi is not yet complete

3) rpc call fails:
future<int> fi = rpc(add, 1, 2);
try {
  cout << "1+2 = " << fi << "\n"; //will throw if fi contains exception
} catch (rpc_connect_error &e) {
  ...
}

4) I want to cancel the rpc if it isn't ready yet:
future<int> fi = rpc(add, 1, 2);
...doing other things...
fi.cancel(); // cancels if not yet complete

5) I want a basic timeout
fi.timed_wait(100 /*ms*/);
if (!fi.ready()) fi.cancel();

6) My remote call may return an exception (and my rpc library has some
exception transportation mechanism)
try {
  cout << "1+2 = " << fi << "\n";
} catch (...) {
  cout << "ERROR\n";
}

7) I have both a return value and an "Out" argument:
future<int> multiplied;
future<int> fi = rpc(add_and_mult, 1, 2, multiplied);
cout << "1+2 = " << fi << "\n";
cout << "1*2 = " << multiplied << "\n";

This is the ideal application of futures. My futures library can support all
of the above uses today without modification. As a bonus, then any code which
uses futures can transparently use the rpc library as a back-end (except for
dispatch of course)...a future is a future is a future. I'll work with you as
I prepare for boost submission if you want to explore this route.

Braddock Gaskill
Dockside Vision Inc