diff options
author | Nick Hudson <nick.hudson@isode.com> | 2013-05-31 10:55:55 (GMT) |
---|---|---|
committer | Nick Hudson <nick.hudson@isode.com> | 2013-05-31 11:15:23 (GMT) |
commit | 7d7ecdbb01daa051472bf40e269b78c4faf7b34e (patch) | |
tree | bf75e02f6118f2882a3c6d0e53a34307921b6e7c /src/com/isode | |
parent | 3335b1dfa9b429d90088184f58daff01e84432f2 (diff) | |
download | stroke-7d7ecdbb01daa051472bf40e269b78c4faf7b34e.zip stroke-7d7ecdbb01daa051472bf40e269b78c4faf7b34e.tar.bz2 |
Workaround for some misbehaving SSLEngine implementations
Some implementations of SSLEngine (notably Apache harmony used in
Android) never return the FINSHED status from calls to wrap or unwrap,
causing the TLSLayer to never emit its completed signal.
With this change, we treat a return of NOT_HANDSHAKING as equivalent
to FINISHED. The NOT_HANDSHAKING will never happen before handshaking
has finished, because the status during handshaking should always be
NEED_WRAP, NEED_UNWRAP, or NEED_TASK.
Test-information:
Tested with OracleJDK and OpenJDK using Isode M-Link Console to ensure
that the behaviour when negotiating TLS is unchanged (debugging shows
that in these cases it always sees the FINISHED status).
Tested on Android. Without this patch TLS handshakes don't complete;
with the patch, they do.
Change-Id: Ied2989cb2a3458dc6b1d2584dcc6c722d18e1355
Signed-off-by: Nick Hudson <nick.hudson@isode.com>
Diffstat (limited to 'src/com/isode')
-rw-r--r-- | src/com/isode/stroke/tls/java/JSSEContext.java | 19 |
1 files changed, 15 insertions, 4 deletions
diff --git a/src/com/isode/stroke/tls/java/JSSEContext.java b/src/com/isode/stroke/tls/java/JSSEContext.java index 257a70c..8c351bb 100644 --- a/src/com/isode/stroke/tls/java/JSSEContext.java +++ b/src/com/isode/stroke/tls/java/JSSEContext.java @@ -247,13 +247,19 @@ public class JSSEContext extends TLSContext { * a status is an indication that we need to re-check whether * anything's pending to be written */ - if (handshakeStatus == HandshakeStatus.FINISHED) { + if (handshakeStatus == HandshakeStatus.FINISHED || + (!handshakeCompleted && + handshakeStatus == HandshakeStatus.NOT_HANDSHAKING)) { /* Special case will happen when the handshake completes following * an unwrap. The first time we tried wrapping some plain stuff, * it triggers the handshake but won't itself have been dealt with. * So now the handshake has finished, we have to try sending it * again - */ + * The second checking clause is necessary for certain + * SSLEngine implementations (notably Apache Harmony + * used on Android) which never return FINISHED + */ + handshakeCompleted = true; wrapAndSendData(); onConnected.emit(); @@ -410,9 +416,14 @@ public class JSSEContext extends TLSContext { plainToSend.compact(); /* FINISHED can only come back for wrap() or unwrap(); so check to - * see if we just had it + * see if we just had it. + * The second checking clause is necessary for certain + * SSLEngine implementations (notably Apache Harmony + * used on Android) which never return FINISHED */ - if (handshakeStatus == HandshakeStatus.FINISHED) { + if (handshakeStatus == HandshakeStatus.FINISHED || + (!handshakeCompleted && + handshakeStatus == HandshakeStatus.NOT_HANDSHAKING)) { handshakeFinished = true; } |