diff --git a/websocket-sharp/Ext.cs b/websocket-sharp/Ext.cs index cb6565fc1..d0d560c0d 100644 --- a/websocket-sharp/Ext.cs +++ b/websocket-sharp/Ext.cs @@ -69,6 +69,7 @@ public static class Ext private static readonly byte[] _last = new byte[] { 0x00 }; private static readonly int _retry = 5; private const string _tspecials = "()<>@,;:\\\"/[]?={} \t"; + private static UTF8Encoding _utf8 = new UTF8Encoding (false, true); #endregion @@ -156,7 +157,7 @@ internal static byte[] Append (this ushort code, string reason) var ret = code.InternalToByteArray (ByteOrder.Big); if (reason != null && reason.Length > 0) { var buff = new List (ret); - buff.AddRange (Encoding.UTF8.GetBytes (reason)); + buff.AddRange (_utf8.GetBytes (reason)); ret = buff.ToArray (); } @@ -496,18 +497,14 @@ internal static bool IsPortNumber (this int value) internal static bool IsReserved (this ushort code) { - return code == 1004 - || code == 1005 - || code == 1006 - || code == 1015; + return !( (code > 999 && code < 1004) + || (code > 1006 && code < 1012) + || (code > 2999 && code < 5000) ); } internal static bool IsReserved (this CloseStatusCode code) { - return code == CloseStatusCode.Undefined - || code == CloseStatusCode.NoStatus - || code == CloseStatusCode.Abnormal - || code == CloseStatusCode.TlsHandshakeFailure; + return IsReserved ((ushort)code); } internal static bool IsSupported (this byte opcode) @@ -961,7 +958,7 @@ internal static bool TryGetUTF8DecodedString (this byte[] bytes, out string s) s = null; try { - s = Encoding.UTF8.GetString (bytes); + s = _utf8.GetString (bytes); } catch { return false; @@ -975,7 +972,7 @@ internal static bool TryGetUTF8EncodedBytes (this string s, out byte[] bytes) bytes = null; try { - bytes = Encoding.UTF8.GetBytes (s); + bytes = _utf8.GetBytes (s); } catch { return false; @@ -1018,17 +1015,12 @@ internal static string Unquote (this string value) internal static string UTF8Decode (this byte[] bytes) { - try { - return Encoding.UTF8.GetString (bytes); - } - catch { - return null; - } + return _utf8.GetString (bytes); } internal static byte[] UTF8Encode (this string s) { - return Encoding.UTF8.GetBytes (s); + return _utf8.GetBytes (s); } internal static void WriteBytes (this Stream stream, byte[] bytes, int bufferLength) diff --git a/websocket-sharp/MessageEventArgs.cs b/websocket-sharp/MessageEventArgs.cs index adf7391aa..445283425 100644 --- a/websocket-sharp/MessageEventArgs.cs +++ b/websocket-sharp/MessageEventArgs.cs @@ -61,6 +61,7 @@ internal MessageEventArgs (WebSocketFrame frame) { _opcode = frame.Opcode; _rawData = frame.PayloadData.ApplicationData; + setData (); } internal MessageEventArgs (Opcode opcode, byte[] rawData) @@ -70,6 +71,7 @@ internal MessageEventArgs (Opcode opcode, byte[] rawData) _opcode = opcode; _rawData = rawData; + setData (); } #endregion @@ -103,7 +105,6 @@ internal Opcode Opcode { /// public string Data { get { - setData (); return _data; } } @@ -152,7 +153,6 @@ public bool IsText { /// public byte[] RawData { get { - setData (); return _rawData; } } diff --git a/websocket-sharp/WebSocket.cs b/websocket-sharp/WebSocket.cs index 7effc8852..5cca863bb 100644 --- a/websocket-sharp/WebSocket.cs +++ b/websocket-sharp/WebSocket.cs @@ -1065,6 +1065,11 @@ private bool checkReceivedFrame (WebSocketFrame frame, out string message) return false; } + if (frame.Opcode == 0x0 && !_inContinuation) { + message = "A continuation frame has been received but there is nothing to continue."; + return false; + } + if (frame.Rsv2 == Rsv.On) { message = "The RSV2 of a frame is non-zero without any negotiation for it."; return false; @@ -1575,8 +1580,19 @@ private bool ping (byte[] data) private bool processCloseFrame (WebSocketFrame frame) { - var payload = frame.PayloadData; - close (payload, !payload.HasReservedCode, false, true); + try { + PayloadData payload; + + if (frame.PayloadData.Length > 1) + payload = new PayloadData (frame.PayloadData.Code, frame.PayloadData.Reason); + else + payload = frame.PayloadData; + + close (payload, !payload.HasReservedCode, false, true); + } + catch { + close (1002, String.Empty); + } return false; }