2016-03-22 11 views
0

Netty 4.0を使用していて、通常の動作を説明するReference counted objects guideを読んだことがありますが、例外が発生した場合、どうすればByteBufをリリースするのか分かりません。nettyバッファを安全に解放する方法は?

例:

protected void encode(ChannelHandlerContext ctx, Object msg, List<Object> out) throws Exception { 
    ByteBuf buf = null; 
    if (msg instanceof HttpMessage) { 
     if (state != ST_INIT) { 
      throw new IllegalStateException("unexpected message type: " + StringUtil.simpleClassName(msg)); 
     } 

     @SuppressWarnings({ "unchecked", "CastConflictsWithInstanceof" }) 
     H m = (H) msg; 

     buf = ctx.alloc().buffer(); 
     // Encode the message. 
     encodeInitialLine(buf, m);// 
     encodeHeaders(m.headers(), buf); 
     buf.writeBytes(CRLF); 
     state = HttpHeaders.isTransferEncodingChunked(m) ? ST_CONTENT_CHUNK : ST_CONTENT_NON_CHUNK; 
    } 

    // Bypass the encoder in case of an empty buffer, so that the following idiom works: 
    // 
    //  ch.write(Unpooled.EMPTY_BUFFER).addListener(ChannelFutureListener.CLOSE); 
    // 
    // See https://github.com/netty/netty/issues/2983 for more information. 

    if (msg instanceof ByteBuf && !((ByteBuf) msg).isReadable()) { 
     out.add(EMPTY_BUFFER); 
     return; 
    } 

    if (msg instanceof HttpContent || msg instanceof ByteBuf || msg instanceof FileRegion) { 

     if (state == ST_INIT) { 
      throw new IllegalStateException("unexpected message type: " + StringUtil.simpleClassName(msg)); 
     } 

     final long contentLength = contentLength(msg); 
     if (state == ST_CONTENT_NON_CHUNK) { 
      if (contentLength > 0) { 
       if (buf != null && buf.writableBytes() >= contentLength && msg instanceof HttpContent) { 
        // merge into other buffer for performance reasons 
        buf.writeBytes(((HttpContent) msg).content()); 
        out.add(buf); 
       } else { 
        if (buf != null) { 
         out.add(buf); 
        } 
        out.add(encodeAndRetain(msg)); 
       } 
      } else { 
       if (buf != null) { 
        out.add(buf); 
       } else { 
        // Need to produce some output otherwise an 
        // IllegalStateException will be thrown 
        out.add(EMPTY_BUFFER); 
       } 
      } 

      if (msg instanceof LastHttpContent) { 
       state = ST_INIT; 
      } 
     } else if (state == ST_CONTENT_CHUNK) { 
      if (buf != null) { 
       out.add(buf); 
      } 
      encodeChunkedContent(ctx, msg, contentLength, out); 
     } else { 
      throw new Error(); 
     } 
    } else { 
     if (buf != null) { 
      out.add(buf); 
     } 
    } 
} 

encodeInitialLine(buf, m);が例外をスローした場合、どのように私はbufを解放するのですか?

答えて

1

try-finallyブロックでメソッド全体をラップし、finallyブロックでbufがnullかどうかを確認する必要があります。 nullでない場合は、buf.release()を呼び出します。

protected void encode(ChannelHandlerContext ctx, Object msg, List<Object> out) throws Exception { 
    ByteBuf buf = null; 
    try { 
     ... 
    } finally { 
     if (buf != null) { 
      buf.release(); 
     } 
    } 
} 
+0

bufがwriteAndFlushに準備されているとき、これをどう対処するのですか? – wangbin

+0

'writeAndFlush'を使って送信すると、' writeAndFlush(buf.retain()) ' – Ferrybig

関連する問題