简体   繁体   中英

C# Async Socket Client Blocks Main Interface Thread

Another.networking question this time related to an Async Socket Client which is based on the MSDN examples at least for this initial version. Currently when the user clicks a button on the interface an Async Connect attempt is made to connect to a.networked device, the code is shown below -

//Mouse Event handler for main thread
private void btn_Read_MouseDown(object sender, MouseEventArgs e)
{
    Stopwatch sw = Stopwatch.StartNew();
    if (!networkDev.Connected)
        networkDev.Connect("192.168.1.176", 1025);

    if(networkDev.Connected)
       networkDev.getReading();
    sw.Stop();//Time time taken...
}

If the end point is switched on and exists on the.network this code works fine (less than a second for whole operation). However should the.networked device be switched off or unavailable the AsyncSocket Connect function holds up the main forms thread. Currently if the device is unavailable the whole interface locks up for about 20 seconds (using the stopwatch). I think that I am locking because the main thread is waiting for the return on the Connect request, does this mean I need to put that connect request on another thread?

I have included the code the Async Socket Client I am using -

    public bool Connect(String ip_address, UInt16 port)
    {
        bool success = false;

        try
        {
            IPAddress ip;
            success = IPAddress.TryParse(ip_address, out ip);
            if (success)
                success = Connect(ip, port);
        }
        catch (Exception ex)
        {
            Console.Out.WriteLine(ex.Message);
        }
        return success;
    }     

    public bool Connect(IPAddress ip_address, UInt16 port)
    {
        mSocket.BeginConnect(ip_address, port, 
           new AsyncCallback(ConnectCallback), mSocket);
        connectDone.WaitOne();//Blocks until the connect operation completes, 
                              //(time taken?) timeout?
        return mSocket.Connected;
    }

    private void ConnectCallback(IAsyncResult ar)
    {
        //Retreive the socket from thestate object
        try
        {
            Socket mSocket = (Socket)ar.AsyncState;
            //Set signal for Connect done so that thread will come out of 
            //WaitOne state and continue
            connectDone.Set();

        }
        catch (Exception ex)
        {
            Console.Out.WriteLine(ex.Message);
        }       
    }

I was hoping that by using an Async client which has its own thread that this would then stop freezing the interface if the host didn't exist but this does not appear to be the case. After the initial connect failure which takes 20s all subsequent connection attempts are returned immediately (less than a ms). Also something I thought strange, if the initial connection attempt succeeds, any later calls to connect to a non existent host return immediately. A little baffled by what is happening but wondering if its related to the fact that the Socket I use is stored in my AsyncSocket class. Any help much appreciated, if more of the client code is required let me know.

You claim it's asynchronous, but your Connect method clearly isn't:

mSocket.BeginConnect(ip_address, port, ...);
connectDone.WaitOne(); // Blocks until the connect operation completes [...]

You're blocking until it's completed, which is the antithesis of asynchronous behaviour. What's the point of using BeginConnect if you're going to block until it's connected?

You're blocking your UI thread here:

connectDone.WaitOne();  //Blocks until the connect operation completes, (time taken?) timeout?

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM