From 2a5adc0b2bce398b821b491c2f8a49562ecb1567 Mon Sep 17 00:00:00 2001 From: Matthias Einwag Date: Fri, 26 Sep 2014 22:47:27 +0200 Subject: [PATCH] Send a websocket close frame with status code when receiving invalid frames Motivation: According to the websocket specification peers may send a close frame when they detect a protocol violation (with status code 1002). The current implementation simply closes the connection. This update should add this functionality. The functionality is optional - but it might help other implementations with debugging when they receive such a frame. Modification: When a protocol violation in the decoder is detected and a close was not already initiated by the remote peer a close frame is sent. Result: Remotes which will send an invalid frame will now get a close frame that indicates the protocol violation instead of only seeing a closed connection. --- .../codec/http/websocketx/WebSocket08FrameDecoder.java | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/codec-http/src/main/java/io/netty/handler/codec/http/websocketx/WebSocket08FrameDecoder.java b/codec-http/src/main/java/io/netty/handler/codec/http/websocketx/WebSocket08FrameDecoder.java index 454415a827..ea911d3f78 100644 --- a/codec-http/src/main/java/io/netty/handler/codec/http/websocketx/WebSocket08FrameDecoder.java +++ b/codec-http/src/main/java/io/netty/handler/codec/http/websocketx/WebSocket08FrameDecoder.java @@ -300,8 +300,8 @@ public class WebSocket08FrameDecoder extends ByteToMessageDecoder return; } if (frameOpcode == OPCODE_CLOSE) { - checkCloseFrameBody(ctx, payloadBuffer); receivedClosingHandshake = true; + checkCloseFrameBody(ctx, payloadBuffer); out.add(new CloseWebSocketFrame(frameFinalFlag, frameRsv, payloadBuffer)); payloadBuffer = null; return; @@ -368,7 +368,13 @@ public class WebSocket08FrameDecoder extends ByteToMessageDecoder private void protocolViolation(ChannelHandlerContext ctx, CorruptedFrameException ex) { state = State.CORRUPT; if (ctx.channel().isActive()) { - ctx.writeAndFlush(Unpooled.EMPTY_BUFFER).addListener(ChannelFutureListener.CLOSE); + Object closeMessage; + if (receivedClosingHandshake) { + closeMessage = Unpooled.EMPTY_BUFFER; + } else { + closeMessage = new CloseWebSocketFrame(1002, null); + } + ctx.writeAndFlush(closeMessage).addListener(ChannelFutureListener.CLOSE); } throw ex; }