summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
Diffstat (limited to 'src/com/isode/stroke/session')
-rw-r--r--src/com/isode/stroke/session/BasicSessionStream.java73
-rw-r--r--src/com/isode/stroke/session/Session.java59
-rw-r--r--src/com/isode/stroke/session/SessionStream.java20
3 files changed, 105 insertions, 47 deletions
diff --git a/src/com/isode/stroke/session/BasicSessionStream.java b/src/com/isode/stroke/session/BasicSessionStream.java
index 9ba862d..4048363 100644
--- a/src/com/isode/stroke/session/BasicSessionStream.java
+++ b/src/com/isode/stroke/session/BasicSessionStream.java
@@ -20,6 +20,7 @@ import com.isode.stroke.parser.PayloadParserFactoryCollection;
import com.isode.stroke.serializer.PayloadSerializerCollection;
import com.isode.stroke.signals.Slot;
import com.isode.stroke.signals.Slot1;
+import com.isode.stroke.signals.SignalConnection;
import com.isode.stroke.streamstack.CompressionLayer;
import com.isode.stroke.streamstack.ConnectionLayer;
import com.isode.stroke.streamstack.StreamStack;
@@ -29,6 +30,8 @@ import com.isode.stroke.streamstack.XMPPLayer;
import com.isode.stroke.tls.Certificate;
import com.isode.stroke.tls.CertificateVerificationError;
import com.isode.stroke.tls.TLSContextFactory;
+import com.isode.stroke.tls.TLSOptions;
+import com.isode.stroke.tls.TLSError;
public class BasicSessionStream extends SessionStream {
@@ -38,7 +41,8 @@ public class BasicSessionStream extends SessionStream {
PayloadParserFactoryCollection payloadParserFactories,
PayloadSerializerCollection payloadSerializers,
TLSContextFactory tlsContextFactory,
- TimerFactory timerFactory) {
+ TimerFactory timerFactory,
+ TLSOptions tlsOptions) {
available = false;
this.connection = connection;
this.payloadParserFactories = payloadParserFactories;
@@ -52,40 +56,40 @@ public class BasicSessionStream extends SessionStream {
this.compressionLayer = null;
this.tlsLayer = null;
this.whitespacePingLayer = null;
-
+ this.tlsOptions_ = tlsOptions;
xmppLayer = new XMPPLayer(payloadParserFactories, payloadSerializers, streamType);
- xmppLayer.onStreamStart.connect(new Slot1<ProtocolHeader>() {
+ onStreamStartConnection = xmppLayer.onStreamStart.connect(new Slot1<ProtocolHeader>() {
public void call(ProtocolHeader p1) {
handleStreamStartReceived(p1);
}
});
- xmppLayer.onElement.connect(new Slot1<Element>() {
+ onElementConnection = xmppLayer.onElement.connect(new Slot1<Element>() {
public void call(Element p1) {
handleElementReceived(p1);
}
});
- xmppLayer.onError.connect(new Slot() {
+ onErrorConnection = xmppLayer.onError.connect(new Slot() {
public void call() {
handleXMPPError();
}
});
- xmppLayer.onDataRead.connect(new Slot1<SafeByteArray>() {
+ onDataReadConnection = xmppLayer.onDataRead.connect(new Slot1<SafeByteArray>() {
public void call(SafeByteArray p1) {
handleDataRead(p1);
}
});
- xmppLayer.onWriteData.connect(new Slot1<SafeByteArray>() {
+ onWriteDataConnection = xmppLayer.onWriteData.connect(new Slot1<SafeByteArray>() {
public void call(SafeByteArray p1) {
handleDataWritten(p1);
}
});
- connection.onDisconnected.connect(new Slot1<Connection.Error>() {
+ onDisconnectedConnection = connection.onDisconnected.connect(new Slot1<Connection.Error>() {
public void call(Connection.Error p1) {
handleConnectionFinished(p1);
@@ -99,6 +103,28 @@ public class BasicSessionStream extends SessionStream {
}
+ /**
+ * User will have to call disconnect() method to free up the resources.
+ */
+ @Override
+ public void disconnect() {
+ if(tlsLayer != null) {
+ onErrorConnection.disconnect();
+ onConnectedConnection.disconnect();
+ tlsLayer = null;
+ }
+ whitespacePingLayer = null;
+ streamStack = null;
+ onDisconnectedConnection.disconnect();
+ connectionLayer = null;
+ onStreamStartConnection.disconnect();
+ onElementConnection.disconnect();
+ onErrorConnection.disconnect();
+ onDataReadConnection.disconnect();
+ onWriteDataConnection.disconnect();
+ xmppLayer = null;
+ }
+
public void writeHeader(ProtocolHeader header) {
assert available;
xmppLayer.writeHeader(header);
@@ -133,18 +159,18 @@ public class BasicSessionStream extends SessionStream {
public void addTLSEncryption() {
assert available;
- tlsLayer = new TLSLayer(tlsContextFactory);
+ tlsLayer = new TLSLayer(tlsContextFactory, tlsOptions_);
if (hasTLSCertificate() && !tlsLayer.setClientCertificate(getTLSCertificate())) {
- onClosed.emit(new Error(Error.Type.InvalidTLSCertificateError));
+ onClosed.emit(new SessionStreamError(SessionStreamError.Type.InvalidTLSCertificateError));
} else {
streamStack.addLayer(tlsLayer);
- tlsLayer.onError.connect(new Slot() {
+ onErrorConnection = tlsLayer.onError.connect(new Slot1<TLSError>() {
- public void call() {
- handleTLSError();
+ public void call(TLSError e) {
+ handleTLSError(e);
}
});
- tlsLayer.onConnected.connect(new Slot() {
+ onConnectedConnection = tlsLayer.onConnected.connect(new Slot() {
public void call() {
handleTLSConnected();
@@ -211,25 +237,25 @@ public class BasicSessionStream extends SessionStream {
private void handleXMPPError() {
available = false;
- onClosed.emit(new Error(Error.Type.ParseError));
+ onClosed.emit(new SessionStreamError(SessionStreamError.Type.ParseError));
}
private void handleTLSConnected() {
onTLSEncrypted.emit();
}
- private void handleTLSError() {
+ private void handleTLSError(TLSError error) {
available = false;
- onClosed.emit(new Error(Error.Type.TLSError));
+ onClosed.emit(error);
}
private void handleConnectionFinished(Connection.Error error) {
available = false;
if (Connection.Error.ReadError.equals(error)) {
- onClosed.emit(new Error(Error.Type.ConnectionReadError));
+ onClosed.emit(new SessionStreamError(SessionStreamError.Type.ConnectionReadError));
}
else if (error != null) {
- onClosed.emit(new Error(Error.Type.ConnectionWriteError));
+ onClosed.emit(new SessionStreamError(SessionStreamError.Type.ConnectionWriteError));
}
else {
onClosed.emit(null);
@@ -262,5 +288,12 @@ public class BasicSessionStream extends SessionStream {
private TLSLayer tlsLayer;
private WhitespacePingLayer whitespacePingLayer;
private StreamStack streamStack;
-
+ private TLSOptions tlsOptions_;
+ private SignalConnection onErrorConnection;
+ private SignalConnection onConnectedConnection;
+ private SignalConnection onDisconnectedConnection;
+ private SignalConnection onStreamStartConnection;
+ private SignalConnection onElementConnection;
+ private SignalConnection onDataReadConnection;
+ private SignalConnection onWriteDataConnection;
}
diff --git a/src/com/isode/stroke/session/Session.java b/src/com/isode/stroke/session/Session.java
index 815be02..0255627 100644
--- a/src/com/isode/stroke/session/Session.java
+++ b/src/com/isode/stroke/session/Session.java
@@ -22,6 +22,7 @@ import com.isode.stroke.serializer.PayloadSerializerCollection;
import com.isode.stroke.signals.Signal1;
import com.isode.stroke.signals.Slot;
import com.isode.stroke.signals.Slot1;
+import com.isode.stroke.signals.SignalConnection;
import com.isode.stroke.streamstack.ConnectionLayer;
import com.isode.stroke.streamstack.StreamStack;
import com.isode.stroke.streamstack.XMPPLayer;
@@ -46,27 +47,31 @@ public abstract class Session {
public Session(
final Connection connection,
final PayloadParserFactoryCollection payloadParserFactories,
- final PayloadSerializerCollection payloadSerializers,
- final EventLoop eventLoop) {
+ final PayloadSerializerCollection payloadSerializers) {
this.connection = connection;
- this.eventLoop = eventLoop;
this.payloadParserFactories = payloadParserFactories;
this.payloadSerializers = payloadSerializers;
+ xmppLayer = null;
+ connectionLayer = null;
+ streamStack = null;
finishing = false;
}
public void startSession() {
initializeStreamStack();
- handleSessionStarted();
+ handleSessionStarted();
}
public void finishSession() {
+ if (finishing) {
+ return;
+ }
finishing = true;
- connection.disconnect();
- handleSessionFinished(null);
- finishing = false;
- onSessionFinished.emit(null);
+ if (xmppLayer != null) {
+ xmppLayer.writeFooter();
+ }
+ connection.disconnect();
}
public void sendElement(Element stanza) {
@@ -94,11 +99,14 @@ public abstract class Session {
}
protected void finishSession(SessionError error) {
+ if (finishing) {
+ return;
+ }
finishing = true;
- connection.disconnect();
- handleSessionFinished(error);
- finishing = false;
- onSessionFinished.emit(error);
+ if (xmppLayer != null) {
+ xmppLayer.writeFooter();
+ }
+ connection.disconnect();
}
protected void handleSessionStarted() {
@@ -133,7 +141,7 @@ public abstract class Session {
});
xmppLayer.onDataRead.connect(onDataRead);
xmppLayer.onWriteData.connect(onDataWritten);
- connection.onDisconnected.connect(new Slot1<Connection.Error>() {
+ onDisconnectedConnection = connection.onDisconnected.connect(new Slot1<Connection.Error>() {
public void call(Connection.Error p1) {
handleDisconnected(p1);
@@ -151,28 +159,33 @@ public abstract class Session {
public StreamStack getStreamStack() {
return streamStack;
-
-
}
- /*void setFinished();*/ /* This seems to be unused in Swiften*/
+ /*protected void setFinished();*/ /* This seems to be unused in Swiften*/
private void handleDisconnected(Connection.Error connectionError) {
+ onDisconnectedConnection.disconnect();
if (connectionError != null) {
switch (connectionError) {
case ReadError:
- finishSession(SessionError.ConnectionReadError);
+ handleSessionFinished(SessionError.ConnectionReadError);
+ onSessionFinished.emit(SessionError.ConnectionReadError);
break;
case WriteError:
- finishSession(SessionError.ConnectionWriteError);
+ handleSessionFinished(SessionError.ConnectionWriteError);
+ onSessionFinished.emit(SessionError.ConnectionWriteError);
break;
}
- } else {
- finishSession();
+ }
+ else {
+ SessionError error = null;
+ handleSessionFinished(error);
+ onSessionFinished.emit(error);
}
}
- private JID localJID;
- private JID remoteJID;
+
+ private JID localJID = new JID();
+ private JID remoteJID = new JID();
private Connection connection;
private PayloadParserFactoryCollection payloadParserFactories;
private PayloadSerializerCollection payloadSerializers;
@@ -180,5 +193,5 @@ public abstract class Session {
private ConnectionLayer connectionLayer;
private StreamStack streamStack;
private boolean finishing;
- private final EventLoop eventLoop;
+ private SignalConnection onDisconnectedConnection;
}
diff --git a/src/com/isode/stroke/session/SessionStream.java b/src/com/isode/stroke/session/SessionStream.java
index 3171ec0..78d5588 100644
--- a/src/com/isode/stroke/session/SessionStream.java
+++ b/src/com/isode/stroke/session/SessionStream.java
@@ -6,12 +6,13 @@
* Copyright (c) 2010-2014, Isode Limited, London, England.
* All rights reserved.
*/
-package com.isode.stroke.session;
+package com.isode.stroke.session;
import java.util.List;
import com.isode.stroke.base.SafeByteArray;
import com.isode.stroke.base.ByteArray;
+import com.isode.stroke.base.Error;
import com.isode.stroke.elements.Element;
import com.isode.stroke.elements.ProtocolHeader;
import com.isode.stroke.signals.Signal;
@@ -22,7 +23,7 @@ import com.isode.stroke.tls.CertificateWithKey;
public abstract class SessionStream {
- public static class Error implements com.isode.stroke.base.Error {
+ public static class SessionStreamError implements Error {
public enum Type {
@@ -33,7 +34,7 @@ public abstract class SessionStream {
ConnectionWriteError
}
- public Error(Type type) {
+ public SessionStreamError(Type type) {
this.type = type;
}
public final Type type;
@@ -64,7 +65,18 @@ public abstract class SessionStream {
public abstract void setWhitespacePingEnabled(boolean enabled);
public abstract void resetXMPPParser();
-
+
+ public abstract void disconnect();
+
+ protected void finalize() throws Throwable {
+ try {
+ disconnect();
+ }
+ finally {
+ super.finalize();
+ }
+ }
+
public void setTLSCertificate(CertificateWithKey cert) {
certificate = cert;
}