From 1fcd19a28fbab687eb2be65ad3535d1564d656cc Mon Sep 17 00:00:00 2001 From: Trustin Lee Date: Sat, 21 Dec 2013 19:56:36 +0900 Subject: [PATCH] Fix a bug where adaptive recvbuf size prediction doesn't work correctly when maxMessagesPerRead is > 1 --- .../channel/nio/AbstractNioByteChannel.java | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) diff --git a/transport/src/main/java/io/netty/channel/nio/AbstractNioByteChannel.java b/transport/src/main/java/io/netty/channel/nio/AbstractNioByteChannel.java index 78006538c8..535ebd255e 100644 --- a/transport/src/main/java/io/netty/channel/nio/AbstractNioByteChannel.java +++ b/transport/src/main/java/io/netty/channel/nio/AbstractNioByteChannel.java @@ -110,8 +110,10 @@ public abstract class AbstractNioByteChannel extends AbstractNioChannel { int messages = 0; boolean close = false; try { + int byteBufCapacity = allocHandle.guess(); + int totalReadAmount = 0; do { - byteBuf = allocHandle.allocate(allocator); + byteBuf = allocator.ioBuffer(byteBufCapacity); int writable = byteBuf.writableBytes(); int localReadAmount = doReadBytes(byteBuf); if (localReadAmount <= 0) { @@ -120,16 +122,26 @@ public abstract class AbstractNioByteChannel extends AbstractNioChannel { close = localReadAmount < 0; break; } + pipeline.fireChannelRead(byteBuf); byteBuf = null; - allocHandle.record(localReadAmount); + + if (totalReadAmount >= Integer.MAX_VALUE - localReadAmount) { + // Avoid overflow. + totalReadAmount = Integer.MAX_VALUE; + break; + } + + totalReadAmount += localReadAmount; if (localReadAmount < writable) { - // we read less then what the buffer can hold so it seems like we drained it completely + // Read less than what the buffer can hold, + // which might mean we drained the recv buffer completely. break; } } while (++ messages < maxMessagesPerRead); pipeline.fireChannelReadComplete(); + allocHandle.record(totalReadAmount); if (close) { closeOnRead(pipeline);