Source code

Revision control

Copy as Markdown

Other Tools

/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#ifndef nsAHttpConnection_h__
#define nsAHttpConnection_h__
#include "mozilla/net/DNS.h"
#include "nsHttp.h"
#include "nsISupports.h"
#include "nsAHttpTransaction.h"
#include "Http3WebTransportSession.h"
#include "HttpTrafficAnalyzer.h"
#include "nsIRequest.h"
class nsIAsyncInputStream;
class nsIAsyncOutputStream;
class nsISocketTransport;
class nsITLSSocketControl;
namespace mozilla {
namespace net {
class nsHttpConnectionInfo;
class HttpConnectionBase;
class nsHttpRequestHead;
class nsHttpResponseHead;
//-----------------------------------------------------------------------------
// Abstract base class for a HTTP connection
//-----------------------------------------------------------------------------
// 5a66aed7-eede-468b-ac2b-e5fb431fcc5c
#define NS_AHTTPCONNECTION_IID \
{ \
0x5a66aed7, 0xeede, 0x468b, { \
0xac, 0x2b, 0xe5, 0xfb, 0x43, 0x1f, 0xcc, 0x5c \
} \
}
class nsAHttpConnection : public nsISupports {
public:
NS_DECLARE_STATIC_IID_ACCESSOR(NS_AHTTPCONNECTION_IID)
//-------------------------------------------------------------------------
// NOTE: these methods may only be called on the socket thread.
//-------------------------------------------------------------------------
//
// called by a transaction when the response headers have all been read.
// the connection can force the transaction to reset it's response headers,
// and prepare for a new set of response headers, by setting |*reset=TRUE|.
//
// @return failure code to close the transaction.
//
[[nodiscard]] virtual nsresult OnHeadersAvailable(nsAHttpTransaction*,
nsHttpRequestHead*,
nsHttpResponseHead*,
bool* reset) = 0;
//
// called by a transaction to resume either sending or receiving data
// after a transaction returned NS_BASE_STREAM_WOULD_BLOCK from its
// ReadSegments/WriteSegments methods.
//
[[nodiscard]] virtual nsresult ResumeSend() = 0;
[[nodiscard]] virtual nsresult ResumeRecv() = 0;
// called by a transaction to force a "send/recv from network" iteration
// even if not scheduled by socket associated with connection
[[nodiscard]] virtual nsresult ForceSend() = 0;
[[nodiscard]] virtual nsresult ForceRecv() = 0;
// After a connection has had ResumeSend() called by a transaction,
// and it is ready to write to the network it may need to know the
// transaction that has data to write. This is only an issue for
// multiplexed protocols like SPDY - h1
// implicitly has this information in a 1:1 relationship with the
// transaction(s) they manage.
virtual void TransactionHasDataToWrite(nsAHttpTransaction*) {
// by default do nothing - only multiplexed protocols need to overload
}
// This is the companion to *HasDataToWrite() for the case
// when a gecko caller has called ResumeRecv() after being paused
virtual void TransactionHasDataToRecv(nsAHttpTransaction*) {
// by default do nothing - only multiplexed protocols need to overload
}
// called by the connection manager to close a transaction being processed
// by this connection.
//
// @param transaction
// the transaction being closed.
// @param reason
// the reason for closing the transaction. NS_BASE_STREAM_CLOSED
// is equivalent to NS_OK.
//
virtual void CloseTransaction(nsAHttpTransaction* transaction,
nsresult reason) = 0;
// get a reference to the connection's connection info object.
virtual void GetConnectionInfo(nsHttpConnectionInfo**) = 0;
// get the transport level information for this connection. This may fail
// if it is in use.
[[nodiscard]] virtual nsresult TakeTransport(nsISocketTransport**,
nsIAsyncInputStream**,
nsIAsyncOutputStream**) = 0;
[[nodiscard]] virtual Http3WebTransportSession* GetWebTransportSession(
nsAHttpTransaction* aTransaction) = 0;
// called by a transaction to get the TLS socket control from the socket.
virtual void GetTLSSocketControl(nsITLSSocketControl**) = 0;
// called by a transaction to determine whether or not the connection is
// persistent... important in determining the end of a response.
virtual bool IsPersistent() = 0;
// called to determine or set if a connection has been reused.
virtual bool IsReused() = 0;
virtual void DontReuse() = 0;
// called by a transaction when the transaction reads more from the socket
// than it should have (eg. containing part of the next response).
[[nodiscard]] virtual nsresult PushBack(const char* data,
uint32_t length) = 0;
// Used to determine if the connection wants read events even though
// it has not written out a transaction. Used when a connection has issued
// a preamble such as a proxy ssl CONNECT sequence.
virtual bool IsProxyConnectInProgress() = 0;
// Used by a transaction to manage the state of previous response bodies on
// the same connection and work around buggy servers.
virtual bool LastTransactionExpectedNoContent() = 0;
virtual void SetLastTransactionExpectedNoContent(bool) = 0;
// Transfer the base http connection object along with a
// reference to it to the caller.
virtual already_AddRefed<HttpConnectionBase> TakeHttpConnection() = 0;
// Like TakeHttpConnection() but do not drop our own ref
virtual already_AddRefed<HttpConnectionBase> HttpConnection() = 0;
// Get the nsISocketTransport used by the connection without changing
// references or ownership.
virtual nsISocketTransport* Transport() = 0;
// The number of transaction bytes written out on this HTTP Connection, does
// not count CONNECT tunnel setup
virtual int64_t BytesWritten() = 0;
// Update the callbacks used to provide security info. May be called on
// any thread.
virtual void SetSecurityCallbacks(nsIInterfaceRequestor* aCallbacks) = 0;
// nsHttp.h version
virtual HttpVersion Version() = 0;
// A notification of the current active tab id change.
virtual void CurrentBrowserIdChanged(uint64_t id) = 0;
// categories set by nsHttpTransaction to identify how this connection is
// being used.
virtual void SetTrafficCategory(HttpTrafficCategory) = 0;
virtual nsresult GetSelfAddr(NetAddr* addr) = 0;
virtual nsresult GetPeerAddr(NetAddr* addr) = 0;
virtual bool ResolvedByTRR() = 0;
virtual nsIRequest::TRRMode EffectiveTRRMode() = 0;
virtual nsITRRSkipReason::value TRRSkipReason() = 0;
virtual bool GetEchConfigUsed() = 0;
virtual PRIntervalTime LastWriteTime() = 0;
virtual void SetCloseReason(ConnectionCloseReason aReason) = 0;
};
NS_DEFINE_STATIC_IID_ACCESSOR(nsAHttpConnection, NS_AHTTPCONNECTION_IID)
#define NS_DECL_NSAHTTPCONNECTION(fwdObject) \
[[nodiscard]] nsresult OnHeadersAvailable( \
nsAHttpTransaction*, nsHttpRequestHead*, nsHttpResponseHead*, \
bool* reset) override; \
void CloseTransaction(nsAHttpTransaction*, nsresult) override; \
[[nodiscard]] nsresult TakeTransport( \
nsISocketTransport**, nsIAsyncInputStream**, nsIAsyncOutputStream**) \
override; \
[[nodiscard]] Http3WebTransportSession* GetWebTransportSession( \
nsAHttpTransaction* aTransaction) override; \
bool IsPersistent() override; \
bool IsReused() override; \
void DontReuse() override; \
[[nodiscard]] nsresult PushBack(const char*, uint32_t) override; \
already_AddRefed<HttpConnectionBase> TakeHttpConnection() override; \
already_AddRefed<HttpConnectionBase> HttpConnection() override; \
void CurrentBrowserIdChanged(uint64_t id) override; \
/* \
Thes methods below have automatic definitions that just forward the \
function to a lower level connection object \
*/ \
void GetConnectionInfo(nsHttpConnectionInfo** result) override { \
if (!(fwdObject)) { \
*result = nullptr; \
return; \
} \
return (fwdObject)->GetConnectionInfo(result); \
} \
void GetTLSSocketControl(nsITLSSocketControl** result) override { \
if (!(fwdObject)) { \
*result = nullptr; \
return; \
} \
return (fwdObject)->GetTLSSocketControl(result); \
} \
[[nodiscard]] nsresult ResumeSend() override { \
if (!(fwdObject)) return NS_ERROR_FAILURE; \
return (fwdObject)->ResumeSend(); \
} \
[[nodiscard]] nsresult ResumeRecv() override { \
if (!(fwdObject)) return NS_ERROR_FAILURE; \
return (fwdObject)->ResumeRecv(); \
} \
[[nodiscard]] nsresult ForceSend() override { \
if (!(fwdObject)) return NS_ERROR_FAILURE; \
return (fwdObject)->ForceSend(); \
} \
[[nodiscard]] nsresult ForceRecv() override { \
if (!(fwdObject)) return NS_ERROR_FAILURE; \
return (fwdObject)->ForceRecv(); \
} \
nsISocketTransport* Transport() override { \
if (!(fwdObject)) return nullptr; \
return (fwdObject)->Transport(); \
} \
HttpVersion Version() override { \
return (fwdObject) ? (fwdObject)->Version() \
: mozilla::net::HttpVersion::UNKNOWN; \
} \
bool IsProxyConnectInProgress() override { \
return (!(fwdObject)) ? false : (fwdObject)->IsProxyConnectInProgress(); \
} \
bool LastTransactionExpectedNoContent() override { \
return (!(fwdObject)) ? false \
: (fwdObject)->LastTransactionExpectedNoContent(); \
} \
void SetLastTransactionExpectedNoContent(bool val) override { \
if (fwdObject) (fwdObject)->SetLastTransactionExpectedNoContent(val); \
} \
int64_t BytesWritten() override { \
return (fwdObject) ? (fwdObject)->BytesWritten() : 0; \
} \
void SetSecurityCallbacks(nsIInterfaceRequestor* aCallbacks) override { \
if (fwdObject) (fwdObject)->SetSecurityCallbacks(aCallbacks); \
} \
void SetTrafficCategory(HttpTrafficCategory aCategory) override { \
if (fwdObject) (fwdObject)->SetTrafficCategory(aCategory); \
} \
nsresult GetSelfAddr(NetAddr* addr) override { \
if (!(fwdObject)) return NS_ERROR_FAILURE; \
return (fwdObject)->GetSelfAddr(addr); \
} \
nsresult GetPeerAddr(NetAddr* addr) override { \
if (!(fwdObject)) return NS_ERROR_FAILURE; \
return (fwdObject)->GetPeerAddr(addr); \
} \
bool ResolvedByTRR() override { \
return (!(fwdObject)) ? false : (fwdObject)->ResolvedByTRR(); \
} \
nsIRequest::TRRMode EffectiveTRRMode() override { \
return (!(fwdObject)) ? nsIRequest::TRR_DEFAULT_MODE \
: (fwdObject)->EffectiveTRRMode(); \
} \
nsITRRSkipReason::value TRRSkipReason() override { \
return (!(fwdObject)) ? nsITRRSkipReason::TRR_UNSET \
: (fwdObject)->TRRSkipReason(); \
} \
bool GetEchConfigUsed() override { \
return (!(fwdObject)) ? false : (fwdObject)->GetEchConfigUsed(); \
} \
void SetCloseReason(ConnectionCloseReason aReason) override { \
if (fwdObject) (fwdObject)->SetCloseReason(aReason); \
} \
PRIntervalTime LastWriteTime() override;
// ThrottleResponse deliberately ommited since we want different implementation
// for h1 and h2 connections.
} // namespace net
} // namespace mozilla
#endif // nsAHttpConnection_h__