SSL / BlockHound works out of the box with the default SSL provider (#9969)
Motivation: JDK is the default SSL provider and internally uses blocking IO operations. Modifications: Add allowBlockingCallsInside configuration for SslHandler runAllDelegate function. Result: When BlockHound is installed, SSL works out of the box with the default SSL provider. Co-authored-by: violetagg <milesg78@gmail.com>
This commit is contained in:
parent
b49bd5644f
commit
0671b18e24
@ -65,6 +65,16 @@ class Hidden {
|
||||
"confirmShutdown"
|
||||
);
|
||||
|
||||
builder.allowBlockingCallsInside(
|
||||
"io.netty.handler.ssl.SslHandler",
|
||||
"handshake"
|
||||
);
|
||||
|
||||
builder.allowBlockingCallsInside(
|
||||
"io.netty.handler.ssl.SslHandler",
|
||||
"runAllDelegatedTasks"
|
||||
);
|
||||
|
||||
builder.nonBlockingThreadPredicate(new Function<Predicate<Thread>, Predicate<Thread>>() {
|
||||
@Override
|
||||
public Predicate<Thread> apply(final Predicate<Thread> p) {
|
||||
|
@ -934,7 +934,7 @@ public class SslHandlerTest {
|
||||
}
|
||||
}
|
||||
|
||||
private void testHandshakeWithExecutor(Executor executor) throws Exception {
|
||||
private static void testHandshakeWithExecutor(Executor executor) throws Exception {
|
||||
final SslContext sslClientCtx = SslContextBuilder.forClient()
|
||||
.trustManager(InsecureTrustManagerFactory.INSTANCE)
|
||||
.sslProvider(SslProvider.JDK).build();
|
||||
@ -991,7 +991,7 @@ public class SslHandlerTest {
|
||||
testHandshakeTimeoutBecauseExecutorNotExecute(false);
|
||||
}
|
||||
|
||||
private void testHandshakeTimeoutBecauseExecutorNotExecute(final boolean client) throws Exception {
|
||||
private static void testHandshakeTimeoutBecauseExecutorNotExecute(final boolean client) throws Exception {
|
||||
final SslContext sslClientCtx = SslContextBuilder.forClient()
|
||||
.trustManager(InsecureTrustManagerFactory.INSTANCE)
|
||||
.sslProvider(SslProvider.JDK).build();
|
||||
|
@ -46,6 +46,8 @@
|
||||
<properties>
|
||||
<maven.compiler.source>1.8</maven.compiler.source>
|
||||
<maven.compiler.target>1.8</maven.compiler.target>
|
||||
<!-- Needed for SelfSignedCertificate -->
|
||||
<argLine.java9.extras>--add-exports java.base/sun.security.x509=ALL-UNNAMED</argLine.java9.extras>
|
||||
<skipJapicmp>true</skipJapicmp>
|
||||
</properties>
|
||||
|
||||
@ -55,7 +57,17 @@
|
||||
<artifactId>netty-transport</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>${project.groupId}</groupId>
|
||||
<artifactId>netty-handler</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.bouncycastle</groupId>
|
||||
<artifactId>bcpkix-jdk15on</artifactId>
|
||||
<optional>true</optional>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>io.projectreactor.tools</groupId>
|
||||
<artifactId>blockhound</artifactId>
|
||||
|
@ -15,15 +15,41 @@
|
||||
*/
|
||||
package io.netty.util.internal;
|
||||
|
||||
import io.netty.bootstrap.Bootstrap;
|
||||
import io.netty.bootstrap.ServerBootstrap;
|
||||
import io.netty.buffer.UnpooledByteBufAllocator;
|
||||
import io.netty.channel.Channel;
|
||||
import io.netty.channel.ChannelFuture;
|
||||
import io.netty.channel.ChannelHandlerContext;
|
||||
import io.netty.channel.ChannelInboundHandlerAdapter;
|
||||
import io.netty.channel.ChannelInitializer;
|
||||
import io.netty.channel.EventLoopGroup;
|
||||
import io.netty.channel.nio.NioEventLoopGroup;
|
||||
import io.netty.channel.socket.nio.NioServerSocketChannel;
|
||||
import io.netty.channel.socket.nio.NioSocketChannel;
|
||||
import io.netty.handler.ssl.SslContext;
|
||||
import io.netty.handler.ssl.SslContextBuilder;
|
||||
import io.netty.handler.ssl.SslHandler;
|
||||
import io.netty.handler.ssl.SslHandshakeCompletionEvent;
|
||||
import io.netty.handler.ssl.SslProvider;
|
||||
import io.netty.handler.ssl.util.InsecureTrustManagerFactory;
|
||||
import io.netty.handler.ssl.util.SelfSignedCertificate;
|
||||
import io.netty.util.ReferenceCountUtil;
|
||||
import io.netty.util.concurrent.GlobalEventExecutor;
|
||||
import io.netty.util.concurrent.ImmediateEventExecutor;
|
||||
import io.netty.util.concurrent.ImmediateExecutor;
|
||||
import io.netty.util.internal.Hidden.NettyBlockHoundIntegration;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Test;
|
||||
import reactor.blockhound.BlockHound;
|
||||
import reactor.blockhound.integration.BlockHoundIntegration;
|
||||
|
||||
import java.net.InetSocketAddress;
|
||||
import java.util.ServiceLoader;
|
||||
import java.util.concurrent.ExecutionException;
|
||||
import java.util.concurrent.Executor;
|
||||
import java.util.concurrent.ExecutorService;
|
||||
import java.util.concurrent.Executors;
|
||||
import java.util.concurrent.FutureTask;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
@ -66,4 +92,89 @@ public class NettyBlockHoundIntegrationTest {
|
||||
assertTrue("Blocking call was reported", throwable.getMessage().contains("Blocking call"));
|
||||
}
|
||||
}
|
||||
|
||||
// Tests copied from io.netty.handler.ssl.SslHandlerTest
|
||||
@Test
|
||||
public void testHandshakeWithExecutorThatExecuteDirectory() throws Exception {
|
||||
testHandshakeWithExecutor(Runnable::run);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHandshakeWithImmediateExecutor() throws Exception {
|
||||
testHandshakeWithExecutor(ImmediateExecutor.INSTANCE);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHandshakeWithImmediateEventExecutor() throws Exception {
|
||||
testHandshakeWithExecutor(ImmediateEventExecutor.INSTANCE);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHandshakeWithExecutor() throws Exception {
|
||||
ExecutorService executorService = Executors.newCachedThreadPool();
|
||||
try {
|
||||
testHandshakeWithExecutor(executorService);
|
||||
} finally {
|
||||
executorService.shutdown();
|
||||
}
|
||||
}
|
||||
|
||||
private static void testHandshakeWithExecutor(Executor executor) throws Exception {
|
||||
final SslContext sslClientCtx = SslContextBuilder.forClient()
|
||||
.trustManager(InsecureTrustManagerFactory.INSTANCE)
|
||||
.sslProvider(SslProvider.JDK).build();
|
||||
|
||||
final SelfSignedCertificate cert = new SelfSignedCertificate();
|
||||
final SslContext sslServerCtx = SslContextBuilder.forServer(cert.key(), cert.cert())
|
||||
.sslProvider(SslProvider.JDK).build();
|
||||
|
||||
EventLoopGroup group = new NioEventLoopGroup();
|
||||
Channel sc = null;
|
||||
Channel cc = null;
|
||||
final SslHandler clientSslHandler = sslClientCtx.newHandler(UnpooledByteBufAllocator.DEFAULT, executor);
|
||||
final SslHandler serverSslHandler = sslServerCtx.newHandler(UnpooledByteBufAllocator.DEFAULT, executor);
|
||||
|
||||
try {
|
||||
sc = new ServerBootstrap()
|
||||
.group(group)
|
||||
.channel(NioServerSocketChannel.class)
|
||||
.childHandler(serverSslHandler)
|
||||
.bind(new InetSocketAddress(0)).syncUninterruptibly().channel();
|
||||
|
||||
ChannelFuture future = new Bootstrap()
|
||||
.group(group)
|
||||
.channel(NioSocketChannel.class)
|
||||
.handler(new ChannelInitializer<Channel>() {
|
||||
@Override
|
||||
protected void initChannel(Channel ch) {
|
||||
ch.pipeline()
|
||||
.addLast(clientSslHandler)
|
||||
.addLast(new ChannelInboundHandlerAdapter() {
|
||||
|
||||
@Override
|
||||
public void userEventTriggered(ChannelHandlerContext ctx, Object evt) {
|
||||
if (evt instanceof SslHandshakeCompletionEvent &&
|
||||
((SslHandshakeCompletionEvent) evt).cause() != null) {
|
||||
((SslHandshakeCompletionEvent) evt).cause().printStackTrace();
|
||||
}
|
||||
ctx.fireUserEventTriggered(evt);
|
||||
}
|
||||
});
|
||||
}
|
||||
}).connect(sc.localAddress());
|
||||
cc = future.syncUninterruptibly().channel();
|
||||
|
||||
assertTrue(clientSslHandler.handshakeFuture().await().isSuccess());
|
||||
assertTrue(serverSslHandler.handshakeFuture().await().isSuccess());
|
||||
} finally {
|
||||
if (cc != null) {
|
||||
cc.close().syncUninterruptibly();
|
||||
}
|
||||
if (sc != null) {
|
||||
sc.close().syncUninterruptibly();
|
||||
}
|
||||
group.shutdownGracefully();
|
||||
ReferenceCountUtil.release(sslClientCtx);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user