1*d9f75844SAndroid Build Coastguard Worker /* 2*d9f75844SAndroid Build Coastguard Worker * Copyright 2004 The WebRTC Project Authors. All rights reserved. 3*d9f75844SAndroid Build Coastguard Worker * 4*d9f75844SAndroid Build Coastguard Worker * Use of this source code is governed by a BSD-style license 5*d9f75844SAndroid Build Coastguard Worker * that can be found in the LICENSE file in the root of the source 6*d9f75844SAndroid Build Coastguard Worker * tree. An additional intellectual property rights grant can be found 7*d9f75844SAndroid Build Coastguard Worker * in the file PATENTS. All contributing project authors may 8*d9f75844SAndroid Build Coastguard Worker * be found in the AUTHORS file in the root of the source tree. 9*d9f75844SAndroid Build Coastguard Worker */ 10*d9f75844SAndroid Build Coastguard Worker 11*d9f75844SAndroid Build Coastguard Worker #ifndef P2P_BASE_PSEUDO_TCP_H_ 12*d9f75844SAndroid Build Coastguard Worker #define P2P_BASE_PSEUDO_TCP_H_ 13*d9f75844SAndroid Build Coastguard Worker 14*d9f75844SAndroid Build Coastguard Worker #include <stddef.h> 15*d9f75844SAndroid Build Coastguard Worker #include <stdint.h> 16*d9f75844SAndroid Build Coastguard Worker 17*d9f75844SAndroid Build Coastguard Worker #include <list> 18*d9f75844SAndroid Build Coastguard Worker #include <memory> 19*d9f75844SAndroid Build Coastguard Worker 20*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/synchronization/mutex.h" 21*d9f75844SAndroid Build Coastguard Worker #include "rtc_base/system/rtc_export.h" 22*d9f75844SAndroid Build Coastguard Worker 23*d9f75844SAndroid Build Coastguard Worker namespace cricket { 24*d9f75844SAndroid Build Coastguard Worker 25*d9f75844SAndroid Build Coastguard Worker ////////////////////////////////////////////////////////////////////// 26*d9f75844SAndroid Build Coastguard Worker // IPseudoTcpNotify 27*d9f75844SAndroid Build Coastguard Worker ////////////////////////////////////////////////////////////////////// 28*d9f75844SAndroid Build Coastguard Worker 29*d9f75844SAndroid Build Coastguard Worker class PseudoTcp; 30*d9f75844SAndroid Build Coastguard Worker 31*d9f75844SAndroid Build Coastguard Worker class IPseudoTcpNotify { 32*d9f75844SAndroid Build Coastguard Worker public: 33*d9f75844SAndroid Build Coastguard Worker // Notification of tcp events 34*d9f75844SAndroid Build Coastguard Worker virtual void OnTcpOpen(PseudoTcp* tcp) = 0; 35*d9f75844SAndroid Build Coastguard Worker virtual void OnTcpReadable(PseudoTcp* tcp) = 0; 36*d9f75844SAndroid Build Coastguard Worker virtual void OnTcpWriteable(PseudoTcp* tcp) = 0; 37*d9f75844SAndroid Build Coastguard Worker virtual void OnTcpClosed(PseudoTcp* tcp, uint32_t error) = 0; 38*d9f75844SAndroid Build Coastguard Worker 39*d9f75844SAndroid Build Coastguard Worker // Write the packet onto the network 40*d9f75844SAndroid Build Coastguard Worker enum WriteResult { WR_SUCCESS, WR_TOO_LARGE, WR_FAIL }; 41*d9f75844SAndroid Build Coastguard Worker virtual WriteResult TcpWritePacket(PseudoTcp* tcp, 42*d9f75844SAndroid Build Coastguard Worker const char* buffer, 43*d9f75844SAndroid Build Coastguard Worker size_t len) = 0; 44*d9f75844SAndroid Build Coastguard Worker 45*d9f75844SAndroid Build Coastguard Worker protected: ~IPseudoTcpNotify()46*d9f75844SAndroid Build Coastguard Worker virtual ~IPseudoTcpNotify() {} 47*d9f75844SAndroid Build Coastguard Worker }; 48*d9f75844SAndroid Build Coastguard Worker 49*d9f75844SAndroid Build Coastguard Worker ////////////////////////////////////////////////////////////////////// 50*d9f75844SAndroid Build Coastguard Worker // PseudoTcp 51*d9f75844SAndroid Build Coastguard Worker ////////////////////////////////////////////////////////////////////// 52*d9f75844SAndroid Build Coastguard Worker 53*d9f75844SAndroid Build Coastguard Worker class RTC_EXPORT PseudoTcp { 54*d9f75844SAndroid Build Coastguard Worker public: 55*d9f75844SAndroid Build Coastguard Worker static uint32_t Now(); 56*d9f75844SAndroid Build Coastguard Worker 57*d9f75844SAndroid Build Coastguard Worker PseudoTcp(IPseudoTcpNotify* notify, uint32_t conv); 58*d9f75844SAndroid Build Coastguard Worker virtual ~PseudoTcp(); 59*d9f75844SAndroid Build Coastguard Worker 60*d9f75844SAndroid Build Coastguard Worker int Connect(); 61*d9f75844SAndroid Build Coastguard Worker int Recv(char* buffer, size_t len); 62*d9f75844SAndroid Build Coastguard Worker int Send(const char* buffer, size_t len); 63*d9f75844SAndroid Build Coastguard Worker void Close(bool force); 64*d9f75844SAndroid Build Coastguard Worker int GetError(); 65*d9f75844SAndroid Build Coastguard Worker 66*d9f75844SAndroid Build Coastguard Worker enum TcpState { 67*d9f75844SAndroid Build Coastguard Worker TCP_LISTEN, 68*d9f75844SAndroid Build Coastguard Worker TCP_SYN_SENT, 69*d9f75844SAndroid Build Coastguard Worker TCP_SYN_RECEIVED, 70*d9f75844SAndroid Build Coastguard Worker TCP_ESTABLISHED, 71*d9f75844SAndroid Build Coastguard Worker TCP_CLOSED 72*d9f75844SAndroid Build Coastguard Worker }; State()73*d9f75844SAndroid Build Coastguard Worker TcpState State() const { return m_state; } 74*d9f75844SAndroid Build Coastguard Worker 75*d9f75844SAndroid Build Coastguard Worker // Call this when the PMTU changes. 76*d9f75844SAndroid Build Coastguard Worker void NotifyMTU(uint16_t mtu); 77*d9f75844SAndroid Build Coastguard Worker 78*d9f75844SAndroid Build Coastguard Worker // Call this based on timeout value returned from GetNextClock. 79*d9f75844SAndroid Build Coastguard Worker // It's ok to call this too frequently. 80*d9f75844SAndroid Build Coastguard Worker void NotifyClock(uint32_t now); 81*d9f75844SAndroid Build Coastguard Worker 82*d9f75844SAndroid Build Coastguard Worker // Call this whenever a packet arrives. 83*d9f75844SAndroid Build Coastguard Worker // Returns true if the packet was processed successfully. 84*d9f75844SAndroid Build Coastguard Worker bool NotifyPacket(const char* buffer, size_t len); 85*d9f75844SAndroid Build Coastguard Worker 86*d9f75844SAndroid Build Coastguard Worker // Call this to determine the next time NotifyClock should be called. 87*d9f75844SAndroid Build Coastguard Worker // Returns false if the socket is ready to be destroyed. 88*d9f75844SAndroid Build Coastguard Worker bool GetNextClock(uint32_t now, long& timeout); 89*d9f75844SAndroid Build Coastguard Worker 90*d9f75844SAndroid Build Coastguard Worker // Call these to get/set option values to tailor this PseudoTcp 91*d9f75844SAndroid Build Coastguard Worker // instance's behaviour for the kind of data it will carry. 92*d9f75844SAndroid Build Coastguard Worker // If an unrecognized option is set or got, an assertion will fire. 93*d9f75844SAndroid Build Coastguard Worker // 94*d9f75844SAndroid Build Coastguard Worker // Setting options for OPT_RCVBUF or OPT_SNDBUF after Connect() is called 95*d9f75844SAndroid Build Coastguard Worker // will result in an assertion. 96*d9f75844SAndroid Build Coastguard Worker enum Option { 97*d9f75844SAndroid Build Coastguard Worker OPT_NODELAY, // Whether to enable Nagle's algorithm (0 == off) 98*d9f75844SAndroid Build Coastguard Worker OPT_ACKDELAY, // The Delayed ACK timeout (0 == off). 99*d9f75844SAndroid Build Coastguard Worker OPT_RCVBUF, // Set the receive buffer size, in bytes. 100*d9f75844SAndroid Build Coastguard Worker OPT_SNDBUF, // Set the send buffer size, in bytes. 101*d9f75844SAndroid Build Coastguard Worker }; 102*d9f75844SAndroid Build Coastguard Worker void GetOption(Option opt, int* value); 103*d9f75844SAndroid Build Coastguard Worker void SetOption(Option opt, int value); 104*d9f75844SAndroid Build Coastguard Worker 105*d9f75844SAndroid Build Coastguard Worker // Returns current congestion window in bytes. 106*d9f75844SAndroid Build Coastguard Worker uint32_t GetCongestionWindow() const; 107*d9f75844SAndroid Build Coastguard Worker 108*d9f75844SAndroid Build Coastguard Worker // Returns amount of data in bytes that has been sent, but haven't 109*d9f75844SAndroid Build Coastguard Worker // been acknowledged. 110*d9f75844SAndroid Build Coastguard Worker uint32_t GetBytesInFlight() const; 111*d9f75844SAndroid Build Coastguard Worker 112*d9f75844SAndroid Build Coastguard Worker // Returns number of bytes that were written in buffer and haven't 113*d9f75844SAndroid Build Coastguard Worker // been sent. 114*d9f75844SAndroid Build Coastguard Worker uint32_t GetBytesBufferedNotSent() const; 115*d9f75844SAndroid Build Coastguard Worker 116*d9f75844SAndroid Build Coastguard Worker // Returns current round-trip time estimate in milliseconds. 117*d9f75844SAndroid Build Coastguard Worker uint32_t GetRoundTripTimeEstimateMs() const; 118*d9f75844SAndroid Build Coastguard Worker 119*d9f75844SAndroid Build Coastguard Worker protected: 120*d9f75844SAndroid Build Coastguard Worker enum SendFlags { sfNone, sfDelayedAck, sfImmediateAck }; 121*d9f75844SAndroid Build Coastguard Worker 122*d9f75844SAndroid Build Coastguard Worker struct Segment { 123*d9f75844SAndroid Build Coastguard Worker uint32_t conv, seq, ack; 124*d9f75844SAndroid Build Coastguard Worker uint8_t flags; 125*d9f75844SAndroid Build Coastguard Worker uint16_t wnd; 126*d9f75844SAndroid Build Coastguard Worker const char* data; 127*d9f75844SAndroid Build Coastguard Worker uint32_t len; 128*d9f75844SAndroid Build Coastguard Worker uint32_t tsval, tsecr; 129*d9f75844SAndroid Build Coastguard Worker }; 130*d9f75844SAndroid Build Coastguard Worker 131*d9f75844SAndroid Build Coastguard Worker struct SSegment { SSegmentSSegment132*d9f75844SAndroid Build Coastguard Worker SSegment(uint32_t s, uint32_t l, bool c) 133*d9f75844SAndroid Build Coastguard Worker : seq(s), len(l), /*tstamp(0),*/ xmit(0), bCtrl(c) {} 134*d9f75844SAndroid Build Coastguard Worker uint32_t seq, len; 135*d9f75844SAndroid Build Coastguard Worker // uint32_t tstamp; 136*d9f75844SAndroid Build Coastguard Worker uint8_t xmit; 137*d9f75844SAndroid Build Coastguard Worker bool bCtrl; 138*d9f75844SAndroid Build Coastguard Worker }; 139*d9f75844SAndroid Build Coastguard Worker typedef std::list<SSegment> SList; 140*d9f75844SAndroid Build Coastguard Worker 141*d9f75844SAndroid Build Coastguard Worker struct RSegment { 142*d9f75844SAndroid Build Coastguard Worker uint32_t seq, len; 143*d9f75844SAndroid Build Coastguard Worker }; 144*d9f75844SAndroid Build Coastguard Worker 145*d9f75844SAndroid Build Coastguard Worker uint32_t queue(const char* data, uint32_t len, bool bCtrl); 146*d9f75844SAndroid Build Coastguard Worker 147*d9f75844SAndroid Build Coastguard Worker // Creates a packet and submits it to the network. This method can either 148*d9f75844SAndroid Build Coastguard Worker // send payload or just an ACK packet. 149*d9f75844SAndroid Build Coastguard Worker // 150*d9f75844SAndroid Build Coastguard Worker // `seq` is the sequence number of this packet. 151*d9f75844SAndroid Build Coastguard Worker // `flags` is the flags for sending this packet. 152*d9f75844SAndroid Build Coastguard Worker // `offset` is the offset to read from `m_sbuf`. 153*d9f75844SAndroid Build Coastguard Worker // `len` is the number of bytes to read from `m_sbuf` as payload. If this 154*d9f75844SAndroid Build Coastguard Worker // value is 0 then this is an ACK packet, otherwise this packet has payload. 155*d9f75844SAndroid Build Coastguard Worker IPseudoTcpNotify::WriteResult packet(uint32_t seq, 156*d9f75844SAndroid Build Coastguard Worker uint8_t flags, 157*d9f75844SAndroid Build Coastguard Worker uint32_t offset, 158*d9f75844SAndroid Build Coastguard Worker uint32_t len); 159*d9f75844SAndroid Build Coastguard Worker bool parse(const uint8_t* buffer, uint32_t size); 160*d9f75844SAndroid Build Coastguard Worker 161*d9f75844SAndroid Build Coastguard Worker void attemptSend(SendFlags sflags = sfNone); 162*d9f75844SAndroid Build Coastguard Worker 163*d9f75844SAndroid Build Coastguard Worker void closedown(uint32_t err = 0); 164*d9f75844SAndroid Build Coastguard Worker 165*d9f75844SAndroid Build Coastguard Worker bool clock_check(uint32_t now, long& nTimeout); 166*d9f75844SAndroid Build Coastguard Worker 167*d9f75844SAndroid Build Coastguard Worker bool process(Segment& seg); 168*d9f75844SAndroid Build Coastguard Worker bool transmit(const SList::iterator& seg, uint32_t now); 169*d9f75844SAndroid Build Coastguard Worker 170*d9f75844SAndroid Build Coastguard Worker void adjustMTU(); 171*d9f75844SAndroid Build Coastguard Worker 172*d9f75844SAndroid Build Coastguard Worker protected: 173*d9f75844SAndroid Build Coastguard Worker // This method is used in test only to query receive buffer state. 174*d9f75844SAndroid Build Coastguard Worker bool isReceiveBufferFull() const; 175*d9f75844SAndroid Build Coastguard Worker 176*d9f75844SAndroid Build Coastguard Worker // This method is only used in tests, to disable window scaling 177*d9f75844SAndroid Build Coastguard Worker // support for testing backward compatibility. 178*d9f75844SAndroid Build Coastguard Worker void disableWindowScale(); 179*d9f75844SAndroid Build Coastguard Worker 180*d9f75844SAndroid Build Coastguard Worker private: 181*d9f75844SAndroid Build Coastguard Worker // Queue the connect message with TCP options. 182*d9f75844SAndroid Build Coastguard Worker void queueConnectMessage(); 183*d9f75844SAndroid Build Coastguard Worker 184*d9f75844SAndroid Build Coastguard Worker // Parse TCP options in the header. 185*d9f75844SAndroid Build Coastguard Worker void parseOptions(const char* data, uint32_t len); 186*d9f75844SAndroid Build Coastguard Worker 187*d9f75844SAndroid Build Coastguard Worker // Apply a TCP option that has been read from the header. 188*d9f75844SAndroid Build Coastguard Worker void applyOption(char kind, const char* data, uint32_t len); 189*d9f75844SAndroid Build Coastguard Worker 190*d9f75844SAndroid Build Coastguard Worker // Apply window scale option. 191*d9f75844SAndroid Build Coastguard Worker void applyWindowScaleOption(uint8_t scale_factor); 192*d9f75844SAndroid Build Coastguard Worker 193*d9f75844SAndroid Build Coastguard Worker // Resize the send buffer with `new_size` in bytes. 194*d9f75844SAndroid Build Coastguard Worker void resizeSendBuffer(uint32_t new_size); 195*d9f75844SAndroid Build Coastguard Worker 196*d9f75844SAndroid Build Coastguard Worker // Resize the receive buffer with `new_size` in bytes. This call adjusts 197*d9f75844SAndroid Build Coastguard Worker // window scale factor `m_swnd_scale` accordingly. 198*d9f75844SAndroid Build Coastguard Worker void resizeReceiveBuffer(uint32_t new_size); 199*d9f75844SAndroid Build Coastguard Worker 200*d9f75844SAndroid Build Coastguard Worker class LockedFifoBuffer final { 201*d9f75844SAndroid Build Coastguard Worker public: 202*d9f75844SAndroid Build Coastguard Worker explicit LockedFifoBuffer(size_t size); 203*d9f75844SAndroid Build Coastguard Worker ~LockedFifoBuffer(); 204*d9f75844SAndroid Build Coastguard Worker 205*d9f75844SAndroid Build Coastguard Worker size_t GetBuffered() const; 206*d9f75844SAndroid Build Coastguard Worker bool SetCapacity(size_t size); 207*d9f75844SAndroid Build Coastguard Worker bool ReadOffset(void* buffer, 208*d9f75844SAndroid Build Coastguard Worker size_t bytes, 209*d9f75844SAndroid Build Coastguard Worker size_t offset, 210*d9f75844SAndroid Build Coastguard Worker size_t* bytes_read); 211*d9f75844SAndroid Build Coastguard Worker bool WriteOffset(const void* buffer, 212*d9f75844SAndroid Build Coastguard Worker size_t bytes, 213*d9f75844SAndroid Build Coastguard Worker size_t offset, 214*d9f75844SAndroid Build Coastguard Worker size_t* bytes_written); 215*d9f75844SAndroid Build Coastguard Worker bool Read(void* buffer, size_t bytes, size_t* bytes_read); 216*d9f75844SAndroid Build Coastguard Worker bool Write(const void* buffer, size_t bytes, size_t* bytes_written); 217*d9f75844SAndroid Build Coastguard Worker void ConsumeReadData(size_t size); 218*d9f75844SAndroid Build Coastguard Worker void ConsumeWriteBuffer(size_t size); 219*d9f75844SAndroid Build Coastguard Worker bool GetWriteRemaining(size_t* size) const; 220*d9f75844SAndroid Build Coastguard Worker 221*d9f75844SAndroid Build Coastguard Worker private: 222*d9f75844SAndroid Build Coastguard Worker bool ReadOffsetLocked(void* buffer, 223*d9f75844SAndroid Build Coastguard Worker size_t bytes, 224*d9f75844SAndroid Build Coastguard Worker size_t offset, 225*d9f75844SAndroid Build Coastguard Worker size_t* bytes_read) 226*d9f75844SAndroid Build Coastguard Worker RTC_EXCLUSIVE_LOCKS_REQUIRED(mutex_); 227*d9f75844SAndroid Build Coastguard Worker bool WriteOffsetLocked(const void* buffer, 228*d9f75844SAndroid Build Coastguard Worker size_t bytes, 229*d9f75844SAndroid Build Coastguard Worker size_t offset, 230*d9f75844SAndroid Build Coastguard Worker size_t* bytes_written) 231*d9f75844SAndroid Build Coastguard Worker RTC_EXCLUSIVE_LOCKS_REQUIRED(mutex_); 232*d9f75844SAndroid Build Coastguard Worker 233*d9f75844SAndroid Build Coastguard Worker // the allocated buffer 234*d9f75844SAndroid Build Coastguard Worker std::unique_ptr<char[]> buffer_ RTC_GUARDED_BY(mutex_); 235*d9f75844SAndroid Build Coastguard Worker // size of the allocated buffer 236*d9f75844SAndroid Build Coastguard Worker size_t buffer_length_ RTC_GUARDED_BY(mutex_); 237*d9f75844SAndroid Build Coastguard Worker // amount of readable data in the buffer 238*d9f75844SAndroid Build Coastguard Worker size_t data_length_ RTC_GUARDED_BY(mutex_); 239*d9f75844SAndroid Build Coastguard Worker // offset to the readable data 240*d9f75844SAndroid Build Coastguard Worker size_t read_position_ RTC_GUARDED_BY(mutex_); 241*d9f75844SAndroid Build Coastguard Worker mutable webrtc::Mutex mutex_; 242*d9f75844SAndroid Build Coastguard Worker }; 243*d9f75844SAndroid Build Coastguard Worker 244*d9f75844SAndroid Build Coastguard Worker IPseudoTcpNotify* m_notify; 245*d9f75844SAndroid Build Coastguard Worker enum Shutdown { SD_NONE, SD_GRACEFUL, SD_FORCEFUL } m_shutdown; 246*d9f75844SAndroid Build Coastguard Worker int m_error; 247*d9f75844SAndroid Build Coastguard Worker 248*d9f75844SAndroid Build Coastguard Worker // TCB data 249*d9f75844SAndroid Build Coastguard Worker TcpState m_state; 250*d9f75844SAndroid Build Coastguard Worker uint32_t m_conv; 251*d9f75844SAndroid Build Coastguard Worker bool m_bReadEnable, m_bWriteEnable, m_bOutgoing; 252*d9f75844SAndroid Build Coastguard Worker uint32_t m_lasttraffic; 253*d9f75844SAndroid Build Coastguard Worker 254*d9f75844SAndroid Build Coastguard Worker // Incoming data 255*d9f75844SAndroid Build Coastguard Worker typedef std::list<RSegment> RList; 256*d9f75844SAndroid Build Coastguard Worker RList m_rlist; 257*d9f75844SAndroid Build Coastguard Worker uint32_t m_rbuf_len, m_rcv_nxt, m_rcv_wnd, m_lastrecv; 258*d9f75844SAndroid Build Coastguard Worker uint8_t m_rwnd_scale; // Window scale factor. 259*d9f75844SAndroid Build Coastguard Worker LockedFifoBuffer m_rbuf; 260*d9f75844SAndroid Build Coastguard Worker 261*d9f75844SAndroid Build Coastguard Worker // Outgoing data 262*d9f75844SAndroid Build Coastguard Worker SList m_slist; 263*d9f75844SAndroid Build Coastguard Worker uint32_t m_sbuf_len, m_snd_nxt, m_snd_wnd, m_lastsend, m_snd_una; 264*d9f75844SAndroid Build Coastguard Worker uint8_t m_swnd_scale; // Window scale factor. 265*d9f75844SAndroid Build Coastguard Worker LockedFifoBuffer m_sbuf; 266*d9f75844SAndroid Build Coastguard Worker 267*d9f75844SAndroid Build Coastguard Worker // Maximum segment size, estimated protocol level, largest segment sent 268*d9f75844SAndroid Build Coastguard Worker uint32_t m_mss, m_msslevel, m_largest, m_mtu_advise; 269*d9f75844SAndroid Build Coastguard Worker // Retransmit timer 270*d9f75844SAndroid Build Coastguard Worker uint32_t m_rto_base; 271*d9f75844SAndroid Build Coastguard Worker 272*d9f75844SAndroid Build Coastguard Worker // Timestamp tracking 273*d9f75844SAndroid Build Coastguard Worker uint32_t m_ts_recent, m_ts_lastack; 274*d9f75844SAndroid Build Coastguard Worker 275*d9f75844SAndroid Build Coastguard Worker // Round-trip calculation 276*d9f75844SAndroid Build Coastguard Worker uint32_t m_rx_rttvar, m_rx_srtt, m_rx_rto; 277*d9f75844SAndroid Build Coastguard Worker 278*d9f75844SAndroid Build Coastguard Worker // Congestion avoidance, Fast retransmit/recovery, Delayed ACKs 279*d9f75844SAndroid Build Coastguard Worker uint32_t m_ssthresh, m_cwnd; 280*d9f75844SAndroid Build Coastguard Worker uint8_t m_dup_acks; 281*d9f75844SAndroid Build Coastguard Worker uint32_t m_recover; 282*d9f75844SAndroid Build Coastguard Worker uint32_t m_t_ack; 283*d9f75844SAndroid Build Coastguard Worker 284*d9f75844SAndroid Build Coastguard Worker // Configuration options 285*d9f75844SAndroid Build Coastguard Worker bool m_use_nagling; 286*d9f75844SAndroid Build Coastguard Worker uint32_t m_ack_delay; 287*d9f75844SAndroid Build Coastguard Worker 288*d9f75844SAndroid Build Coastguard Worker // This is used by unit tests to test backward compatibility of 289*d9f75844SAndroid Build Coastguard Worker // PseudoTcp implementations that don't support window scaling. 290*d9f75844SAndroid Build Coastguard Worker bool m_support_wnd_scale; 291*d9f75844SAndroid Build Coastguard Worker }; 292*d9f75844SAndroid Build Coastguard Worker 293*d9f75844SAndroid Build Coastguard Worker } // namespace cricket 294*d9f75844SAndroid Build Coastguard Worker 295*d9f75844SAndroid Build Coastguard Worker #endif // P2P_BASE_PSEUDO_TCP_H_ 296