我使用Netty IO(4.0.29 Final)来解码来自TCP服务器的字节。在我的管道的第一个位置,我使用LengthFieldBasedFrameDecoder来分割帧中的字节(这个处理程序工作正常)。在我的管道的第二个位置,我实现了我自己的处理程序,扩展了Netty的ByteToMessageDecoder。
在这个自定义处理程序中,我想做几个动作:
基于字节#14和#15聚合帧,它们分别代表段号和段总数(所以当段号等于段总计数时,我的缓冲区已完成,它可以发送到下一个处理程序)。
private ByteBuf aggregate;
private short lastSegmentId;
@Override
protected void decode(ChannelHandlerContext ctx, ByteBuf in,
List<Object> out) throws Exception
{
String hexDump = ByteBufUtil.hexDump(in);
RecordingService.record(hexDump);
in = in.order(ByteOrder.LITTLE_ENDIAN);
byte segId = in.getByte(14);
byte segCnt = in.getByte(15);
int readableBytes = in.readableBytes();
int sum = 0;
for (int index = 0; index < readableBytes-2; index++)
{
short s = in.readUnsignedByte();
sum += s;
}
int checksum = in.readUnsignedShort();
if (sum == checksum)
{
//
// Checksum correct
//
if (segId == (lastSegmentId + 1))
{
lastSegmentId = segId;
byte[] byteArray = new byte[readableBytes-18];
in.getBytes(16, byteArray, 0, readableBytes-18);
aggregate.writeBytes(byteArray);
if (lastSegmentId == segCnt)
{
aggregate.readerIndex(0);
out.add(aggregate.copy());
lastSegmentId = 0;
aggregate.clear();
}
else
{
lastSegmentId = 0;
aggregate.clear();
}
}
else
{
//
// Checksum not correct
//
}
}
}
这个自定义处理程序可以正常工作,但它会及时消耗大量内存,几个小时后,我的程序中出现了“OutOfMemoryError:java heap space”。
我使用Java VisualVM来监视我的程序,我发现名为“nioEventLoopGroup-2-1”的netty线程占用了大量内存。如果我评论十六进制转储和代码进行聚合,则内存消耗会大幅减少。
Netty thread memory consumption
我认为我的代码导致了问题,但我找不到解决方案。
你能帮我理解什么是错的吗?
感谢。