Pass argument to AsyncCallback function?

17,328

Solution 1

I'm going to presume you're using System.Net.Sockets.Socket here. If you look at the overloads of BeginReceive you'll see the object parameter (named state). You can pass an arbitrary value as this parameter and it will flow through to your AsyncCallback call back. You can then acess it using the AsyncState property of IAsyncResult object passed into your callback. Eg;

public void SomeMethod() {
  int myImportantVariable = 5;
  System.Net.Sockets.Socket s;
  s.BeginReceive(buffer, offset, size, SocketFlags.None, new new AsyncCallback(OnDataReceived), myImportantVariable);
}

private void OnDataReceived(IAsyncResult result) {
  Console.WriteLine("My Important Variable was: {0}", result.AsyncState); // Prints 5
}

Solution 2

This is a problem I prefer to solve with anonymous delegates:

var someDataIdLikeToKeep = new object();
mySocket.BeginBlaBla(some, other, ar => {
        mySocket.EndBlaBla(ar);
        CallSomeFunc(someDataIdLikeToKeep);
    }, null) //no longer passing state as we captured what we need in callback closure

It saves having to cast a state object in the receiving function.

Solution 3

When you call BeginReceive, you can pass any object as its last parameter. The same object will be made available to your callback through IAsyncResult's AsyncState property.

Share:
17,328
user1192403
Author by

user1192403

Updated on June 05, 2022

Comments

  • user1192403
    user1192403 about 2 years

    I'm learning socket programming and I have the following function:

    public void OnDataReceived(IAsyncResult asyn)
    

    and this is how the callback gets set:

    pfnWorkerCallBack = new AsyncCallback(OnDataReceived);
    

    The problem is I need to pass another argument to OnDataReceived callback function, how can I do this? I'm trying to make a simple tcp server and I need to track from which client the data is coming from. Any tips? Thanks!

  • AurelianRQ
    AurelianRQ over 12 years
    @user1192403 Glad to hear it :)
  • Vahid Ghadiri
    Vahid Ghadiri over 6 years
    What if we are going to pass multiple parameters?
  • AurelianRQ
    AurelianRQ over 6 years
    Then you would have to use some kind of container for it; public class Foo { public int Bar {get;set;} public string Baz {get;set;} } And then pass an instance of that into the BeginReceive method and cast result.AsyncState back to that type.