mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-28 07:13:20 +00:00
Bug 1652677 - P2: Implement necko part of echconfig r=dragana
Differential Revision: https://phabricator.services.mozilla.com/D89455
This commit is contained in:
parent
35c03a8910
commit
71089ed718
@ -182,6 +182,10 @@ class FakeSocketTransportProvider : public nsISocketTransport {
|
||||
MOZ_ASSERT(false);
|
||||
return NS_OK;
|
||||
}
|
||||
NS_IMETHOD SetEchConfig(const nsACString& aEchConfig) override {
|
||||
MOZ_ASSERT(false);
|
||||
return NS_OK;
|
||||
}
|
||||
NS_IMETHOD ResolvedByTRR(bool* _retval) override {
|
||||
MOZ_ASSERT(false);
|
||||
return NS_OK;
|
||||
|
@ -319,6 +319,15 @@ FuzzySecurityInfo::SetEsniTxt(const nsACString& aEsniTxt) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
FuzzySecurityInfo::GetEchConfig(nsACString& aEchConfig) { return NS_OK; }
|
||||
|
||||
NS_IMETHODIMP
|
||||
FuzzySecurityInfo::SetEchConfig(const nsACString& aEchConfig) {
|
||||
MOZ_CRASH("Unused");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
void FuzzySecurityInfo::SerializeToIPC(IPC::Message* aMsg) {
|
||||
MOZ_CRASH("Unused");
|
||||
}
|
||||
|
@ -255,9 +255,9 @@ interface nsISocketTransport : nsITransport
|
||||
|
||||
/**
|
||||
* If we know that a server speaks only tls <1.3 there is no need to try
|
||||
* to use esni and query dns for esni keys.
|
||||
* to use esni/ech and query dns for esni/echconfig.
|
||||
*/
|
||||
const unsigned long DONT_TRY_ESNI = (1 << 10);
|
||||
const unsigned long DONT_TRY_ESNI_OR_ECH = (1 << 10);
|
||||
|
||||
/**
|
||||
* These two bits encode the TRR mode of the request.
|
||||
@ -331,6 +331,13 @@ interface nsISocketTransport : nsITransport
|
||||
*/
|
||||
readonly attribute boolean esniUsed;
|
||||
|
||||
/**
|
||||
* Called to set the echConfig to the securityInfo object.
|
||||
* Note that echConfig taks priority over esni, so when this function is
|
||||
* called esni will not be used.
|
||||
*/
|
||||
void setEchConfig(in ACString echConfig);
|
||||
|
||||
/**
|
||||
* IP address resolved using TRR.
|
||||
*/
|
||||
|
@ -1073,8 +1073,10 @@ nsresult nsSocketTransport::ResolveHost() {
|
||||
dnsFlags, nullptr, this, mSocketTransportService,
|
||||
mOriginAttributes, getter_AddRefs(mDNSRequest));
|
||||
mEsniQueried = false;
|
||||
// NOTE: If we already have echConfig, we don't try ESNI.
|
||||
if (mSocketTransportService->IsEsniEnabled() && NS_SUCCEEDED(rv) &&
|
||||
!(mConnectionFlags & (DONT_TRY_ESNI | BE_CONSERVATIVE))) {
|
||||
!(mConnectionFlags & (DONT_TRY_ESNI_OR_ECH | BE_CONSERVATIVE)) &&
|
||||
mEchConfig.IsEmpty()) {
|
||||
bool isSSL = false;
|
||||
for (unsigned int i = 0; i < mTypes.Length(); ++i) {
|
||||
if (mTypes[i].EqualsLiteral("ssl")) {
|
||||
@ -1558,9 +1560,16 @@ nsresult nsSocketTransport::InitiateSocket() {
|
||||
}
|
||||
#endif
|
||||
|
||||
if (!mDNSRecordTxt.IsEmpty() && !mUsingQuic && mSecInfo) {
|
||||
nsCOMPtr<nsISSLSocketControl> secCtrl = do_QueryInterface(mSecInfo);
|
||||
if (secCtrl) {
|
||||
nsCOMPtr<nsISSLSocketControl> secCtrl = do_QueryInterface(mSecInfo);
|
||||
if (secCtrl) {
|
||||
if (!mEchConfig.IsEmpty() &&
|
||||
!(mConnectionFlags & (DONT_TRY_ESNI_OR_ECH | BE_CONSERVATIVE))) {
|
||||
SOCKET_LOG(("nsSocketTransport::InitiateSocket set echconfig."));
|
||||
rv = secCtrl->SetEchConfig(mEchConfig);
|
||||
if (NS_FAILED(rv)) {
|
||||
return rv;
|
||||
}
|
||||
} else if (!mDNSRecordTxt.IsEmpty() && !mUsingQuic) {
|
||||
SOCKET_LOG(("nsSocketTransport::InitiateSocket set esni keys."));
|
||||
rv = secCtrl->SetEsniTxt(mDNSRecordTxt);
|
||||
if (NS_FAILED(rv)) {
|
||||
@ -3628,6 +3637,12 @@ nsSocketTransport::GetEsniUsed(bool* aEsniUsed) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsSocketTransport::SetEchConfig(const nsACString& aEchConfig) {
|
||||
mEchConfig = aEchConfig;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsSocketTransport::ResolvedByTRR(bool* aResolvedByTRR) {
|
||||
*aResolvedByTRR = mResolvedByTRR;
|
||||
|
@ -331,6 +331,7 @@ class nsSocketTransport final : public nsASocketHandler,
|
||||
PRIntervalTime mDNSARequestFinished;
|
||||
nsCOMPtr<nsICancelable> mDNSTxtRequest;
|
||||
nsCString mDNSRecordTxt;
|
||||
nsCString mEchConfig;
|
||||
bool mEsniQueried;
|
||||
bool mEsniUsed;
|
||||
bool mResolvedByTRR;
|
||||
|
@ -214,6 +214,11 @@ Maybe<uint16_t> SVCBRecord::GetPort() { return mPort; }
|
||||
|
||||
Maybe<nsCString> SVCBRecord::GetAlpn() { return mAlpn; }
|
||||
|
||||
NS_IMETHODIMP SVCBRecord::GetEchConfig(nsACString& aEchConfig) {
|
||||
aEchConfig = mData.mEchConfig;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP SVCBRecord::GetValues(nsTArray<RefPtr<nsISVCParam>>& aValues) {
|
||||
for (const auto& v : mData.mSvcFieldValue) {
|
||||
RefPtr<nsISVCParam> param = new SvcParam(v.mValue);
|
||||
|
@ -89,6 +89,7 @@ struct SVCB {
|
||||
void GetIPHints(CopyableTArray<mozilla::net::NetAddr>& aAddresses) const;
|
||||
uint16_t mSvcFieldPriority = 0;
|
||||
nsCString mSvcDomainName;
|
||||
nsCString mEchConfig;
|
||||
bool mHasIPHints = false;
|
||||
bool mHasEchConfig = false;
|
||||
CopyableTArray<SvcFieldValue> mSvcFieldValue;
|
||||
|
@ -1097,6 +1097,7 @@ nsresult TRR::DohDecode(nsCString& aHost) {
|
||||
}
|
||||
if (value.mValue.is<SvcParamEchConfig>()) {
|
||||
parsed.mHasEchConfig = true;
|
||||
parsed.mEchConfig = value.mValue.as<SvcParamEchConfig>().mValue;
|
||||
}
|
||||
parsed.mSvcFieldValue.AppendElement(value);
|
||||
}
|
||||
|
@ -92,6 +92,7 @@ interface nsISVCBRecord : nsISupports {
|
||||
readonly attribute ACString name;
|
||||
[noscript, nostdcall, notxpcom] readonly attribute MaybePort port;
|
||||
[noscript, nostdcall, notxpcom] readonly attribute MaybeAlpn alpn;
|
||||
readonly attribute ACString echConfig;
|
||||
readonly attribute bool hasIPHintAddress;
|
||||
readonly attribute Array<nsISVCParam> values;
|
||||
};
|
||||
|
@ -367,6 +367,7 @@ struct HttpConnectionInfoCloneArgs
|
||||
nsCString topWindowOrigin;
|
||||
bool isHttp3;
|
||||
bool hasIPHintAddress;
|
||||
nsCString echConfig;
|
||||
ProxyInfoCloneArgs[] proxyInfo;
|
||||
};
|
||||
|
||||
|
@ -2067,6 +2067,14 @@ SocketTransportShim::GetEsniUsed(bool* aEsniUsed) {
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
SocketTransportShim::SetEchConfig(const nsACString& aEchConfig) {
|
||||
if (mIsWebsocket) {
|
||||
LOG3(("WARNING: SocketTransportShim::SetEchConfig %p", this));
|
||||
}
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
SocketTransportShim::ResolvedByTRR(bool* aResolvedByTRR) {
|
||||
if (mIsWebsocket) {
|
||||
|
@ -339,6 +339,7 @@ already_AddRefed<nsHttpConnectionInfo> nsHttpConnectionInfo::Clone() const {
|
||||
clone->SetIPv4Disabled(GetIPv4Disabled());
|
||||
clone->SetIPv6Disabled(GetIPv6Disabled());
|
||||
clone->SetHasIPHintAddress(HasIPHintAddress());
|
||||
clone->SetEchConfig(GetEchConfig());
|
||||
MOZ_ASSERT(clone->Equals(this));
|
||||
|
||||
return clone.forget();
|
||||
@ -393,6 +394,10 @@ nsHttpConnectionInfo::CloneAndAdoptHTTPSSVCRecord(
|
||||
clone->SetHasIPHintAddress(hasIPHint);
|
||||
}
|
||||
|
||||
nsAutoCString echConfig;
|
||||
Unused << aRecord->GetEchConfig(echConfig);
|
||||
clone->SetEchConfig(echConfig);
|
||||
|
||||
return clone.forget();
|
||||
}
|
||||
|
||||
@ -421,6 +426,7 @@ void nsHttpConnectionInfo::SerializeHttpConnectionInfo(
|
||||
aArgs.topWindowOrigin() = aInfo->GetTopWindowOrigin();
|
||||
aArgs.isHttp3() = aInfo->IsHttp3();
|
||||
aArgs.hasIPHintAddress() = aInfo->HasIPHintAddress();
|
||||
aArgs.echConfig() = aInfo->GetEchConfig();
|
||||
|
||||
if (!aInfo->ProxyInfo()) {
|
||||
return;
|
||||
@ -465,6 +471,7 @@ nsHttpConnectionInfo::DeserializeHttpConnectionInfoCloneArgs(
|
||||
cinfo->SetIPv4Disabled(aInfoArgs.isIPv4Disabled());
|
||||
cinfo->SetIPv6Disabled(aInfoArgs.isIPv6Disabled());
|
||||
cinfo->SetHasIPHintAddress(aInfoArgs.hasIPHintAddress());
|
||||
cinfo->SetEchConfig(aInfoArgs.echConfig());
|
||||
|
||||
return cinfo.forget();
|
||||
}
|
||||
@ -491,6 +498,7 @@ void nsHttpConnectionInfo::CloneAsDirectRoute(nsHttpConnectionInfo** outCI) {
|
||||
clone->SetIPv4Disabled(GetIPv4Disabled());
|
||||
clone->SetIPv6Disabled(GetIPv6Disabled());
|
||||
clone->SetHasIPHintAddress(HasIPHintAddress());
|
||||
clone->SetEchConfig(GetEchConfig());
|
||||
|
||||
clone.forget(outCI);
|
||||
}
|
||||
|
@ -212,6 +212,9 @@ class nsHttpConnectionInfo final : public ARefBase {
|
||||
void SetHasIPHintAddress(bool aHasIPHint) { mHasIPHintAddress = aHasIPHint; }
|
||||
bool HasIPHintAddress() const { return mHasIPHintAddress; }
|
||||
|
||||
void SetEchConfig(const nsACString& aEchConfig) { mEchConfig = aEchConfig; }
|
||||
const nsCString& GetEchConfig() const { return mEchConfig; }
|
||||
|
||||
private:
|
||||
// These constructor versions are intended to be used from Clone() and
|
||||
// DeserializeHttpConnectionInfoCloneArgs().
|
||||
@ -264,6 +267,7 @@ class nsHttpConnectionInfo final : public ARefBase {
|
||||
bool mIsHttp3;
|
||||
|
||||
bool mHasIPHintAddress = false;
|
||||
nsCString mEchConfig;
|
||||
|
||||
// for RefPtr
|
||||
NS_INLINE_DECL_THREADSAFE_REFCOUNTING(nsHttpConnectionInfo, override)
|
||||
|
@ -4237,7 +4237,7 @@ nsresult nsHttpConnectionMgr::nsHalfOpenSocket::SetupStreams(
|
||||
}
|
||||
|
||||
if (ci->GetLessThanTls13()) {
|
||||
tmpFlags |= nsISocketTransport::DONT_TRY_ESNI;
|
||||
tmpFlags |= nsISocketTransport::DONT_TRY_ESNI_OR_ECH;
|
||||
}
|
||||
|
||||
if (((mCaps & NS_HTTP_BE_CONSERVATIVE) || ci->GetBeConservative()) &&
|
||||
@ -4330,6 +4330,11 @@ nsresult nsHttpConnectionMgr::nsHalfOpenSocket::SetupStreams(
|
||||
rv = socketTransport->SetSecurityCallbacks(this);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
if (gHttpHandler->EchConfigEnabled()) {
|
||||
rv = socketTransport->SetEchConfig(ci->GetEchConfig());
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
}
|
||||
|
||||
Telemetry::Accumulate(Telemetry::HTTP_CONNECTION_ENTRY_CACHE_HIT_1,
|
||||
mEnt->mUsedForConnection);
|
||||
mEnt->mUsedForConnection = true;
|
||||
|
@ -151,6 +151,12 @@ interface nsISSLSocketControl : nsISupports {
|
||||
*/
|
||||
attribute ACString esniTxt;
|
||||
|
||||
/*
|
||||
* echConfig is defined for conveying the ECH configuration.
|
||||
* This is encoded in base64.
|
||||
*/
|
||||
attribute ACString echConfig;
|
||||
|
||||
/**
|
||||
* The id used to uniquely identify the connection to the peer.
|
||||
*/
|
||||
|
@ -285,6 +285,17 @@ CommonSocketControl::SetEsniTxt(const nsACString& aEsniTxt) {
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
CommonSocketControl::GetEchConfig(nsACString& aEchConfig) {
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
CommonSocketControl::SetEchConfig(const nsACString& aEchConfig) {
|
||||
// TODO: Implement this in bug 1654507.
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
CommonSocketControl::GetPeerId(nsACString& aResult) {
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
|
@ -728,6 +728,40 @@ nsNSSSocketInfo::SetEsniTxt(const nsACString& aEsniTxt) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsNSSSocketInfo::GetEchConfig(nsACString& aEchConfig) {
|
||||
aEchConfig = mEchConfig;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsNSSSocketInfo::SetEchConfig(const nsACString& aEchConfig) {
|
||||
mEchConfig = aEchConfig;
|
||||
|
||||
#if 0
|
||||
if (mEchConfig.Length()) {
|
||||
nsAutoCString echBin;
|
||||
if (NS_OK != Base64Decode(mEchConfig, echBin)) {
|
||||
MOZ_LOG(gPIPNSSLog, LogLevel::Error,
|
||||
("[%p] Invalid EchConfig record. Couldn't base64 decode\n",
|
||||
(void*)mFd));
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
if (SECSuccess != SSL_SetClientEchConfigs(
|
||||
mFd, reinterpret_cast<const PRUint8*>(echBin.get()),
|
||||
echBin.Length())) {
|
||||
MOZ_LOG(gPIPNSSLog, LogLevel::Error,
|
||||
("[%p] Invalid EchConfig record %s\n", (void*)mFd,
|
||||
PR_ErrorToName(PR_GetError())));
|
||||
return NS_OK;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsNSSSocketInfo::GetPeerId(nsACString& aResult) {
|
||||
if (!mPeerId.IsEmpty()) {
|
||||
|
@ -68,6 +68,8 @@ class nsNSSSocketInfo final : public CommonSocketControl {
|
||||
NS_IMETHOD SetClientCert(nsIX509Cert* aClientCert) override;
|
||||
NS_IMETHOD GetEsniTxt(nsACString& aEsniTxt) override;
|
||||
NS_IMETHOD SetEsniTxt(const nsACString& aEsniTxt) override;
|
||||
NS_IMETHOD GetEchConfig(nsACString& aEchConfig) override;
|
||||
NS_IMETHOD SetEchConfig(const nsACString& aEchConfig) override;
|
||||
NS_IMETHOD GetPeerId(nsACString& aResult) override;
|
||||
|
||||
PRStatus CloseSocketAndDestroy();
|
||||
@ -181,6 +183,7 @@ class nsNSSSocketInfo final : public CommonSocketControl {
|
||||
nsresult ActivateSSL();
|
||||
|
||||
nsCString mEsniTxt;
|
||||
nsCString mEchConfig;
|
||||
nsCString mPeerId;
|
||||
bool mEarlyDataAccepted;
|
||||
bool mDenyClientCert;
|
||||
|
Loading…
Reference in New Issue
Block a user