websocket_frame_parser.h 3.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091
  1. // Copyright (c) 2012 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #ifndef NET_WEBSOCKETS_WEBSOCKET_FRAME_PARSER_H_
  5. #define NET_WEBSOCKETS_WEBSOCKET_FRAME_PARSER_H_
  6. #include <stddef.h>
  7. #include <stdint.h>
  8. #include <memory>
  9. #include <vector>
  10. #include "base/containers/span.h"
  11. #include "net/base/net_export.h"
  12. #include "net/websockets/websocket_errors.h"
  13. #include "net/websockets/websocket_frame.h"
  14. namespace net {
  15. // Parses WebSocket frames from byte stream.
  16. //
  17. // Specification of WebSocket frame format is available at
  18. // <http://tools.ietf.org/html/rfc6455#section-5>.
  19. // This class does *NOT* unmask frame payload.
  20. class NET_EXPORT WebSocketFrameParser {
  21. public:
  22. WebSocketFrameParser();
  23. WebSocketFrameParser(const WebSocketFrameParser&) = delete;
  24. WebSocketFrameParser& operator=(const WebSocketFrameParser&) = delete;
  25. ~WebSocketFrameParser();
  26. // Decodes the given byte stream and stores parsed WebSocket frames in
  27. // |frame_chunks|.
  28. // Each WebSocketFrameChunk's payload is a subspan of [data, data + length).
  29. // Thus callers must take care of its lifecycle.
  30. //
  31. // If the parser encounters invalid payload length format, Decode() fails
  32. // and returns false. Once Decode() has failed, the parser refuses to decode
  33. // any more data and future invocations of Decode() will simply return false.
  34. //
  35. // Payload data of parsed WebSocket frames may be incomplete; see comments in
  36. // websocket_frame.h for more details.
  37. bool Decode(const char* data,
  38. size_t length,
  39. std::vector<std::unique_ptr<WebSocketFrameChunk>>* frame_chunks);
  40. // Returns kWebSocketNormalClosure if the parser has not failed to decode
  41. // WebSocket frames. Otherwise returns WebSocketError which is defined in
  42. // websocket_errors.h. We can convert net::WebSocketError to net::Error by
  43. // using WebSocketErrorToNetError().
  44. WebSocketError websocket_error() const { return websocket_error_; }
  45. private:
  46. // Tries to decode a frame header from |data|.
  47. // If successful, this function updates
  48. // |current_frame_header_|, and |masking_key_| (if available) and returns
  49. // the number of consumed bytes in |data|.
  50. // If there is not enough data in the remaining buffer to parse a frame
  51. // header, this function returns 0 without doing anything.
  52. // This function may update |websocket_error_| if it observes a corrupt frame.
  53. size_t DecodeFrameHeader(base::span<const char> data);
  54. // Decodes frame payload and creates a WebSocketFrameChunk object.
  55. // This function updates |frame_offset_| after
  56. // parsing. This function returns a frame object even if no payload data is
  57. // available at this moment, so the receiver could make use of frame header
  58. // information. If the end of frame is reached, this function clears
  59. // |current_frame_header_|, |frame_offset_| and |masking_key_|.
  60. std::unique_ptr<WebSocketFrameChunk> DecodeFramePayload(
  61. bool first_chunk,
  62. base::span<const char>* data);
  63. // Internal buffer to store the data to parse header.
  64. std::vector<char> incomplete_header_buffer_;
  65. // Frame header and masking key of the current frame.
  66. // |masking_key_| is filled with zeros if the current frame is not masked.
  67. std::unique_ptr<WebSocketFrameHeader> current_frame_header_;
  68. // Amount of payload data read so far for the current frame.
  69. uint64_t frame_offset_ = 0;
  70. WebSocketError websocket_error_ = kWebSocketNormalClosure;
  71. };
  72. } // namespace net
  73. #endif // NET_WEBSOCKETS_WEBSOCKET_FRAME_PARSER_H_