ich übertrage Daten zwischen 2 Sockets... geht auch einwandfrei.
Nur beim abbrechen eines Transfers habe ich ein Problem.
Wenn der SENDER den Dateiempfang abbricht bekommt der Empfänger das nicht mit...
Er bleibt hier hängen - also liest immer wieder 0 Bytes:
while (red < t.Size) { tmp = t.Connection.readData(buffer); red += tmp; t.Transferred = red; s.Write(buffer, 0, tmp); }
Sollte nicht eigentlich eine Socketexception ausgelöst werden?
Wenn ich allerdings beim Empfänger abbreche, dann bekommen Sender und Empfänger eine Exception das der Socket geschlossen ist und alles ist ok.
Wieso klappt das nicht wenn der Sender abbricht?
Zum Verständnis:
Transfer bündelt alle Informationen zum Transfer wie z.b. Dateiname, Grösse etc und die Socketverbindung(Connection) an sich
Die Methode zum übertragen der Daten:
private void transfer(Transfer t) { this.Transfers.Add(t); byte[] buffer = new byte[10 * 1024]; this.tCalculate = new Thread(new ParameterizedThreadStart(calculateTransferSpeed)); if (t.Incoming) { logger.log("Incoming: " + t.FileName); //Bestätigung des Empfangs senden t.Connection.writeText(Commands.Ok); logger.log("Incoming: Acceptet Transfer"); //Empfang und speichern der Daten BufferedStream s=null; logger.log("Incoming: Starting receiving"); try { s = new BufferedStream(File.Open(t.Path, FileMode.Create), 2 * 1024 * 1024); int tmp, red = 0; this.tCalculate.Start(t); while (red < t.Size) { tmp = t.Connection.readData(buffer); red += tmp; t.Transferred = red; s.Write(buffer, 0, tmp); } logger.log("Incoming: Receiving done"); } catch (Exception ex) { exceptionThrown(ex); logger.log("Incoming: Error while receiving"); } finally { t.Connection.disconnect(); this.tCalculate.Abort(); t.Speed = 0; s.Close(); logger.log("Incoming: Resources closed"); } } else { logger.log("Sending: " + t.FileName); //Verbindung aufbauen t.Connection = new Connection(t.Ip, t.Port); logger.log("Sending: Verbindung aufgebaut"); t.Connection.writeText(Commands.Hello); if (t.Connection.readText().Equals(Commands.Hello)) { t.Connection.writeText(t.FileName); t.Connection.writeText(Convert.ToString(t.Size)); if (t.Connection.readText().Equals(Commands.Ok)) { BufferedStream s = null; logger.log("Sending: Starting Data Transfer"); try { s = new BufferedStream(File.Open(t.Path, FileMode.Open), 2 * 1024 * 1024); int tmp, written = 0; this.tCalculate.Start(t); while (written < t.Size) { tmp = s.Read(buffer, 0, buffer.Length); t.Connection.writeData(buffer, tmp); written += tmp; t.Transferred = written; } logger.log("Sending: Sending ok"); } catch(Exception ex) { exceptionThrown(ex); logger.log("Sending: Error while sending"); } finally { this.tCalculate.Abort(); t.Speed = 0; s.Close(); t.Connection.disconnect(); logger.log("Sending: Reources closed"); } } else { t.Connection.disconnect(); } } } }
Abbrechen tue ich die Sache wie folgt (In der Connectioen welche zum Transfer gehört):
public void disconnect() { try { this.socket.Shutdown(SocketShutdown.Both); } catch { } finally { this.socket.Close(); this.connected = false; } }