2016-06-02 6 views
0

Ich habe eine StreamWriter/StreamReader Verbindung von einem NetworkStream zur Steuerung eines Testgeräts eingerichtet. Die zugrunde liegende Verbindung ist TCP.C# StreamWriter/NetworkStream/TcpClient/Kein Senden von Daten nach Leerlauf für +5 min

In diesem bestimmten Fall bleibt diese Verbindung für einige Minuten inaktiv. Nach +5 Minuten Durchlauf, wenn ich streamWriter.writeLine(...) rufe, dann flush, werden keine Daten von meinem Computer zum Testgerät gesendet (Pakete auf wireshark). Vor und während der Leerlaufzeit werden keine Pakete ausgetauscht. Keine FIN oder RST-Pakete, etc ...

Debuggen mein streamWriter Objekt, scheint es immer noch gültig zu sein (connected = true, etc ...)

Ich habe Probleme identifizieren, was Teil meines StreamWriter/NetworkStream/TcpClient Objekt ist Zeitüberschreitung oder Schließen ohne Senden einer FIN- oder RST-Nachricht, um die Verbindung formal zu schließen. Hier

ist eine gekürzte Version des Codes, die fehlschlägt:

private void button1_Click(object sender, EventArgs e) 
{ 
     TcpClient client; 
     NetworkStream networkStream; 
     System.IO.StreamReader streamReader; 
     System.IO.StreamWriter streamWriter; 
     string outputString; 

     client = new TcpClient("555.555.555.555", 5025); 
     client.ReceiveTimeout = 5000; 
     networkStream = client.GetStream(); 
     streamReader = new System.IO.StreamReader(networkStream); 
     streamWriter = new System.IO.StreamWriter(networkStream); 

     //This section works fine, every time 
     streamWriter.WriteLine("*IDN?\n");  //Ask for equipment identification 
     streamWriter.Flush(); 
     outputString = streamReader.ReadLine(); 
     Console.WriteLine("First Attempt: Connected to: {0}", outputString); 

     System.Threading.Thread.Sleep(301000); //Simulate idle connection time 

     //The read in this section fails if the sleep above is longer than 5 minutes 
     streamWriter.WriteLine("*IDN?\n");  //Ask for equipment identification 
     streamWriter.Flush(); 
     outputString = streamReader.ReadLine(); 
     Console.WriteLine("Second Attempt: Connected to: {0}", outputString); 
} 

Der Fehler ist gefunden, wenn ich versuche, die Antwort zurück aus zu lesen, was ich geschrieben habe, um die Ausrüstung. Da das Gerät meine Anfrage nie gesehen hat, erhalte ich einen Lese-Timeout-Fehler.

Wenn ich meinen Schlaf auf etwas weniger als 5 Minuten ändere, funktioniert alles gut.

Ich habe in die Implementierung einer Art von Keep am Socket untersucht, aber mein Verständnis ist, dass nativ eine TCP-Verbindung geöffnet bleibt, bis beide Enden es schließt.

Ich glaube auch nicht, dass dies ein Netzwerkproblem von Drittanbietern ist, da Wireshark zeigt, dass keine FIN- oder RST-Nachrichten gesendet/empfangen wurden und mein Versuch, eine Nachricht nach 5 Minuten zu schreiben, wird von Wireshark nicht gesehen läuft auch auf meinem Computer.

Ich verwende Microsoft Visual Studio 2010 auf meinem Windows 7 Computer, wenn das hilft.

Alle Empfehlungen würden sehr geschätzt werden. Bitte lassen Sie mich auch wissen, wenn ich weitere Details erläutern oder etwas klären muss.

+0

Ich hatte das gleiche Problem. Es ist kein Problem mit Ihrem Code. Irgendetwas zwischen den Geräten bereinigt ungenutzte Verbindungen (wahrscheinlich eine Stateful Firewall?). Das Hinzufügen eines Keepalive (in meinem Fall waren 10 Minuten ausreichend) war die einzige Lösung, die ich finden konnte. – itsme86

+0

einen Versuch wert * nur für den Fall * - Set 'NoDelay' auf dem TCP-Client –

+0

Mit einigem zusätzlichen Graben habe ich meine Antivirus-Software 'Symantec' deaktiviert und konnte das Problem nicht mehr neu erstellen. Es scheint, dass die Richtlinie auf meinem Computer, die von der IT-Abteilung eingerichtet wurde, eine inaktive Verbindung herunterfährt. In dem Bemühen, mit der Richtlinie gut zu spielen, werde ich eine einfache Zeitüberprüfung implementieren, bei der, wenn das letzte Mal, dass die Verbindung verwendet wurde, über eine bestimmte Zeit vergangen ist, ich die Verbindung schließe und die Verbindung wieder öffne. – Peter

Antwort

0

Dieses Problem wurde gelöst, indem eine Zeitüberprüfung implementiert wurde, die die Verbindung schließen und wiederherstellen würde, wenn mehr als ein paar Minuten verstrichen und kein Datenverkehr vorhanden war. Dies liegt daran, dass die Antiviren-Software, die auf dem Host-Computer ausgeführt wurde, proaktiv war, jedoch ohne Benachrichtigung, wodurch inaktive Socket-Verbindungen beendet wurden.

Verwandte Themen