SslHandler benchmark and SslEngine multiple packets benchmark
Motivation: We currently don't have a benchmark which includes SslHandler. The SslEngine benchmarks also always include a single TLS packet when encoding/decoding. In practice when reading data from the network there may be multiple TLS packets present and we should expand the benchmarks to understand this use case. Modifications: - SslEngine benchmarks should include wrapping/unwrapping of multiple TLS packets - Introduce SslHandler benchmarks which can also account for wrapping/unwrapping of multiple TLS packets Result: SslHandler and SslEngine benchmarks are more comprehensive.
This commit is contained in:
parent
53fc693901
commit
743d2d374c
@ -0,0 +1,308 @@
|
||||
/*
|
||||
* Copyright 2017 The Netty Project
|
||||
*
|
||||
* The Netty Project licenses this file to you under the Apache License, version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance with the License. You may obtain a
|
||||
* copy of the License at:
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software distributed under the License
|
||||
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
|
||||
* or implied. See the License for the specific language governing permissions and limitations under
|
||||
* the License.
|
||||
*/
|
||||
package io.netty.microbench.channel;
|
||||
|
||||
import io.netty.buffer.ByteBufAllocator;
|
||||
import io.netty.channel.Channel;
|
||||
import io.netty.channel.ChannelFuture;
|
||||
import io.netty.channel.ChannelHandler;
|
||||
import io.netty.channel.ChannelHandlerContext;
|
||||
import io.netty.channel.ChannelPipeline;
|
||||
import io.netty.channel.ChannelProgressivePromise;
|
||||
import io.netty.channel.ChannelPromise;
|
||||
import io.netty.channel.EventLoop;
|
||||
import io.netty.channel.embedded.EmbeddedChannel;
|
||||
import io.netty.util.Attribute;
|
||||
import io.netty.util.AttributeKey;
|
||||
import io.netty.util.ReferenceCountUtil;
|
||||
import io.netty.util.concurrent.EventExecutor;
|
||||
|
||||
import java.net.SocketAddress;
|
||||
|
||||
import static io.netty.util.internal.ObjectUtil.checkNotNull;
|
||||
|
||||
public abstract class EmbeddedChannelHandlerContext implements ChannelHandlerContext {
|
||||
private static final String HANDLER_NAME = "microbench-delegator-ctx";
|
||||
private final EventLoop eventLoop;
|
||||
private final Channel channel;
|
||||
private final ByteBufAllocator alloc;
|
||||
private final ChannelHandler handler;
|
||||
private SocketAddress localAddress;
|
||||
|
||||
protected EmbeddedChannelHandlerContext(ByteBufAllocator alloc, ChannelHandler handler, EmbeddedChannel channel) {
|
||||
this.alloc = checkNotNull(alloc, "alloc");
|
||||
this.channel = checkNotNull(channel, "channel");
|
||||
this.handler = checkNotNull(handler, "handler");
|
||||
eventLoop = checkNotNull(channel.eventLoop(), "eventLoop");
|
||||
}
|
||||
|
||||
protected abstract void handleException(Throwable t);
|
||||
|
||||
@Override
|
||||
public final <T> Attribute<T> attr(AttributeKey<T> key) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final <T> boolean hasAttr(AttributeKey<T> key) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final Channel channel() {
|
||||
return channel;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final EventExecutor executor() {
|
||||
return eventLoop;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final String name() {
|
||||
return HANDLER_NAME;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandler handler() {
|
||||
return handler;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final boolean isRemoved() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext fireChannelRegistered() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext fireChannelUnregistered() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext fireChannelActive() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext fireChannelInactive() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext fireExceptionCaught(Throwable cause) {
|
||||
try {
|
||||
handler().exceptionCaught(this, cause);
|
||||
} catch (Exception e) {
|
||||
handleException(e);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext fireUserEventTriggered(Object event) {
|
||||
ReferenceCountUtil.release(event);
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext fireChannelRead(Object msg) {
|
||||
ReferenceCountUtil.release(msg);
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext fireChannelReadComplete() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext fireChannelWritabilityChanged() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture bind(SocketAddress localAddress) {
|
||||
return bind(localAddress, newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture connect(SocketAddress remoteAddress) {
|
||||
return connect(remoteAddress, newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture connect(SocketAddress remoteAddress, SocketAddress localAddress) {
|
||||
return connect(remoteAddress, localAddress, newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture disconnect() {
|
||||
return disconnect(newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture close() {
|
||||
return close(newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture deregister() {
|
||||
return deregister(newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture bind(SocketAddress localAddress, ChannelPromise promise) {
|
||||
try {
|
||||
channel().bind(localAddress, promise);
|
||||
this.localAddress = localAddress;
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture connect(SocketAddress remoteAddress, ChannelPromise promise) {
|
||||
try {
|
||||
channel().connect(remoteAddress, localAddress, promise);
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture connect(SocketAddress remoteAddress, SocketAddress localAddress,
|
||||
ChannelPromise promise) {
|
||||
try {
|
||||
channel().connect(remoteAddress, localAddress, promise);
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture disconnect(ChannelPromise promise) {
|
||||
try {
|
||||
channel().disconnect(promise);
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture close(ChannelPromise promise) {
|
||||
try {
|
||||
channel().close(promise);
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture deregister(ChannelPromise promise) {
|
||||
try {
|
||||
channel().deregister(promise);
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext read() {
|
||||
try {
|
||||
channel().read();
|
||||
} catch (Exception e) {
|
||||
handleException(e);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture write(Object msg) {
|
||||
return channel().write(msg);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture write(Object msg, ChannelPromise promise) {
|
||||
return channel().write(msg, promise);
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelHandlerContext flush() {
|
||||
channel().flush();
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture writeAndFlush(Object msg, ChannelPromise promise) {
|
||||
return channel().writeAndFlush(msg, promise);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture writeAndFlush(Object msg) {
|
||||
return writeAndFlush(msg, newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelPipeline pipeline() {
|
||||
return channel().pipeline();
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ByteBufAllocator alloc() {
|
||||
return alloc;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelPromise newPromise() {
|
||||
return channel().newPromise();
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelProgressivePromise newProgressivePromise() {
|
||||
return channel().newProgressivePromise();
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture newSucceededFuture() {
|
||||
return channel().newSucceededFuture();
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture newFailedFuture(Throwable cause) {
|
||||
return channel().newFailedFuture(cause);
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelPromise voidPromise() {
|
||||
return channel().voidPromise();
|
||||
}
|
||||
}
|
@ -0,0 +1,103 @@
|
||||
/*
|
||||
* Copyright 2017 The Netty Project
|
||||
*
|
||||
* The Netty Project licenses this file to you under the Apache License, version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance with the License. You may obtain a
|
||||
* copy of the License at:
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software distributed under the License
|
||||
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
|
||||
* or implied. See the License for the specific language governing permissions and limitations under
|
||||
* the License.
|
||||
*/
|
||||
package io.netty.microbench.channel;
|
||||
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufAllocator;
|
||||
import io.netty.channel.ChannelFuture;
|
||||
import io.netty.channel.ChannelHandler;
|
||||
import io.netty.channel.ChannelPromise;
|
||||
import io.netty.channel.embedded.EmbeddedChannel;
|
||||
import io.netty.handler.codec.ByteToMessageDecoder;
|
||||
import io.netty.util.internal.ObjectUtil;
|
||||
|
||||
public abstract class EmbeddedChannelWriteAccumulatingHandlerContext extends EmbeddedChannelHandlerContext {
|
||||
private ByteBuf cumulation;
|
||||
private ByteToMessageDecoder.Cumulator cumulator;
|
||||
|
||||
protected EmbeddedChannelWriteAccumulatingHandlerContext(ByteBufAllocator alloc, ChannelHandler handler,
|
||||
ByteToMessageDecoder.Cumulator writeCumulator) {
|
||||
this(alloc, handler, writeCumulator, new EmbeddedChannel());
|
||||
}
|
||||
|
||||
protected EmbeddedChannelWriteAccumulatingHandlerContext(ByteBufAllocator alloc, ChannelHandler handler,
|
||||
ByteToMessageDecoder.Cumulator writeCumulator,
|
||||
EmbeddedChannel channel) {
|
||||
super(alloc, handler, channel);
|
||||
this.cumulator = ObjectUtil.checkNotNull(writeCumulator, "writeCumulator");
|
||||
}
|
||||
|
||||
public final ByteBuf cumulation() {
|
||||
return cumulation;
|
||||
}
|
||||
|
||||
public final void releaseCumulation() {
|
||||
if (cumulation != null) {
|
||||
cumulation.release();
|
||||
cumulation = null;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture write(Object msg) {
|
||||
return write(msg, newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture write(Object msg, ChannelPromise promise) {
|
||||
try {
|
||||
if (msg instanceof ByteBuf) {
|
||||
if (cumulation == null) {
|
||||
cumulation = (ByteBuf) msg;
|
||||
} else {
|
||||
cumulation = cumulator.cumulate(alloc(), cumulation, (ByteBuf) msg);
|
||||
}
|
||||
promise.setSuccess();
|
||||
} else {
|
||||
channel().write(msg, promise);
|
||||
}
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture writeAndFlush(Object msg, ChannelPromise promise) {
|
||||
try {
|
||||
if (msg instanceof ByteBuf) {
|
||||
ByteBuf buf = (ByteBuf) msg;
|
||||
if (cumulation == null) {
|
||||
cumulation = buf;
|
||||
} else {
|
||||
cumulation = cumulator.cumulate(alloc(), cumulation, buf);
|
||||
}
|
||||
promise.setSuccess();
|
||||
} else {
|
||||
channel().writeAndFlush(msg, promise);
|
||||
}
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final ChannelFuture writeAndFlush(Object msg) {
|
||||
return writeAndFlush(msg, newPromise());
|
||||
}
|
||||
}
|
@ -14,246 +14,32 @@
|
||||
*/
|
||||
package io.netty.microbench.channel;
|
||||
|
||||
import static io.netty.util.internal.ObjectUtil.checkNotNull;
|
||||
import io.netty.buffer.ByteBufAllocator;
|
||||
import io.netty.channel.Channel;
|
||||
import io.netty.channel.ChannelFuture;
|
||||
import io.netty.channel.ChannelHandler;
|
||||
import io.netty.channel.ChannelHandlerContext;
|
||||
import io.netty.channel.ChannelPipeline;
|
||||
import io.netty.channel.ChannelProgressivePromise;
|
||||
import io.netty.channel.ChannelPromise;
|
||||
import io.netty.channel.EventLoop;
|
||||
import io.netty.channel.embedded.EmbeddedChannel;
|
||||
import io.netty.util.Attribute;
|
||||
import io.netty.util.AttributeKey;
|
||||
import io.netty.util.ReferenceCounted;
|
||||
import io.netty.util.concurrent.EventExecutor;
|
||||
|
||||
import java.net.SocketAddress;
|
||||
|
||||
public abstract class EmbeddedChannelWriteReleaseHandlerContext implements ChannelHandlerContext {
|
||||
private static final String HANDLER_NAME = "microbench-delegator-ctx";
|
||||
private final EventLoop eventLoop;
|
||||
private final Channel channel;
|
||||
private final ByteBufAllocator alloc;
|
||||
private final ChannelHandler handler;
|
||||
private SocketAddress localAddress;
|
||||
|
||||
public EmbeddedChannelWriteReleaseHandlerContext(ByteBufAllocator alloc, ChannelHandler handler) {
|
||||
public abstract class EmbeddedChannelWriteReleaseHandlerContext extends EmbeddedChannelHandlerContext {
|
||||
protected EmbeddedChannelWriteReleaseHandlerContext(ByteBufAllocator alloc, ChannelHandler handler) {
|
||||
this(alloc, handler, new EmbeddedChannel());
|
||||
}
|
||||
|
||||
public EmbeddedChannelWriteReleaseHandlerContext(ByteBufAllocator alloc, ChannelHandler handler,
|
||||
protected EmbeddedChannelWriteReleaseHandlerContext(ByteBufAllocator alloc, ChannelHandler handler,
|
||||
EmbeddedChannel channel) {
|
||||
this.alloc = checkNotNull(alloc, "alloc");
|
||||
this.channel = checkNotNull(channel, "channel");
|
||||
this.handler = checkNotNull(handler, "handler");
|
||||
eventLoop = checkNotNull(channel.eventLoop(), "eventLoop");
|
||||
super(alloc, handler, channel);
|
||||
}
|
||||
|
||||
protected abstract void handleException(Throwable t);
|
||||
|
||||
@Override
|
||||
public <T> Attribute<T> attr(AttributeKey<T> key) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> boolean hasAttr(AttributeKey<T> key) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Channel channel() {
|
||||
return channel;
|
||||
}
|
||||
|
||||
@Override
|
||||
public EventExecutor executor() {
|
||||
return eventLoop;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String name() {
|
||||
return HANDLER_NAME;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandler handler() {
|
||||
return handler;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isRemoved() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext fireChannelRegistered() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext fireChannelUnregistered() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext fireChannelActive() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext fireChannelInactive() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext fireExceptionCaught(Throwable cause) {
|
||||
try {
|
||||
handler().exceptionCaught(this, cause);
|
||||
} catch (Exception e) {
|
||||
handleException(e);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext fireUserEventTriggered(Object event) {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext fireChannelRead(Object msg) {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext fireChannelReadComplete() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext fireChannelWritabilityChanged() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture bind(SocketAddress localAddress) {
|
||||
return bind(localAddress, newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture connect(SocketAddress remoteAddress) {
|
||||
return connect(remoteAddress, newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture connect(SocketAddress remoteAddress, SocketAddress localAddress) {
|
||||
return connect(remoteAddress, localAddress, newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture disconnect() {
|
||||
return disconnect(newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture close() {
|
||||
return close(newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture deregister() {
|
||||
return deregister(newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture bind(SocketAddress localAddress, ChannelPromise promise) {
|
||||
try {
|
||||
channel().bind(localAddress, promise);
|
||||
this.localAddress = localAddress;
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture connect(SocketAddress remoteAddress, ChannelPromise promise) {
|
||||
try {
|
||||
channel().connect(remoteAddress, localAddress, promise);
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture connect(SocketAddress remoteAddress, SocketAddress localAddress,
|
||||
ChannelPromise promise) {
|
||||
try {
|
||||
channel().connect(remoteAddress, localAddress, promise);
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture disconnect(ChannelPromise promise) {
|
||||
try {
|
||||
channel().disconnect(promise);
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture close(ChannelPromise promise) {
|
||||
try {
|
||||
channel().close(promise);
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture deregister(ChannelPromise promise) {
|
||||
try {
|
||||
channel().deregister(promise);
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext read() {
|
||||
try {
|
||||
channel().read();
|
||||
} catch (Exception e) {
|
||||
handleException(e);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture write(Object msg) {
|
||||
public final ChannelFuture write(Object msg) {
|
||||
return write(msg, newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture write(Object msg, ChannelPromise promise) {
|
||||
public final ChannelFuture write(Object msg, ChannelPromise promise) {
|
||||
try {
|
||||
if (msg instanceof ReferenceCounted) {
|
||||
((ReferenceCounted) msg).release();
|
||||
@ -269,53 +55,23 @@ public abstract class EmbeddedChannelWriteReleaseHandlerContext implements Chann
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelHandlerContext flush() {
|
||||
channel().flush();
|
||||
return this;
|
||||
public final ChannelFuture writeAndFlush(Object msg, ChannelPromise promise) {
|
||||
try {
|
||||
if (msg instanceof ReferenceCounted) {
|
||||
((ReferenceCounted) msg).release();
|
||||
promise.setSuccess();
|
||||
} else {
|
||||
channel().writeAndFlush(msg, promise);
|
||||
}
|
||||
} catch (Exception e) {
|
||||
promise.setFailure(e);
|
||||
handleException(e);
|
||||
}
|
||||
return promise;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture writeAndFlush(Object msg, ChannelPromise promise) {
|
||||
return channel().writeAndFlush(msg, promise);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture writeAndFlush(Object msg) {
|
||||
public final ChannelFuture writeAndFlush(Object msg) {
|
||||
return writeAndFlush(msg, newPromise());
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelPipeline pipeline() {
|
||||
return channel().pipeline();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ByteBufAllocator alloc() {
|
||||
return alloc;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelPromise newPromise() {
|
||||
return channel().newPromise();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelProgressivePromise newProgressivePromise() {
|
||||
return channel().newProgressivePromise();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture newSucceededFuture() {
|
||||
return channel().newSucceededFuture();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelFuture newFailedFuture(Throwable cause) {
|
||||
return channel().newFailedFuture(cause);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelPromise voidPromise() {
|
||||
return channel().voidPromise();
|
||||
}
|
||||
}
|
||||
|
@ -15,7 +15,7 @@
|
||||
*/
|
||||
package io.netty.microbench.handler.ssl;
|
||||
|
||||
import io.netty.buffer.PooledByteBufAllocator;
|
||||
import io.netty.buffer.ByteBufAllocator;
|
||||
import io.netty.handler.ssl.SslContext;
|
||||
import io.netty.handler.ssl.SslContextBuilder;
|
||||
import io.netty.handler.ssl.SslProvider;
|
||||
@ -25,11 +25,11 @@ import io.netty.util.ReferenceCountUtil;
|
||||
import io.netty.util.internal.PlatformDependent;
|
||||
import org.openjdk.jmh.annotations.Param;
|
||||
|
||||
import java.io.File;
|
||||
import java.nio.ByteBuffer;
|
||||
import javax.net.ssl.SSLEngine;
|
||||
import javax.net.ssl.SSLEngineResult;
|
||||
import javax.net.ssl.SSLException;
|
||||
import java.io.File;
|
||||
import java.nio.ByteBuffer;
|
||||
|
||||
|
||||
public class AbstractSslEngineBenchmark extends AbstractMicrobenchmark {
|
||||
@ -82,12 +82,12 @@ public class AbstractSslEngineBenchmark extends AbstractMicrobenchmark {
|
||||
}
|
||||
}
|
||||
|
||||
SSLEngine newClientEngine(String cipher) {
|
||||
return configureEngine(clientContext.newEngine(PooledByteBufAllocator.DEFAULT), cipher);
|
||||
SSLEngine newClientEngine(ByteBufAllocator allocator, String cipher) {
|
||||
return configureEngine(clientContext.newHandler(allocator).engine(), cipher);
|
||||
}
|
||||
|
||||
SSLEngine newServerEngine(String cipher) {
|
||||
return configureEngine(serverContext.newEngine(PooledByteBufAllocator.DEFAULT), cipher);
|
||||
SSLEngine newServerEngine(ByteBufAllocator allocator, String cipher) {
|
||||
return configureEngine(serverContext.newHandler(allocator).engine(), cipher);
|
||||
}
|
||||
|
||||
abstract SslProvider sslProvider();
|
||||
@ -142,9 +142,9 @@ public class AbstractSslEngineBenchmark extends AbstractMicrobenchmark {
|
||||
private ByteBuffer clientAppReadBuffer;
|
||||
private ByteBuffer empty;
|
||||
|
||||
protected final void initEngines() {
|
||||
clientEngine = newClientEngine();
|
||||
serverEngine = newServerEngine();
|
||||
protected final void initEngines(ByteBufAllocator allocator) {
|
||||
clientEngine = newClientEngine(allocator);
|
||||
serverEngine = newServerEngine(allocator);
|
||||
}
|
||||
|
||||
protected final void destroyEngines() {
|
||||
@ -241,15 +241,15 @@ public class AbstractSslEngineBenchmark extends AbstractMicrobenchmark {
|
||||
serverResult.getStatus() == SSLEngineResult.Status.OK;
|
||||
}
|
||||
|
||||
protected final SSLEngine newClientEngine() {
|
||||
return sslProvider.newClientEngine(cipher);
|
||||
protected final SSLEngine newClientEngine(ByteBufAllocator allocator) {
|
||||
return sslProvider.newClientEngine(allocator, cipher);
|
||||
}
|
||||
|
||||
protected final SSLEngine newServerEngine() {
|
||||
return sslProvider.newServerEngine(cipher);
|
||||
protected final SSLEngine newServerEngine(ByteBufAllocator allocator) {
|
||||
return sslProvider.newServerEngine(allocator, cipher);
|
||||
}
|
||||
|
||||
protected static boolean checkSslEngineResult(SSLEngineResult result, ByteBuffer src, ByteBuffer dst) {
|
||||
static boolean checkSslEngineResult(SSLEngineResult result, ByteBuffer src, ByteBuffer dst) {
|
||||
return result.getStatus() == SSLEngineResult.Status.OK && !src.hasRemaining() && dst.hasRemaining();
|
||||
}
|
||||
|
||||
|
@ -15,15 +15,17 @@
|
||||
*/
|
||||
package io.netty.microbench.handler.ssl;
|
||||
|
||||
import io.netty.util.internal.ThreadLocalRandom;
|
||||
import io.netty.buffer.ByteBufAllocator;
|
||||
import io.netty.buffer.PooledByteBufAllocator;
|
||||
import io.netty.util.internal.PlatformDependent;
|
||||
import org.openjdk.jmh.annotations.Level;
|
||||
import org.openjdk.jmh.annotations.Param;
|
||||
import org.openjdk.jmh.annotations.Setup;
|
||||
import org.openjdk.jmh.annotations.TearDown;
|
||||
|
||||
import java.nio.ByteBuffer;
|
||||
import javax.net.ssl.SSLEngineResult;
|
||||
import javax.net.ssl.SSLException;
|
||||
import java.nio.ByteBuffer;
|
||||
|
||||
public abstract class AbstractSslEngineThroughputBenchmark extends AbstractSslEngineBenchmark {
|
||||
|
||||
@ -35,14 +37,15 @@ public abstract class AbstractSslEngineThroughputBenchmark extends AbstractSslEn
|
||||
|
||||
@Setup(Level.Iteration)
|
||||
public final void setup() throws Exception {
|
||||
initEngines();
|
||||
ByteBufAllocator allocator = new PooledByteBufAllocator(true);
|
||||
initEngines(allocator);
|
||||
initHandshakeBuffers();
|
||||
|
||||
wrapDstBuffer = allocateBuffer(clientEngine.getSession().getPacketBufferSize());
|
||||
wrapDstBuffer = allocateBuffer(clientEngine.getSession().getPacketBufferSize() << 2);
|
||||
wrapSrcBuffer = allocateBuffer(messageSize);
|
||||
|
||||
byte[] bytes = new byte[messageSize];
|
||||
ThreadLocalRandom.current().nextBytes(bytes);
|
||||
PlatformDependent.threadLocalRandom().nextBytes(bytes);
|
||||
wrapSrcBuffer.put(bytes);
|
||||
wrapSrcBuffer.flip();
|
||||
|
||||
@ -66,14 +69,16 @@ public abstract class AbstractSslEngineThroughputBenchmark extends AbstractSslEn
|
||||
|
||||
protected void doTearDown() throws Exception { }
|
||||
|
||||
protected final ByteBuffer doWrap() throws SSLException {
|
||||
wrapSrcBuffer.position(0).limit(messageSize);
|
||||
|
||||
protected final ByteBuffer doWrap(int numWraps) throws SSLException {
|
||||
wrapDstBuffer.clear();
|
||||
|
||||
SSLEngineResult wrapResult = clientEngine.wrap(wrapSrcBuffer, wrapDstBuffer);
|
||||
for (int i = 0; i < numWraps; ++i) {
|
||||
wrapSrcBuffer.position(0).limit(messageSize);
|
||||
|
||||
assert checkSslEngineResult(wrapResult, wrapSrcBuffer, wrapDstBuffer);
|
||||
SSLEngineResult wrapResult = clientEngine.wrap(wrapSrcBuffer, wrapDstBuffer);
|
||||
|
||||
assert checkSslEngineResult(wrapResult, wrapSrcBuffer, wrapDstBuffer);
|
||||
}
|
||||
return wrapDstBuffer;
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,181 @@
|
||||
/*
|
||||
* Copyright 2017 The Netty Project
|
||||
*
|
||||
* The Netty Project licenses this file to you under the Apache License,
|
||||
* version 2.0 (the "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at:
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
* License for the specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package io.netty.microbench.handler.ssl;
|
||||
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufAllocator;
|
||||
import io.netty.channel.ChannelHandler;
|
||||
import io.netty.handler.codec.ByteToMessageDecoder;
|
||||
import io.netty.handler.ssl.SslContext;
|
||||
import io.netty.handler.ssl.SslContextBuilder;
|
||||
import io.netty.handler.ssl.SslHandler;
|
||||
import io.netty.handler.ssl.SslProvider;
|
||||
import io.netty.handler.ssl.util.InsecureTrustManagerFactory;
|
||||
import io.netty.microbench.channel.EmbeddedChannelWriteAccumulatingHandlerContext;
|
||||
import io.netty.microbench.util.AbstractMicrobenchmark;
|
||||
import io.netty.util.ReferenceCountUtil;
|
||||
import org.openjdk.jmh.annotations.Param;
|
||||
|
||||
import java.io.File;
|
||||
import javax.net.ssl.SSLEngine;
|
||||
import javax.net.ssl.SSLException;
|
||||
|
||||
import static io.netty.handler.codec.ByteToMessageDecoder.COMPOSITE_CUMULATOR;
|
||||
import static org.junit.Assert.assertNull;
|
||||
|
||||
public class AbstractSslHandlerBenchmark extends AbstractMicrobenchmark {
|
||||
private static final String PROTOCOL_TLS_V1_2 = "TLSv1.2";
|
||||
|
||||
public enum SslEngineProvider {
|
||||
JDK {
|
||||
@Override
|
||||
SslProvider sslProvider() {
|
||||
return SslProvider.JDK;
|
||||
}
|
||||
},
|
||||
OPENSSL {
|
||||
@Override
|
||||
SslProvider sslProvider() {
|
||||
return SslProvider.OPENSSL;
|
||||
}
|
||||
},
|
||||
OPENSSL_REFCNT {
|
||||
@Override
|
||||
SslProvider sslProvider() {
|
||||
return SslProvider.OPENSSL_REFCNT;
|
||||
}
|
||||
};
|
||||
private final SslContext clientContext = newClientContext();
|
||||
private final SslContext serverContext = newServerContext();
|
||||
|
||||
private SslContext newClientContext() {
|
||||
try {
|
||||
return SslContextBuilder.forClient()
|
||||
.sslProvider(sslProvider())
|
||||
.trustManager(InsecureTrustManagerFactory.INSTANCE)
|
||||
.build();
|
||||
} catch (SSLException e) {
|
||||
throw new IllegalStateException(e);
|
||||
}
|
||||
}
|
||||
|
||||
private SslContext newServerContext() {
|
||||
try {
|
||||
File keyFile = new File(getClass().getResource("test_unencrypted.pem").getFile());
|
||||
File crtFile = new File(getClass().getResource("test.crt").getFile());
|
||||
|
||||
return SslContextBuilder.forServer(crtFile, keyFile)
|
||||
.sslProvider(sslProvider())
|
||||
.build();
|
||||
} catch (Exception e) {
|
||||
throw new IllegalStateException(e);
|
||||
}
|
||||
}
|
||||
|
||||
SslHandler newClientHandler(ByteBufAllocator allocator, String cipher) {
|
||||
SslHandler handler = clientContext.newHandler(allocator);
|
||||
configureEngine(handler.engine(), cipher);
|
||||
return handler;
|
||||
}
|
||||
|
||||
SslHandler newServerHandler(ByteBufAllocator allocator, String cipher) {
|
||||
SslHandler handler = serverContext.newHandler(allocator);
|
||||
configureEngine(handler.engine(), cipher);
|
||||
return handler;
|
||||
}
|
||||
|
||||
abstract SslProvider sslProvider();
|
||||
|
||||
static SSLEngine configureEngine(SSLEngine engine, String cipher) {
|
||||
engine.setEnabledProtocols(new String[]{ PROTOCOL_TLS_V1_2 });
|
||||
engine.setEnabledCipherSuites(new String[]{ cipher });
|
||||
return engine;
|
||||
}
|
||||
}
|
||||
|
||||
@Param
|
||||
public SslEngineProvider sslProvider;
|
||||
|
||||
// Includes cipher required by HTTP/2
|
||||
@Param({ "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256", "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256" })
|
||||
public String cipher;
|
||||
|
||||
protected SslHandler clientSslHandler;
|
||||
protected SslHandler serverSslHandler;
|
||||
protected EmbeddedChannelWriteAccumulatingHandlerContext clientCtx;
|
||||
protected EmbeddedChannelWriteAccumulatingHandlerContext serverCtx;
|
||||
|
||||
protected final void initSslHandlers(ByteBufAllocator allocator) {
|
||||
clientSslHandler = newClientHandler(allocator);
|
||||
serverSslHandler = newServerHandler(allocator);
|
||||
clientCtx = new SslThroughputBenchmarkHandlerContext(allocator, clientSslHandler, COMPOSITE_CUMULATOR);
|
||||
serverCtx = new SslThroughputBenchmarkHandlerContext(allocator, serverSslHandler, COMPOSITE_CUMULATOR);
|
||||
}
|
||||
|
||||
protected final void destroySslHandlers() {
|
||||
try {
|
||||
if (clientSslHandler != null) {
|
||||
ReferenceCountUtil.release(clientSslHandler.engine());
|
||||
}
|
||||
} finally {
|
||||
if (serverSslHandler != null) {
|
||||
ReferenceCountUtil.release(serverSslHandler.engine());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected final void doHandshake() throws Exception {
|
||||
serverSslHandler.handlerAdded(serverCtx);
|
||||
clientSslHandler.handlerAdded(clientCtx);
|
||||
do {
|
||||
ByteBuf clientCumulation = clientCtx.cumulation();
|
||||
if (clientCumulation != null) {
|
||||
serverSslHandler.channelRead(serverCtx, clientCumulation.retain());
|
||||
clientCtx.releaseCumulation();
|
||||
}
|
||||
ByteBuf serverCumulation = serverCtx.cumulation();
|
||||
if (serverCumulation != null) {
|
||||
clientSslHandler.channelRead(clientCtx, serverCumulation.retain());
|
||||
serverCtx.releaseCumulation();
|
||||
}
|
||||
} while (!clientSslHandler.handshakeFuture().isDone() || !serverSslHandler.handshakeFuture().isDone());
|
||||
}
|
||||
|
||||
protected final SslHandler newClientHandler(ByteBufAllocator allocator) {
|
||||
return sslProvider.newClientHandler(allocator, cipher);
|
||||
}
|
||||
|
||||
protected final SslHandler newServerHandler(ByteBufAllocator allocator) {
|
||||
return sslProvider.newServerHandler(allocator, cipher);
|
||||
}
|
||||
|
||||
private static final class SslThroughputBenchmarkHandlerContext extends
|
||||
EmbeddedChannelWriteAccumulatingHandlerContext {
|
||||
SslThroughputBenchmarkHandlerContext(ByteBufAllocator alloc, ChannelHandler handler,
|
||||
ByteToMessageDecoder.Cumulator writeCumulator) {
|
||||
super(alloc, handler, writeCumulator);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void handleException(Throwable t) {
|
||||
handleUnexpectedException(t);
|
||||
}
|
||||
}
|
||||
|
||||
public static void handleUnexpectedException(Throwable t) {
|
||||
assertNull(t);
|
||||
}
|
||||
}
|
@ -0,0 +1,94 @@
|
||||
/*
|
||||
* Copyright 2017 The Netty Project
|
||||
*
|
||||
* The Netty Project licenses this file to you under the Apache License, version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance with the License. You may obtain a
|
||||
* copy of the License at:
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software distributed under the License
|
||||
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
|
||||
* or implied. See the License for the specific language governing permissions and limitations under
|
||||
* the License.
|
||||
*/
|
||||
package io.netty.microbench.handler.ssl;
|
||||
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufAllocator;
|
||||
import io.netty.buffer.PooledByteBufAllocator;
|
||||
import io.netty.channel.embedded.EmbeddedChannel;
|
||||
import io.netty.util.internal.PlatformDependent;
|
||||
import org.openjdk.jmh.annotations.Level;
|
||||
import org.openjdk.jmh.annotations.Param;
|
||||
import org.openjdk.jmh.annotations.Setup;
|
||||
import org.openjdk.jmh.annotations.TearDown;
|
||||
|
||||
public abstract class AbstractSslHandlerThroughputBenchmark extends AbstractSslHandlerBenchmark {
|
||||
@Param({ "64", "128", "512", "1024", "4096" })
|
||||
public int messageSize;
|
||||
|
||||
@Param
|
||||
public BufferType bufferType;
|
||||
|
||||
public enum BufferType {
|
||||
HEAP {
|
||||
@Override
|
||||
ByteBuf newBuffer(ByteBufAllocator allocator, int size) {
|
||||
return allocator.heapBuffer(size);
|
||||
}
|
||||
},
|
||||
DIRECT {
|
||||
@Override
|
||||
ByteBuf newBuffer(ByteBufAllocator allocator, int size) {
|
||||
return allocator.directBuffer(size);
|
||||
}
|
||||
};
|
||||
|
||||
abstract ByteBuf newBuffer(ByteBufAllocator allocator, int size);
|
||||
}
|
||||
|
||||
protected ByteBuf wrapSrcBuffer;
|
||||
protected EmbeddedChannel channel;
|
||||
private ByteBufAllocator allocator;
|
||||
|
||||
@Setup(Level.Iteration)
|
||||
public final void setup() throws Exception {
|
||||
allocator = new PooledByteBufAllocator(true);
|
||||
|
||||
initSslHandlers(allocator);
|
||||
|
||||
wrapSrcBuffer = allocateBuffer(messageSize);
|
||||
|
||||
byte[] bytes = new byte[messageSize];
|
||||
PlatformDependent.threadLocalRandom().nextBytes(bytes);
|
||||
wrapSrcBuffer.writeBytes(bytes);
|
||||
|
||||
// Complete the initial TLS handshake.
|
||||
doHandshake();
|
||||
}
|
||||
|
||||
@TearDown(Level.Iteration)
|
||||
public final void tearDown() throws Exception {
|
||||
destroySslHandlers();
|
||||
wrapSrcBuffer.release();
|
||||
clientCtx.releaseCumulation();
|
||||
serverCtx.releaseCumulation();
|
||||
}
|
||||
|
||||
protected final ByteBuf allocateBuffer(int size) {
|
||||
return bufferType.newBuffer(allocator, size);
|
||||
}
|
||||
|
||||
protected final ByteBuf doWrite(int numWrites) throws Exception {
|
||||
clientCtx.releaseCumulation();
|
||||
|
||||
for (int i = 0; i < numWrites; ++i) {
|
||||
ByteBuf wrapSrcBuffer = this.wrapSrcBuffer.retainedSlice();
|
||||
|
||||
clientSslHandler.write(clientCtx, wrapSrcBuffer, clientCtx.voidPromise());
|
||||
}
|
||||
clientSslHandler.flush(clientCtx);
|
||||
return clientCtx.cumulation().retainedSlice();
|
||||
}
|
||||
}
|
@ -16,23 +16,26 @@
|
||||
package io.netty.microbench.handler.ssl;
|
||||
|
||||
import org.openjdk.jmh.annotations.Benchmark;
|
||||
import org.openjdk.jmh.annotations.Param;
|
||||
import org.openjdk.jmh.annotations.Scope;
|
||||
import org.openjdk.jmh.annotations.State;
|
||||
import org.openjdk.jmh.annotations.Threads;
|
||||
|
||||
import java.nio.ByteBuffer;
|
||||
import javax.net.ssl.SSLEngineResult;
|
||||
import javax.net.ssl.SSLException;
|
||||
import java.nio.ByteBuffer;
|
||||
|
||||
@State(Scope.Benchmark)
|
||||
@Threads(1)
|
||||
public class SslEngineEchoBenchmark extends AbstractSslEngineThroughputBenchmark {
|
||||
|
||||
@Param({ "1", "2", "5", "10" })
|
||||
public int numWraps;
|
||||
private ByteBuffer unwrapDstBuffer;
|
||||
|
||||
@Override
|
||||
protected void doSetup() {
|
||||
unwrapDstBuffer = allocateBuffer(serverEngine.getSession().getApplicationBufferSize());
|
||||
unwrapDstBuffer = allocateBuffer(serverEngine.getSession().getApplicationBufferSize() << 2);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -42,12 +45,15 @@ public class SslEngineEchoBenchmark extends AbstractSslEngineThroughputBenchmark
|
||||
|
||||
@Benchmark
|
||||
public ByteBuffer wrapUnwrap() throws SSLException {
|
||||
ByteBuffer src = doWrap();
|
||||
ByteBuffer src = doWrap(numWraps);
|
||||
src.flip();
|
||||
|
||||
unwrapDstBuffer.clear();
|
||||
|
||||
SSLEngineResult unwrapResult = serverEngine.unwrap(src, unwrapDstBuffer);
|
||||
SSLEngineResult unwrapResult;
|
||||
do {
|
||||
unwrapResult = serverEngine.unwrap(src, unwrapDstBuffer);
|
||||
} while (unwrapResult.getStatus() == SSLEngineResult.Status.OK && src.hasRemaining());
|
||||
|
||||
assert checkSslEngineResult(unwrapResult, src, unwrapDstBuffer);
|
||||
return unwrapDstBuffer;
|
||||
|
@ -15,6 +15,8 @@
|
||||
*/
|
||||
package io.netty.microbench.handler.ssl;
|
||||
|
||||
import io.netty.buffer.ByteBufAllocator;
|
||||
import io.netty.buffer.PooledByteBufAllocator;
|
||||
import org.openjdk.jmh.annotations.Benchmark;
|
||||
import org.openjdk.jmh.annotations.BenchmarkMode;
|
||||
import org.openjdk.jmh.annotations.Level;
|
||||
@ -32,10 +34,13 @@ import java.util.concurrent.TimeUnit;
|
||||
@Threads(1)
|
||||
public class SslEngineHandshakeBenchmark extends AbstractSslEngineBenchmark {
|
||||
|
||||
private ByteBufAllocator allocator;
|
||||
|
||||
@Setup(Level.Iteration)
|
||||
public void setup() {
|
||||
allocator = new PooledByteBufAllocator(true);
|
||||
// Init an engine one time and create the buffers needed for an handshake so we can use them in the benchmark
|
||||
initEngines();
|
||||
initEngines(allocator);
|
||||
initHandshakeBuffers();
|
||||
destroyEngines();
|
||||
}
|
||||
@ -49,7 +54,7 @@ public class SslEngineHandshakeBenchmark extends AbstractSslEngineBenchmark {
|
||||
@BenchmarkMode(Mode.AverageTime)
|
||||
@OutputTimeUnit(TimeUnit.MICROSECONDS)
|
||||
public boolean handshake() throws Exception {
|
||||
initEngines();
|
||||
initEngines(allocator);
|
||||
boolean ok = doHandshake();
|
||||
destroyEngines();
|
||||
assert ok;
|
||||
|
@ -15,21 +15,24 @@
|
||||
*/
|
||||
package io.netty.microbench.handler.ssl;
|
||||
|
||||
import javax.net.ssl.SSLException;
|
||||
|
||||
import org.openjdk.jmh.annotations.Benchmark;
|
||||
import org.openjdk.jmh.annotations.Param;
|
||||
import org.openjdk.jmh.annotations.Scope;
|
||||
import org.openjdk.jmh.annotations.State;
|
||||
import org.openjdk.jmh.annotations.Threads;
|
||||
|
||||
import java.nio.ByteBuffer;
|
||||
import javax.net.ssl.SSLException;
|
||||
|
||||
@State(Scope.Benchmark)
|
||||
@Threads(1)
|
||||
public class SslEngineWrapBenchmark extends AbstractSslEngineThroughputBenchmark {
|
||||
|
||||
@Param({ "1", "2", "5", "10" })
|
||||
public int numWraps;
|
||||
|
||||
@Benchmark
|
||||
public ByteBuffer wrap() throws SSLException {
|
||||
return doWrap();
|
||||
return doWrap(numWraps);
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,38 @@
|
||||
/*
|
||||
* Copyright 2017 The Netty Project
|
||||
*
|
||||
* The Netty Project licenses this file to you under the Apache License,
|
||||
* version 2.0 (the "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at:
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
* License for the specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package io.netty.microbench.handler.ssl;
|
||||
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import org.openjdk.jmh.annotations.Benchmark;
|
||||
import org.openjdk.jmh.annotations.Param;
|
||||
|
||||
public class SslHandlerEchoBenchmark extends AbstractSslHandlerThroughputBenchmark {
|
||||
@Param({ "1", "2", "5", "10" })
|
||||
public int numWrites;
|
||||
|
||||
@Benchmark
|
||||
public ByteBuf wrapUnwrap() throws Exception {
|
||||
ByteBuf src = doWrite(numWrites);
|
||||
|
||||
do {
|
||||
serverSslHandler.channelRead(serverCtx, src);
|
||||
} while (src.isReadable());
|
||||
|
||||
assert !src.isReadable() && src.refCnt() == 1 : "src: " + src + " src.refCnt(): " + src.refCnt();
|
||||
|
||||
return src;
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user