1*6777b538SAndroid Build Coastguard Worker // Copyright 2013 The Chromium Authors 2*6777b538SAndroid Build Coastguard Worker // Use of this source code is governed by a BSD-style license that can be 3*6777b538SAndroid Build Coastguard Worker // found in the LICENSE file. 4*6777b538SAndroid Build Coastguard Worker 5*6777b538SAndroid Build Coastguard Worker #ifndef NET_WEBSOCKETS_WEBSOCKET_DEFLATE_STREAM_H_ 6*6777b538SAndroid Build Coastguard Worker #define NET_WEBSOCKETS_WEBSOCKET_DEFLATE_STREAM_H_ 7*6777b538SAndroid Build Coastguard Worker 8*6777b538SAndroid Build Coastguard Worker #include <stddef.h> 9*6777b538SAndroid Build Coastguard Worker 10*6777b538SAndroid Build Coastguard Worker #include <memory> 11*6777b538SAndroid Build Coastguard Worker #include <string> 12*6777b538SAndroid Build Coastguard Worker #include <vector> 13*6777b538SAndroid Build Coastguard Worker 14*6777b538SAndroid Build Coastguard Worker #include "base/memory/scoped_refptr.h" 15*6777b538SAndroid Build Coastguard Worker #include "net/base/completion_once_callback.h" 16*6777b538SAndroid Build Coastguard Worker #include "net/base/net_export.h" 17*6777b538SAndroid Build Coastguard Worker #include "net/log/net_log_with_source.h" 18*6777b538SAndroid Build Coastguard Worker #include "net/websockets/websocket_deflater.h" 19*6777b538SAndroid Build Coastguard Worker #include "net/websockets/websocket_frame.h" 20*6777b538SAndroid Build Coastguard Worker #include "net/websockets/websocket_inflater.h" 21*6777b538SAndroid Build Coastguard Worker #include "net/websockets/websocket_stream.h" 22*6777b538SAndroid Build Coastguard Worker 23*6777b538SAndroid Build Coastguard Worker namespace net { 24*6777b538SAndroid Build Coastguard Worker 25*6777b538SAndroid Build Coastguard Worker class WebSocketDeflateParameters; 26*6777b538SAndroid Build Coastguard Worker class WebSocketDeflatePredictor; 27*6777b538SAndroid Build Coastguard Worker class IOBufferWithSize; 28*6777b538SAndroid Build Coastguard Worker class NetLogWithSource; 29*6777b538SAndroid Build Coastguard Worker 30*6777b538SAndroid Build Coastguard Worker // WebSocketDeflateStream is a WebSocketStream subclass. 31*6777b538SAndroid Build Coastguard Worker // WebSocketDeflateStream is for permessage-deflate WebSocket extension[1]. 32*6777b538SAndroid Build Coastguard Worker // 33*6777b538SAndroid Build Coastguard Worker // WebSocketDeflateStream::ReadFrames and WriteFrames may change frame 34*6777b538SAndroid Build Coastguard Worker // boundary. In particular, if a control frame is placed in the middle of 35*6777b538SAndroid Build Coastguard Worker // data message frames, the control frame can overtake data frames. 36*6777b538SAndroid Build Coastguard Worker // Say there are frames df1, df2 and cf, df1 and df2 are frames of a 37*6777b538SAndroid Build Coastguard Worker // data message and cf is a control message frame. cf may arrive first and 38*6777b538SAndroid Build Coastguard Worker // data frames may follow cf. 39*6777b538SAndroid Build Coastguard Worker // Note that message boundary will be preserved, i.e. if the last frame of 40*6777b538SAndroid Build Coastguard Worker // a message m1 is read / written before the last frame of a message m2, 41*6777b538SAndroid Build Coastguard Worker // WebSocketDeflateStream will respect the order. 42*6777b538SAndroid Build Coastguard Worker // 43*6777b538SAndroid Build Coastguard Worker // [1]: http://tools.ietf.org/html/draft-ietf-hybi-permessage-compression-12 44*6777b538SAndroid Build Coastguard Worker class NET_EXPORT_PRIVATE WebSocketDeflateStream : public WebSocketStream { 45*6777b538SAndroid Build Coastguard Worker public: 46*6777b538SAndroid Build Coastguard Worker WebSocketDeflateStream(std::unique_ptr<WebSocketStream> stream, 47*6777b538SAndroid Build Coastguard Worker const WebSocketDeflateParameters& params, 48*6777b538SAndroid Build Coastguard Worker std::unique_ptr<WebSocketDeflatePredictor> predictor); 49*6777b538SAndroid Build Coastguard Worker 50*6777b538SAndroid Build Coastguard Worker WebSocketDeflateStream(const WebSocketDeflateStream&) = delete; 51*6777b538SAndroid Build Coastguard Worker WebSocketDeflateStream& operator=(const WebSocketDeflateStream&) = delete; 52*6777b538SAndroid Build Coastguard Worker 53*6777b538SAndroid Build Coastguard Worker ~WebSocketDeflateStream() override; 54*6777b538SAndroid Build Coastguard Worker 55*6777b538SAndroid Build Coastguard Worker // WebSocketStream functions. 56*6777b538SAndroid Build Coastguard Worker int ReadFrames(std::vector<std::unique_ptr<WebSocketFrame>>* frames, 57*6777b538SAndroid Build Coastguard Worker CompletionOnceCallback callback) override; 58*6777b538SAndroid Build Coastguard Worker int WriteFrames(std::vector<std::unique_ptr<WebSocketFrame>>* frames, 59*6777b538SAndroid Build Coastguard Worker CompletionOnceCallback callback) override; 60*6777b538SAndroid Build Coastguard Worker void Close() override; 61*6777b538SAndroid Build Coastguard Worker std::string GetSubProtocol() const override; 62*6777b538SAndroid Build Coastguard Worker std::string GetExtensions() const override; 63*6777b538SAndroid Build Coastguard Worker const NetLogWithSource& GetNetLogWithSource() const override; 64*6777b538SAndroid Build Coastguard Worker 65*6777b538SAndroid Build Coastguard Worker private: 66*6777b538SAndroid Build Coastguard Worker enum ReadingState { 67*6777b538SAndroid Build Coastguard Worker READING_COMPRESSED_MESSAGE, 68*6777b538SAndroid Build Coastguard Worker READING_UNCOMPRESSED_MESSAGE, 69*6777b538SAndroid Build Coastguard Worker NOT_READING, 70*6777b538SAndroid Build Coastguard Worker }; 71*6777b538SAndroid Build Coastguard Worker 72*6777b538SAndroid Build Coastguard Worker enum WritingState { 73*6777b538SAndroid Build Coastguard Worker WRITING_COMPRESSED_MESSAGE, 74*6777b538SAndroid Build Coastguard Worker WRITING_UNCOMPRESSED_MESSAGE, 75*6777b538SAndroid Build Coastguard Worker WRITING_POSSIBLY_COMPRESSED_MESSAGE, 76*6777b538SAndroid Build Coastguard Worker NOT_WRITING, 77*6777b538SAndroid Build Coastguard Worker }; 78*6777b538SAndroid Build Coastguard Worker 79*6777b538SAndroid Build Coastguard Worker // Handles asynchronous completion of ReadFrames() call on |stream_|. 80*6777b538SAndroid Build Coastguard Worker void OnReadComplete(std::vector<std::unique_ptr<WebSocketFrame>>* frames, 81*6777b538SAndroid Build Coastguard Worker int result); 82*6777b538SAndroid Build Coastguard Worker 83*6777b538SAndroid Build Coastguard Worker // This function deflates |frames| and stores the result to |frames| itself. 84*6777b538SAndroid Build Coastguard Worker int Deflate(std::vector<std::unique_ptr<WebSocketFrame>>* frames); 85*6777b538SAndroid Build Coastguard Worker void OnMessageStart( 86*6777b538SAndroid Build Coastguard Worker const std::vector<std::unique_ptr<WebSocketFrame>>& frames, 87*6777b538SAndroid Build Coastguard Worker size_t index); 88*6777b538SAndroid Build Coastguard Worker int AppendCompressedFrame( 89*6777b538SAndroid Build Coastguard Worker const WebSocketFrameHeader& header, 90*6777b538SAndroid Build Coastguard Worker std::vector<std::unique_ptr<WebSocketFrame>>* frames_to_write); 91*6777b538SAndroid Build Coastguard Worker int AppendPossiblyCompressedMessage( 92*6777b538SAndroid Build Coastguard Worker std::vector<std::unique_ptr<WebSocketFrame>>* frames, 93*6777b538SAndroid Build Coastguard Worker std::vector<std::unique_ptr<WebSocketFrame>>* frames_to_write); 94*6777b538SAndroid Build Coastguard Worker 95*6777b538SAndroid Build Coastguard Worker // This function inflates |frames| and stores the result to |frames| itself. 96*6777b538SAndroid Build Coastguard Worker int Inflate(std::vector<std::unique_ptr<WebSocketFrame>>* frames); 97*6777b538SAndroid Build Coastguard Worker 98*6777b538SAndroid Build Coastguard Worker int InflateAndReadIfNecessary( 99*6777b538SAndroid Build Coastguard Worker std::vector<std::unique_ptr<WebSocketFrame>>* frames); 100*6777b538SAndroid Build Coastguard Worker 101*6777b538SAndroid Build Coastguard Worker const std::unique_ptr<WebSocketStream> stream_; 102*6777b538SAndroid Build Coastguard Worker WebSocketDeflater deflater_; 103*6777b538SAndroid Build Coastguard Worker WebSocketInflater inflater_; 104*6777b538SAndroid Build Coastguard Worker ReadingState reading_state_ = NOT_READING; 105*6777b538SAndroid Build Coastguard Worker WritingState writing_state_ = NOT_WRITING; 106*6777b538SAndroid Build Coastguard Worker WebSocketFrameHeader::OpCode current_reading_opcode_ = 107*6777b538SAndroid Build Coastguard Worker WebSocketFrameHeader::kOpCodeText; 108*6777b538SAndroid Build Coastguard Worker WebSocketFrameHeader::OpCode current_writing_opcode_ = 109*6777b538SAndroid Build Coastguard Worker WebSocketFrameHeader::kOpCodeText; 110*6777b538SAndroid Build Coastguard Worker std::unique_ptr<WebSocketDeflatePredictor> predictor_; 111*6777b538SAndroid Build Coastguard Worker 112*6777b538SAndroid Build Coastguard Worker // User callback saved for asynchronous reads. 113*6777b538SAndroid Build Coastguard Worker CompletionOnceCallback read_callback_; 114*6777b538SAndroid Build Coastguard Worker 115*6777b538SAndroid Build Coastguard Worker // References of Deflater outputs kept until next WriteFrames(). 116*6777b538SAndroid Build Coastguard Worker std::vector<scoped_refptr<IOBufferWithSize>> deflater_outputs_; 117*6777b538SAndroid Build Coastguard Worker // References of Inflater outputs kept until next ReadFrames(). 118*6777b538SAndroid Build Coastguard Worker std::vector<scoped_refptr<IOBufferWithSize>> inflater_outputs_; 119*6777b538SAndroid Build Coastguard Worker }; 120*6777b538SAndroid Build Coastguard Worker 121*6777b538SAndroid Build Coastguard Worker } // namespace net 122*6777b538SAndroid Build Coastguard Worker 123*6777b538SAndroid Build Coastguard Worker #endif // NET_WEBSOCKETS_WEBSOCKET_DEFLATE_STREAM_H_ 124