2012-05-22 189 views
2

我有一個Visual Studio 2008 C#.NET 3.5應用程序在Windows XP SP3 x86上運行。在我的應用程序中,我有一個可以同時由多個線程調用的事件處理程序OnSendTask。它打開到遠程主機的TCP連接併發送/接收數據。TcpClient.Connect說:「連接嘗試失敗,因爲連接方...」

例如:

/// <summary> 
/// prevent us from exceeding the maximum number of half-open TCP 
/// connections in Windows XP. 
/// </summary> 
private System.Threading.Semaphore tcp_connection_lock_ = 
    new System.Threading.Semaphore(10, 10); 

public event EventHandler<SendTaskEventArgs> SendTask; 

private void OnSendTask(object sender, SendTaskEventArgs args) 
{ 
    try 
    { 
     tcp_connection_lock_.WaitOne(); 
     using (TcpClient recipient = new TcpClient()) 
     { 
      // error here! 
      recipient.Connect(args.IPAddress, args.Port); 
      using (NetworkStream stream = recipient.GetStream()) 
      { 
       // read/write data 
      } 
    } 
    catch 
    { 
     // write exceptions to the logfile 
    } 
    finally 
    { 
     tcp_connection_lock_.Release(); 
    } 
} 

void SendTasks(int tasks_to_send) 
{ 
    using (ManualResetEvent done_event = new ManualResetEvent(false)) 
    { 
     int countdown = tasks_to_send; 
     for (int i = 0; i < tasks_to_send; ++i) 
     { 
      ThreadPool.QueueUserWorkItem((o) => 
      { 
       SendTaskEventArgs args = new SendTaskEventArgs(/*...*/); 

       EventHandler<SendTaskEventArgs> evt = SendTask; 
       if (evt != null) 
        evt(this, e); 

       if (Interlocked.Decrement(ref countdown) == 0) 
        done_event.Set(); 
      }, i); 
     } 
     done_event.WaitOne(); 
    } 
} 

不幸的是,我偶爾看到這樣的錯誤:

System.Net.Sockets.SocketException: A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond 192.168.0.16:59596 
at System.Net.Sockets.TcpClient.Connect(String hostname, Int32 port) 

的一些信息點:

  • 如果我發送任務到40個遙控器,我將會從大約6處看到這個響應。
  • Wireshark trace顯示沒有嘗試甚至啓動從PC到遠程的TCP連接。
  • 我可以通過電腦ping遠程並獲得一致的良好響應。
  • 遙控器與運行此應用程序的個人電腦在同一個交換機和子網上。在這種方式中沒有花哨的網絡。

有人可以提出什麼可能會導致此錯誤或我可以修復它嗎?

感謝

+0

如果您發送任務到1個遠程,它是否總是成功?該錯誤消息使得它看起來像遠程方引起了問題。 –

+0

我從來沒有見過它無法發送到1個遠程。我同意錯誤信息的發音方式,但第2點表明PC甚至沒有嘗試建立連接。 – PaulH

+0

您可能需要提供更多代碼。 OnSendTask如何被調用?你在哪裏調用tcp_connection_lock_.Release()? –

回答

2

我不知道所有的最大半開TCP連接背後的細節,但是,我相信這是不特定於應用程序的連接,而是全系統。您確定發生此錯誤時系統上沒有其他應用程序創建TCP連接嗎?

每當發生錯誤時,我都會設置一個重試。例如:

private const int MaxRetries = 10; 
private void OnSendTask(object sender, SendTaskEventArgs args) 
{ 
    bool retry = false; 
    try 
    { 
     tcp_connection_lock_.WaitOne(); 
     using (TcpClient recipient = new TcpClient()) 
     { 
      // error here! 
      recipient.Connect(args.IPAddress, args.Port); 
      using (NetworkStream stream = recipient.GetStream()) 
      { 
       // read/write data 
      } 
     } 
    } 
    catch (SocketException ex) 
    { 
     if(args.RetryCount < MaxRetries) 
     { 
      retry = true; 
      args.RetryCount++; 
     } 
     else 
     { 
      // write exceptions to the logfile 
     } 
    } 
    finally 
    { 
     tcp_connection_lock_.Release(); 
    } 

    if(retry) 
    { 
     Thread.Sleep(1); 
     OnSendTask(sender, args); 
    } 
} 
+0

我已經做了一些更多的分析,事實證明,問題在於遙控器並不總是響應在TCP SYN之前發送的ARP請求。 (錯誤的TCP堆棧?) 您的解決方案有效地解決了這個問題,因爲我們現在正在發送更多的ARP請求,所以您可以獲得答案。 :) – PaulH

相關問題