| // Copyright 2015 The Chromium Authors. All rights reserved. | 
 | // Use of this source code is governed by a BSD-style license that can be | 
 | // found in the LICENSE file. | 
 |  | 
 | #ifndef NET_HTTP_BIDIRECTIONAL_STREAM_IMPL_H_ | 
 | #define NET_HTTP_BIDIRECTIONAL_STREAM_IMPL_H_ | 
 |  | 
 | #include <memory> | 
 | #include <vector> | 
 |  | 
 | #include "base/macros.h" | 
 | #include "base/memory/ref_counted.h" | 
 | #include "net/base/load_timing_info.h" | 
 | #include "net/base/net_export.h" | 
 | #include "net/socket/next_proto.h" | 
 | #include "net/traffic_annotation/network_traffic_annotation.h" | 
 | #include "starboard/types.h" | 
 |  | 
 | namespace base { | 
 | class OneShotTimer; | 
 | }  // namespace base | 
 |  | 
 | namespace spdy { | 
 | class SpdyHeaderBlock; | 
 | }  // namespace spdy | 
 |  | 
 | namespace net { | 
 |  | 
 | class IOBuffer; | 
 | class NetLogWithSource; | 
 | struct BidirectionalStreamRequestInfo; | 
 | struct NetErrorDetails; | 
 |  | 
 | // Exposes an interface to do HTTP/2 bidirectional streaming. | 
 | // Note that only one ReadData or SendData should be in flight until the | 
 | // operation completes synchronously or asynchronously. | 
 | // BidirectionalStreamImpl once created by HttpStreamFactory should be owned | 
 | // by BidirectionalStream. | 
 | class NET_EXPORT_PRIVATE BidirectionalStreamImpl { | 
 |  public: | 
 |   // Delegate to handle BidirectionalStreamImpl events. | 
 |   class NET_EXPORT_PRIVATE Delegate { | 
 |    public: | 
 |     Delegate(); | 
 |  | 
 |     // Called when the stream is ready for reading and writing. | 
 |     // The delegate may call BidirectionalStreamImpl::ReadData to start reading, | 
 |     // call BidirectionalStreamImpl::SendData to send data, | 
 |     // or call BidirectionalStreamImpl::Cancel to cancel the stream. | 
 |     // The delegate should not call BidirectionalStreamImpl::Cancel | 
 |     // during this callback. | 
 |     // |request_headers_sent| if true, request headers have been sent. If false, | 
 |     // SendRequestHeaders() needs to be explicitly called. | 
 |     virtual void OnStreamReady(bool request_headers_sent) = 0; | 
 |  | 
 |     // Called when response headers are received. | 
 |     // This is called at most once for the lifetime of a stream. | 
 |     // The delegate may call BidirectionalStreamImpl::ReadData to start | 
 |     // reading, call BidirectionalStreamImpl::SendData to send data, | 
 |     // or call BidirectionalStreamImpl::Cancel to cancel the stream. | 
 |     virtual void OnHeadersReceived( | 
 |         const spdy::SpdyHeaderBlock& response_headers) = 0; | 
 |  | 
 |     // Called when read is completed asynchronously. |bytes_read| specifies how | 
 |     // much data is available. | 
 |     // The delegate may call BidirectionalStreamImpl::ReadData to continue | 
 |     // reading, call BidirectionalStreamImpl::SendData to send data, | 
 |     // or call BidirectionalStreamImpl::Cancel to cancel the stream. | 
 |     virtual void OnDataRead(int bytes_read) = 0; | 
 |  | 
 |     // Called when the entire buffer passed through SendData is sent. | 
 |     // The delegate may call BidirectionalStreamImpl::ReadData to continue | 
 |     // reading, or call BidirectionalStreamImpl::SendData to send data. | 
 |     // The delegate should not call BidirectionalStreamImpl::Cancel | 
 |     // during this callback. | 
 |     virtual void OnDataSent() = 0; | 
 |  | 
 |     // Called when trailers are received. This is called as soon as trailers | 
 |     // are received, which can happen before a read completes. | 
 |     // The delegate is able to continue reading if there is no pending read and | 
 |     // EOF has not been received, or to send data if there is no pending send. | 
 |     virtual void OnTrailersReceived(const spdy::SpdyHeaderBlock& trailers) = 0; | 
 |  | 
 |     // Called when an error occurred. Do not call into the stream after this | 
 |     // point. No other delegate functions will be called after this. | 
 |     virtual void OnFailed(int status) = 0; | 
 |  | 
 |    protected: | 
 |     virtual ~Delegate(); | 
 |  | 
 |    private: | 
 |     DISALLOW_COPY_AND_ASSIGN(Delegate); | 
 |   }; | 
 |  | 
 |   BidirectionalStreamImpl(); | 
 |  | 
 |   // |this| should not be destroyed during Delegate::OnHeadersSent or | 
 |   // Delegate::OnDataSent. | 
 |   virtual ~BidirectionalStreamImpl(); | 
 |  | 
 |   // Starts the BidirectionalStreamImpl and sends request headers. | 
 |   // |send_request_headers_automatically| if true, request headers will be sent | 
 |   // automatically when stream is negotiated. If false, request headers will be | 
 |   // sent only when SendRequestHeaders() is invoked or with next | 
 |   // SendData/SendvData. | 
 |   virtual void Start(const BidirectionalStreamRequestInfo* request_info, | 
 |                      const NetLogWithSource& net_log, | 
 |                      bool send_request_headers_automatically, | 
 |                      BidirectionalStreamImpl::Delegate* delegate, | 
 |                      std::unique_ptr<base::OneShotTimer> timer, | 
 |                      const NetworkTrafficAnnotationTag& traffic_annotation) = 0; | 
 |  | 
 |   // Sends request headers to server. | 
 |   // When |send_request_headers_automatically_| is | 
 |   // false and OnStreamReady() is invoked with request_headers_sent = false, | 
 |   // headers will be combined with next SendData/SendvData unless this | 
 |   // method is called first, in which case headers will be sent separately | 
 |   // without delay. | 
 |   // (This method cannot be called when |send_request_headers_automatically_| is | 
 |   // true nor when OnStreamReady() is invoked with request_headers_sent = true, | 
 |   // since headers have been sent by the stream when stream is negotiated | 
 |   // successfully.) | 
 |   virtual void SendRequestHeaders() = 0; | 
 |  | 
 |   // Reads at most |buf_len| bytes into |buf|. Returns the number of bytes read, | 
 |   // ERR_IO_PENDING if the read is to be completed asynchronously, or an error | 
 |   // code if any error occurred. If returns 0, there is no more data to read. | 
 |   // This should not be called before Delegate::OnHeadersReceived is invoked, | 
 |   // and should not be called again unless it returns with number greater than | 
 |   // 0 or until Delegate::OnDataRead is invoked. | 
 |   virtual int ReadData(IOBuffer* buf, int buf_len) = 0; | 
 |  | 
 |   // Sends data. This should not be called be called before | 
 |   // Delegate::OnHeadersSent is invoked, and should not be called again until | 
 |   // Delegate::OnDataSent is invoked. If |end_stream| is true, the DATA frame | 
 |   // will have an END_STREAM flag. | 
 |   virtual void SendvData(const std::vector<scoped_refptr<IOBuffer>>& buffers, | 
 |                          const std::vector<int>& lengths, | 
 |                          bool end_stream) = 0; | 
 |  | 
 |   // Returns the protocol used by this stream. If stream has not been | 
 |   // established, return kProtoUnknown. | 
 |   virtual NextProto GetProtocol() const = 0; | 
 |  | 
 |   // Total number of bytes received over the network of SPDY data, headers, and | 
 |   // push_promise frames associated with this stream, including the size of | 
 |   // frame headers, after SSL decryption and not including proxy overhead. | 
 |   virtual int64_t GetTotalReceivedBytes() const = 0; | 
 |  | 
 |   // Total number of bytes sent over the network of SPDY frames associated with | 
 |   // this stream, including the size of frame headers, before SSL encryption and | 
 |   // not including proxy overhead. Note that some SPDY frames such as pings are | 
 |   // not associated with any stream, and are not included in this value. | 
 |   virtual int64_t GetTotalSentBytes() const = 0; | 
 |  | 
 |   // Populates the connection establishment part of |load_timing_info|, and | 
 |   // socket reuse info. Return true if LoadTimingInfo is obtained successfully | 
 |   // and false otherwise. | 
 |   virtual bool GetLoadTimingInfo(LoadTimingInfo* load_timing_info) const = 0; | 
 |  | 
 |   // Get the network error details this stream is encountering. | 
 |   // Fills in |details| if it is available; leaves |details| unchanged if it | 
 |   // is unavailable. | 
 |   virtual void PopulateNetErrorDetails(NetErrorDetails* details) = 0; | 
 |  | 
 |  private: | 
 |   DISALLOW_COPY_AND_ASSIGN(BidirectionalStreamImpl); | 
 | }; | 
 |  | 
 | }  // namespace net | 
 |  | 
 | #endif  // NET_HTTP_BIDIRECTIONAL_STREAM_IMPL_H_ |