Merge pull request #4202 from eclipse/jetty-9.4.x-4201-httpclient_throw_sslhandshakeexception
Fixes #4201 - Throw SSLHandshakeException in case of TLS handshake fa…
This commit is contained in:
commit
2efce33fbe
|
@ -35,7 +35,9 @@ import java.util.concurrent.TimeUnit;
|
|||
import java.util.concurrent.atomic.AtomicLong;
|
||||
import java.util.concurrent.atomic.AtomicReference;
|
||||
import javax.net.ssl.SSLEngine;
|
||||
import javax.net.ssl.SSLEngineResult;
|
||||
import javax.net.ssl.SSLException;
|
||||
import javax.net.ssl.SSLHandshakeException;
|
||||
import javax.net.ssl.SSLPeerUnverifiedException;
|
||||
import javax.net.ssl.SSLSocket;
|
||||
|
||||
|
@ -61,6 +63,7 @@ import org.eclipse.jetty.util.StringUtil;
|
|||
import org.eclipse.jetty.util.ssl.SslContextFactory;
|
||||
import org.eclipse.jetty.util.thread.ExecutorThreadPool;
|
||||
import org.eclipse.jetty.util.thread.QueuedThreadPool;
|
||||
import org.hamcrest.Matchers;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.api.condition.EnabledOnJre;
|
||||
|
@ -760,4 +763,48 @@ public class HttpClientTLSTest
|
|||
assertEquals(0, serverBytes.get());
|
||||
assertEquals(0, clientBytes.get());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSSLEngineClosedDuringHandshake() throws Exception
|
||||
{
|
||||
SslContextFactory serverTLSFactory = createServerSslContextFactory();
|
||||
startServer(serverTLSFactory, new EmptyServerHandler());
|
||||
|
||||
SslContextFactory clientTLSFactory = createClientSslContextFactory();
|
||||
QueuedThreadPool clientThreads = new QueuedThreadPool();
|
||||
clientThreads.setName("client");
|
||||
client = new HttpClient(clientTLSFactory)
|
||||
{
|
||||
@Override
|
||||
protected ClientConnectionFactory newSslClientConnectionFactory(SslContextFactory sslContextFactory, ClientConnectionFactory connectionFactory)
|
||||
{
|
||||
if (sslContextFactory == null)
|
||||
sslContextFactory = getSslContextFactory();
|
||||
return new SslClientConnectionFactory(sslContextFactory, getByteBufferPool(), getExecutor(), connectionFactory)
|
||||
{
|
||||
@Override
|
||||
protected SslConnection newSslConnection(ByteBufferPool byteBufferPool, Executor executor, EndPoint endPoint, SSLEngine engine)
|
||||
{
|
||||
return new SslConnection(byteBufferPool, executor, endPoint, engine, isDirectBuffersForEncryption(), isDirectBuffersForDecryption())
|
||||
{
|
||||
@Override
|
||||
protected SSLEngineResult wrap(SSLEngine sslEngine, ByteBuffer[] input, ByteBuffer output) throws SSLException
|
||||
{
|
||||
sslEngine.closeOutbound();
|
||||
return super.wrap(sslEngine, input, output);
|
||||
}
|
||||
};
|
||||
}
|
||||
};
|
||||
}
|
||||
};
|
||||
client.setExecutor(clientThreads);
|
||||
client.start();
|
||||
|
||||
ExecutionException failure = assertThrows(ExecutionException.class, () -> client.newRequest("localhost", connector.getLocalPort())
|
||||
.scheme(HttpScheme.HTTPS.asString())
|
||||
.send());
|
||||
Throwable cause = failure.getCause();
|
||||
assertThat(cause, Matchers.instanceOf(SSLHandshakeException.class));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -378,6 +378,16 @@ public class SslConnection extends AbstractConnection implements Connection.Upgr
|
|||
_decryptedEndPoint.onFillableFail(cause == null ? new IOException() : cause);
|
||||
}
|
||||
|
||||
protected SSLEngineResult wrap(SSLEngine sslEngine, ByteBuffer[] input, ByteBuffer output) throws SSLException
|
||||
{
|
||||
return sslEngine.wrap(input, output);
|
||||
}
|
||||
|
||||
protected SSLEngineResult unwrap(SSLEngine sslEngine, ByteBuffer input, ByteBuffer output) throws SSLException
|
||||
{
|
||||
return sslEngine.unwrap(input, output);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toConnectionString()
|
||||
{
|
||||
|
@ -641,7 +651,7 @@ public class SslConnection extends AbstractConnection implements Connection.Upgr
|
|||
try
|
||||
{
|
||||
_underflown = false;
|
||||
unwrapResult = _sslEngine.unwrap(_encryptedInput, appIn);
|
||||
unwrapResult = unwrap(_sslEngine, _encryptedInput, appIn);
|
||||
}
|
||||
finally
|
||||
{
|
||||
|
@ -716,8 +726,8 @@ public class SslConnection extends AbstractConnection implements Connection.Upgr
|
|||
}
|
||||
catch (Throwable x)
|
||||
{
|
||||
Throwable failure = handleException(x, "fill");
|
||||
handshakeFailed(failure);
|
||||
Throwable f = handleException(x, "fill");
|
||||
Throwable failure = handshakeFailed(f);
|
||||
if (_flushState == FlushState.WAIT_FOR_FILL)
|
||||
{
|
||||
_flushState = FlushState.IDLE;
|
||||
|
@ -854,7 +864,7 @@ public class SslConnection extends AbstractConnection implements Connection.Upgr
|
|||
}
|
||||
}
|
||||
|
||||
private void handshakeFailed(Throwable failure)
|
||||
private Throwable handshakeFailed(Throwable failure)
|
||||
{
|
||||
if (_handshake.compareAndSet(HandshakeState.HANDSHAKE, HandshakeState.FAILED))
|
||||
{
|
||||
|
@ -864,6 +874,7 @@ public class SslConnection extends AbstractConnection implements Connection.Upgr
|
|||
failure = new SSLHandshakeException(failure.getMessage()).initCause(failure);
|
||||
notifyHandshakeFailed(_sslEngine, failure);
|
||||
}
|
||||
return failure;
|
||||
}
|
||||
|
||||
private void terminateInput()
|
||||
|
@ -978,7 +989,7 @@ public class SslConnection extends AbstractConnection implements Connection.Upgr
|
|||
SSLEngineResult wrapResult;
|
||||
try
|
||||
{
|
||||
wrapResult = _sslEngine.wrap(appOuts, _encryptedOutput);
|
||||
wrapResult = wrap(_sslEngine, appOuts, _encryptedOutput);
|
||||
}
|
||||
finally
|
||||
{
|
||||
|
@ -1057,8 +1068,7 @@ public class SslConnection extends AbstractConnection implements Connection.Upgr
|
|||
catch (Throwable x)
|
||||
{
|
||||
Throwable failure = handleException(x, "flush");
|
||||
handshakeFailed(failure);
|
||||
throw failure;
|
||||
throw handshakeFailed(failure);
|
||||
}
|
||||
finally
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue