[Mono-list] delegates and AsyncCallback

Jason Whittington jasonw@develop.com
Mon, 18 Mar 2002 19:36:57 -0500


>I just try to implement asynchronous delegate support, but I don't know
>when to invoke the AsyncCallback passed to BeginInvoke

You should invoke the AsyncCallback delegate right after the method
finishes, and you should invoke it from the worker thread, not the
calling thread.

The reason you're only seeing the callback sometimes is that your code
has a race condition. The main thread occasionally gets the EndInvoke in
before the async_callback fires and then it exits, taking down the
worker thread before it ever manages to call the your callback.  Change
that EndInvoke to a Console.ReadLine() and you'll see the callback get
called every time.

Typically when passing an async callback EndInvoke is called inside the
callback proc, not from the issuing thread. If you think about it,
there's no REASON to pass in the AsyncCallback if your main thread is
going to rendezvous with EndInvoke - it's there to allow you to harvest
the results asynchronously.  I modified your code to reflect this:

======================
using System;

class Test {
	delegate int SimpleDelegate (int a);

	static int F (int a) {
		Console.WriteLine ("Test.F from delegate: " + a);
		return a;
	}

	static void async_callback (IAsyncResult ar)
	{
	int result = ((SimpleDelegate)(ar.AsyncState)).EndInvoke(ar);
	Console.WriteLine(result);
	}
	
	static void Main () {
		SimpleDelegate d = new SimpleDelegate (F);
		d.BeginInvoke(3, new AsyncCallback (async_callback), d);
		System.Console.ReadLine();		
	}
} 
=======================

Hope this helps,
Jason