tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

HttpConnectionBase.h (10816B)


      1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
      2 /* This Source Code Form is subject to the terms of the Mozilla Public
      3 * License, v. 2.0. If a copy of the MPL was not distributed with this
      4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
      5 
      6 #ifndef HttpConnectionBase_h__
      7 #define HttpConnectionBase_h__
      8 
      9 #include "nsHttpConnectionInfo.h"
     10 #include "nsHttpResponseHead.h"
     11 #include "nsAHttpTransaction.h"
     12 #include "nsCOMPtr.h"
     13 #include "nsProxyRelease.h"
     14 #include "prinrval.h"
     15 #include "mozilla/Mutex.h"
     16 #include "ARefBase.h"
     17 #include "TimingStruct.h"
     18 #include "HttpTrafficAnalyzer.h"
     19 
     20 #include "mozilla/net/DNS.h"
     21 #include "mozilla/WeakPtr.h"
     22 #include "nsIAsyncInputStream.h"
     23 #include "nsIAsyncOutputStream.h"
     24 #include "nsIInterfaceRequestor.h"
     25 #include "nsITimer.h"
     26 
     27 class nsISocketTransport;
     28 class nsITLSSocketControl;
     29 
     30 namespace mozilla {
     31 namespace net {
     32 
     33 class ConnectionEntry;
     34 class nsHttpHandler;
     35 class ASpdySession;
     36 class WebTransportSessionBase;
     37 
     38 enum class ConnectionState : uint32_t {
     39  HALF_OPEN = 0,
     40  INITED,
     41  TLS_HANDSHAKING,
     42  ZERORTT,
     43  TRANSFERING,
     44  CLOSED
     45 };
     46 
     47 enum class ConnectionExperienceState : uint32_t {
     48  Not_Experienced = 0,
     49  First_Request_Sent = (1 << 0),
     50  First_Response_Received = (1 << 1),
     51  Experienced = (1 << 2),
     52 };
     53 
     54 MOZ_MAKE_ENUM_CLASS_BITWISE_OPERATORS(ConnectionExperienceState);
     55 
     56 // 1dcc863e-db90-4652-a1fe-13fea0b54e46
     57 #define HTTPCONNECTIONBASE_IID \
     58  {0x437e7d26, 0xa2fd, 0x49f2, {0xb3, 0x7c, 0x84, 0x23, 0xf0, 0x94, 0x72, 0x36}}
     59 
     60 //-----------------------------------------------------------------------------
     61 // nsHttpConnection - represents a connection to a HTTP server (or proxy)
     62 //
     63 // NOTE: this objects lives on the socket thread only.  it should not be
     64 // accessed from any other thread.
     65 //-----------------------------------------------------------------------------
     66 
     67 class HttpConnectionBase : public nsSupportsWeakReference {
     68 public:
     69  NS_INLINE_DECL_STATIC_IID(HTTPCONNECTIONBASE_IID)
     70 
     71  HttpConnectionBase();
     72 
     73  // Activate causes the given transaction to be processed on this
     74  // connection.  It fails if there is already an existing transaction unless
     75  // a multiplexing protocol such as SPDY is being used
     76  [[nodiscard]] virtual nsresult Activate(nsAHttpTransaction*, uint32_t caps,
     77                                          int32_t pri) = 0;
     78 
     79  // Close the underlying socket transport.
     80  virtual void Close(nsresult reason, bool aIsShutdown = false) = 0;
     81 
     82  virtual bool CanReuse() = 0;  // can this connection be reused?
     83  virtual bool CanDirectlyActivate() = 0;
     84 
     85  virtual void DontReuse() = 0;
     86 
     87  virtual nsAHttpTransaction* Transaction() = 0;
     88  nsHttpConnectionInfo* ConnectionInfo() { return mConnInfo; }
     89 
     90  virtual void CloseTransaction(nsAHttpTransaction*, nsresult,
     91                                bool aIsShutdown = false) = 0;
     92 
     93  [[nodiscard]] virtual nsresult OnHeadersAvailable(nsAHttpTransaction*,
     94                                                    nsHttpRequestHead*,
     95                                                    nsHttpResponseHead*,
     96                                                    bool* reset) = 0;
     97 
     98  [[nodiscard]] virtual nsresult TakeTransport(nsISocketTransport**,
     99                                               nsIAsyncInputStream**,
    100                                               nsIAsyncOutputStream**) = 0;
    101 
    102  virtual WebTransportSessionBase* GetWebTransportSession(
    103      nsAHttpTransaction* aTransaction) {
    104    return nullptr;
    105  }
    106 
    107  virtual bool UsingSpdy() { return false; }
    108  virtual bool UsingHttp3() { return false; }
    109 
    110  virtual void SetTransactionCaps(uint32_t aCaps) { mTransactionCaps = aCaps; }
    111 
    112  virtual void PrintDiagnostics(nsCString& log) = 0;
    113 
    114  // IsExperienced() returns true when the connection has started at least one
    115  // non null HTTP transaction of any version.
    116  bool IsExperienced() { return mExperienced; }
    117 
    118  virtual bool TestJoinConnection(const nsACString& hostname, int32_t port) = 0;
    119  virtual bool JoinConnection(const nsACString& hostname, int32_t port) = 0;
    120 
    121  // Return true when the socket this connection is using has not been
    122  // authenticated using a client certificate.  Before SSL negotiation
    123  // has finished this returns false.
    124  virtual bool NoClientCertAuth() const { return true; }
    125 
    126  // HTTP/2 websocket support
    127  virtual ExtendedCONNECTSupport GetExtendedCONNECTSupport() {
    128    return ExtendedCONNECTSupport::NO_SUPPORT;
    129  }
    130 
    131  void GetConnectionInfo(nsHttpConnectionInfo** ci) {
    132    *ci = do_AddRef(mConnInfo).take();
    133  }
    134  virtual void GetTLSSocketControl(nsITLSSocketControl** result) = 0;
    135 
    136  [[nodiscard]] virtual nsresult ResumeSend() = 0;
    137  [[nodiscard]] virtual nsresult ResumeRecv() = 0;
    138  [[nodiscard]] virtual nsresult ForceSend() = 0;
    139  [[nodiscard]] virtual nsresult ForceRecv() = 0;
    140  virtual HttpVersion Version() = 0;
    141  virtual bool LastTransactionExpectedNoContent() = 0;
    142  virtual void SetLastTransactionExpectedNoContent(bool) = 0;
    143  virtual int64_t BytesWritten() = 0;  // includes TLS
    144  void SetSecurityCallbacks(nsIInterfaceRequestor* aCallbacks);
    145  void SetTrafficCategory(HttpTrafficCategory);
    146 
    147  void BootstrapTimings(TimingStruct times);
    148 
    149  virtual bool IsPersistent() = 0;
    150  virtual bool IsReused() = 0;
    151  [[nodiscard]] virtual nsresult PushBack(const char* data,
    152                                          uint32_t length) = 0;
    153  PRIntervalTime Rtt() { return mRtt; }
    154  virtual void SetEvent(nsresult aStatus) = 0;
    155 
    156  virtual nsISocketTransport* Transport() { return nullptr; }
    157 
    158  virtual nsresult GetSelfAddr(NetAddr* addr) = 0;
    159  virtual nsresult GetPeerAddr(NetAddr* addr) = 0;
    160  virtual bool ResolvedByTRR() = 0;
    161  virtual nsIRequest::TRRMode EffectiveTRRMode() = 0;
    162  virtual TRRSkippedReason TRRSkipReason() = 0;
    163  virtual bool GetEchConfigUsed() = 0;
    164  virtual PRIntervalTime LastWriteTime() = 0;
    165 
    166  void ChangeConnectionState(ConnectionState aState);
    167  ConnectionCloseReason CloseReason() const { return mCloseReason; }
    168  void SetCloseReason(ConnectionCloseReason aReason) {
    169    if (mCloseReason == ConnectionCloseReason::UNSET) {
    170      mCloseReason = aReason;
    171    }
    172  }
    173 
    174  void RecordConnectionCloseTelemetry(nsresult aReason);
    175  void RecordConnectionAddressType();
    176 
    177  bool IsProxyConnectInProgress() { return mState == SETTING_UP_TUNNEL; }
    178 
    179  virtual nsresult CreateTunnelStream(nsAHttpTransaction* httpTransaction,
    180                                      HttpConnectionBase** aHttpConnection,
    181                                      bool aIsExtendedCONNECT = false) = 0;
    182  virtual void SetInTunnel() {};
    183 
    184  void SetOwner(ConnectionEntry* aEntry);
    185  ConnectionEntry* OwnerEntry() const;
    186 
    187 protected:
    188  // The capabailities associated with the most recent transaction
    189  uint32_t mTransactionCaps{0};
    190 
    191  RefPtr<nsHttpConnectionInfo> mConnInfo;
    192  // Set when this connection is added to the active connections list,
    193  // cleared when it is removed.
    194  WeakPtr<ConnectionEntry> mOwnerEntry;
    195 
    196  bool mExperienced{false};
    197  // Used to track whether this connection is serving the first request.
    198  bool mHasFirstHttpTransaction{false};
    199 
    200  bool mBootstrappedTimingsSet{false};
    201  TimingStruct mBootstrappedTimings;
    202 
    203  Mutex mCallbacksLock MOZ_UNANNOTATED{"nsHttpConnection::mCallbacksLock"};
    204  nsMainThreadPtrHandle<nsIInterfaceRequestor> mCallbacks;
    205 
    206  nsTArray<HttpTrafficCategory> mTrafficCategory;
    207  PRIntervalTime mRtt{0};
    208  nsresult mErrorBeforeConnect = NS_OK;
    209 
    210  ConnectionState mConnectionState = ConnectionState::HALF_OPEN;
    211 
    212  // Represent if the connection has served more than one request.
    213  ConnectionExperienceState mExperienceState =
    214      ConnectionExperienceState::Not_Experienced;
    215 
    216  ConnectionCloseReason mCloseReason = ConnectionCloseReason::UNSET;
    217 
    218  bool mAddressTypeReported{false};
    219 
    220  // Tunnel retated functions:
    221  enum HttpConnectionState {
    222    UNINITIALIZED,
    223    SETTING_UP_TUNNEL,
    224    REQUEST,
    225  } mState{HttpConnectionState::UNINITIALIZED};
    226  void ChangeState(HttpConnectionState newState);
    227  bool TunnelSetupInProgress() { return mState == SETTING_UP_TUNNEL; }
    228  virtual void SetTunnelSetupDone() {}
    229  virtual nsresult SetupProxyConnectStream() { return NS_OK; }
    230  nsresult CheckTunnelIsNeeded(nsAHttpTransaction* aTransaction);
    231 };
    232 
    233 #define NS_DECL_HTTPCONNECTIONBASE                                             \
    234  [[nodiscard]] nsresult Activate(nsAHttpTransaction*, uint32_t, int32_t)      \
    235      override;                                                                \
    236  [[nodiscard]] nsresult OnHeadersAvailable(                                   \
    237      nsAHttpTransaction*, nsHttpRequestHead*, nsHttpResponseHead*,            \
    238      bool* reset) override;                                                   \
    239  [[nodiscard]] nsresult TakeTransport(                                        \
    240      nsISocketTransport**, nsIAsyncInputStream**, nsIAsyncOutputStream**)     \
    241      override;                                                                \
    242  void Close(nsresult, bool aIsShutdown = false) override;                     \
    243  bool CanReuse() override;                                                    \
    244  bool CanDirectlyActivate() override;                                         \
    245  void DontReuse() override;                                                   \
    246  void CloseTransaction(nsAHttpTransaction*, nsresult,                         \
    247                        bool aIsShutdown = false) override;                    \
    248  void PrintDiagnostics(nsCString&) override;                                  \
    249  bool TestJoinConnection(const nsACString&, int32_t) override;                \
    250  bool JoinConnection(const nsACString&, int32_t) override;                    \
    251  void GetTLSSocketControl(nsITLSSocketControl** result) override;             \
    252  [[nodiscard]] nsresult ResumeSend() override;                                \
    253  [[nodiscard]] nsresult ResumeRecv() override;                                \
    254  [[nodiscard]] nsresult ForceSend() override;                                 \
    255  [[nodiscard]] nsresult ForceRecv() override;                                 \
    256  HttpVersion Version() override;                                              \
    257  bool LastTransactionExpectedNoContent() override;                            \
    258  void SetLastTransactionExpectedNoContent(bool val) override;                 \
    259  bool IsPersistent() override;                                                \
    260  bool IsReused() override;                                                    \
    261  [[nodiscard]] nsresult PushBack(const char* data, uint32_t length) override; \
    262  void SetEvent(nsresult aStatus) override;                                    \
    263  virtual nsAHttpTransaction* Transaction() override;                          \
    264  PRIntervalTime LastWriteTime() override;
    265 
    266 }  // namespace net
    267 }  // namespace mozilla
    268 
    269 #endif  // HttpConnectionBase_h__