From 1a9c9a09a1fe2f6af7b2ea475cbd1a274b5686b8 Mon Sep 17 00:00:00 2001 From: Tom Schuster Date: Mon, 31 Jul 2023 14:49:55 +0000 Subject: [PATCH] Bug 1607009 - Move nonce getting to SheetLoadData. r=emilio Differential Revision: https://phabricator.services.mozilla.com/D183965 --- dom/base/Document.cpp | 3 +- layout/style/Loader.cpp | 70 +++++++++++++----------------------- layout/style/Loader.h | 6 ++-- layout/style/SheetLoadData.h | 11 ++++-- layout/style/StyleSheet.cpp | 3 +- 5 files changed, 41 insertions(+), 52 deletions(-) diff --git a/dom/base/Document.cpp b/dom/base/Document.cpp index c16c86aa12a5..d2e8604b8903 100644 --- a/dom/base/Document.cpp +++ b/dom/base/Document.cpp @@ -12630,7 +12630,8 @@ SheetPreloadStatus Document::PreloadStyle( // Charset names are always ASCII. auto result = CSSLoader()->LoadSheet( uri, aKind, aEncoding, referrerInfo, obs, aEarlyHintPreloaderId, - Element::StringToCORSMode(aCrossOriginAttr), aIntegrity); + Element::StringToCORSMode(aCrossOriginAttr), /* aNonce */ u""_ns, + aIntegrity); if (result.isErr()) { return SheetPreloadStatus::Errored; } diff --git a/layout/style/Loader.cpp b/layout/style/Loader.cpp index 131f4e937b31..9e6e7f3f99e4 100644 --- a/layout/style/Loader.cpp +++ b/layout/style/Loader.cpp @@ -275,7 +275,8 @@ SheetLoadData::SheetLoadData( StyleSheet* aSheet, SyncLoad aSyncLoad, nsINode* aOwningNode, IsAlternate aIsAlternate, MediaMatched aMediaMatches, StylePreloadKind aPreloadKind, nsICSSLoaderObserver* aObserver, - nsIPrincipal* aTriggeringPrincipal, nsIReferrerInfo* aReferrerInfo) + nsIPrincipal* aTriggeringPrincipal, nsIReferrerInfo* aReferrerInfo, + const nsAString& aNonce) : mLoader(aLoader), mTitle(aTitle), mEncoding(nullptr), @@ -302,6 +303,7 @@ SheetLoadData::SheetLoadData( mObserver(aObserver), mTriggeringPrincipal(aTriggeringPrincipal), mReferrerInfo(aReferrerInfo), + mNonce(aNonce), mGuessedEncoding(GetFallbackEncoding(*aLoader, aOwningNode, nullptr)), mCompatMode(aLoader->CompatMode(aPreloadKind)) { MOZ_ASSERT(!mOwningNodeBeforeLoadEvent || @@ -341,6 +343,7 @@ SheetLoadData::SheetLoadData(css::Loader* aLoader, nsIURI* aURI, mObserver(aObserver), mTriggeringPrincipal(aTriggeringPrincipal), mReferrerInfo(aReferrerInfo), + mNonce(u""_ns), mGuessedEncoding(GetFallbackEncoding( *aLoader, nullptr, aParentData ? aParentData->mEncoding : nullptr)), mCompatMode(aLoader->CompatMode(mPreloadKind)) { @@ -355,7 +358,8 @@ SheetLoadData::SheetLoadData( css::Loader* aLoader, nsIURI* aURI, StyleSheet* aSheet, SyncLoad aSyncLoad, UseSystemPrincipal aUseSystemPrincipal, StylePreloadKind aPreloadKind, const Encoding* aPreloadEncoding, nsICSSLoaderObserver* aObserver, - nsIPrincipal* aTriggeringPrincipal, nsIReferrerInfo* aReferrerInfo) + nsIPrincipal* aTriggeringPrincipal, nsIReferrerInfo* aReferrerInfo, + const nsAString& aNonce) : mLoader(aLoader), mEncoding(nullptr), mURI(aURI), @@ -380,6 +384,7 @@ SheetLoadData::SheetLoadData( mObserver(aObserver), mTriggeringPrincipal(aTriggeringPrincipal), mReferrerInfo(aReferrerInfo), + mNonce(aNonce), mGuessedEncoding( GetFallbackEncoding(*aLoader, nullptr, aPreloadEncoding)), mCompatMode(aLoader->CompatMode(aPreloadKind)) { @@ -872,12 +877,7 @@ nsresult Loader::CheckContentPolicy(nsIPrincipal* aLoadingPrincipal, nsCOMPtr secCheckLoadInfo = new net::LoadInfo( aLoadingPrincipal, aTriggeringPrincipal, aRequestingNode, nsILoadInfo::SEC_ONLY_FOR_EXPLICIT_CONTENTSEC_CHECK, contentPolicyType); - - // snapshot the nonce at load start time for performing CSP checks - if (contentPolicyType == nsIContentPolicy::TYPE_INTERNAL_STYLESHEET) { - secCheckLoadInfo->SetCspNonce(aNonce); - MOZ_ASSERT_IF(aPreloadKind != StylePreloadKind::None, aNonce.IsEmpty()); - } + secCheckLoadInfo->SetCspNonce(aNonce); int16_t shouldLoad = nsIContentPolicy::ACCEPT; nsresult rv = NS_CheckContentLoadPolicy(aTargetURI, secCheckLoadInfo, @@ -1252,18 +1252,8 @@ nsresult Loader::LoadSheet(SheetLoadData& aLoadData, SheetState aSheetState, return rv; } - // snapshot the nonce at load start time for performing CSP checks - if (contentPolicyType == nsIContentPolicy::TYPE_INTERNAL_STYLESHEET) { - if (requestingNode) { - // TODO(bug 1607009) move to SheetLoadData - nsString* cspNonce = static_cast( - requestingNode->GetProperty(nsGkAtoms::nonce)); - if (cspNonce) { - nsCOMPtr loadInfo = channel->LoadInfo(); - loadInfo->SetCspNonce(*cspNonce); - } - } - } + nsCOMPtr loadInfo = channel->LoadInfo(); + loadInfo->SetCspNonce(aLoadData.Nonce()); nsCOMPtr stream; rv = channel->Open(getter_AddRefs(stream)); @@ -1391,18 +1381,8 @@ nsresult Loader::LoadSheet(SheetLoadData& aLoadData, SheetState aSheetState, return rv; } - // snapshot the nonce at load start time for performing CSP checks - if (contentPolicyType == nsIContentPolicy::TYPE_INTERNAL_STYLESHEET) { - if (requestingNode) { - // TODO(bug 1607009) move to SheetLoadData - nsString* cspNonce = - static_cast(requestingNode->GetProperty(nsGkAtoms::nonce)); - if (cspNonce) { - nsCOMPtr loadInfo = channel->LoadInfo(); - loadInfo->SetCspNonce(*cspNonce); - } - } - } + nsCOMPtr loadInfo = channel->LoadInfo(); + loadInfo->SetCspNonce(aLoadData.Nonce()); if (!aLoadData.ShouldDefer()) { if (nsCOMPtr cos = do_QueryInterface(channel)) { @@ -1770,7 +1750,7 @@ Result Loader::LoadInlineStyle( auto data = MakeRefPtr( this, aInfo.mTitle, /* aURI = */ nullptr, sheet, SyncLoad::No, aInfo.mContent, isAlternate, matched, StylePreloadKind::None, aObserver, - principal, aInfo.mReferrerInfo); + principal, aInfo.mReferrerInfo, aInfo.mNonce); MOZ_ASSERT(data->GetRequestingNode() == aInfo.mContent); data->mLineNumber = aLineNumber; @@ -1890,7 +1870,7 @@ Result Loader::LoadStyleLink( auto data = MakeRefPtr( this, aInfo.mTitle, aInfo.mURI, sheet, SyncLoad(syncLoad), aInfo.mContent, isAlternate, matched, StylePreloadKind::None, aObserver, principal, - aInfo.mReferrerInfo); + aInfo.mReferrerInfo, aInfo.mNonce); MOZ_ASSERT(data->GetRequestingNode() == requestingNode); @@ -1976,7 +1956,7 @@ nsresult Loader::LoadChildSheet(StyleSheet& aParentSheet, nsIPrincipal* principal = aParentSheet.Principal(); nsresult rv = CheckContentPolicy(LoaderPrincipal(), principal, aURL, requestingNode, - u""_ns, StylePreloadKind::None); + /* aNonce = */ u""_ns, StylePreloadKind::None); if (NS_WARN_IF(NS_FAILED(rv))) { if (aParentData) { MarkLoadTreeFailed(*aParentData); @@ -2060,7 +2040,7 @@ Result, nsresult> Loader::LoadSheetSync( nsCOMPtr referrerInfo = new ReferrerInfo(nullptr); return InternalLoadNonDocumentSheet( aURL, StylePreloadKind::None, aParsingMode, aUseSystemPrincipal, nullptr, - referrerInfo, nullptr, CORS_NONE, u""_ns, 0); + referrerInfo, nullptr, CORS_NONE, u""_ns, u""_ns, 0); } Result, nsresult> Loader::LoadSheet( @@ -2069,26 +2049,26 @@ Result, nsresult> Loader::LoadSheet( nsCOMPtr referrerInfo = new ReferrerInfo(nullptr); return InternalLoadNonDocumentSheet( aURI, StylePreloadKind::None, aParsingMode, aUseSystemPrincipal, nullptr, - referrerInfo, aObserver, CORS_NONE, u""_ns, 0); + referrerInfo, aObserver, CORS_NONE, u""_ns, u""_ns, 0); } Result, nsresult> Loader::LoadSheet( nsIURI* aURL, StylePreloadKind aPreloadKind, const Encoding* aPreloadEncoding, nsIReferrerInfo* aReferrerInfo, nsICSSLoaderObserver* aObserver, uint64_t aEarlyHintPreloaderId, - CORSMode aCORSMode, const nsAString& aIntegrity) { + CORSMode aCORSMode, const nsAString& aNonce, const nsAString& aIntegrity) { LOG(("css::Loader::LoadSheet(aURL, aObserver) api call")); - return InternalLoadNonDocumentSheet(aURL, aPreloadKind, eAuthorSheetFeatures, - UseSystemPrincipal::No, aPreloadEncoding, - aReferrerInfo, aObserver, aCORSMode, - aIntegrity, aEarlyHintPreloaderId); + return InternalLoadNonDocumentSheet( + aURL, aPreloadKind, eAuthorSheetFeatures, UseSystemPrincipal::No, + aPreloadEncoding, aReferrerInfo, aObserver, aCORSMode, aNonce, aIntegrity, + aEarlyHintPreloaderId); } Result, nsresult> Loader::InternalLoadNonDocumentSheet( nsIURI* aURL, StylePreloadKind aPreloadKind, SheetParsingMode aParsingMode, UseSystemPrincipal aUseSystemPrincipal, const Encoding* aPreloadEncoding, nsIReferrerInfo* aReferrerInfo, nsICSSLoaderObserver* aObserver, - CORSMode aCORSMode, const nsAString& aIntegrity, + CORSMode aCORSMode, const nsAString& aNonce, const nsAString& aIntegrity, uint64_t aEarlyHintPreloaderId) { MOZ_ASSERT(aURL, "Must have a URI to load"); MOZ_ASSERT(aUseSystemPrincipal == UseSystemPrincipal::No || !aObserver, @@ -2105,7 +2085,7 @@ Result, nsresult> Loader::InternalLoadNonDocumentSheet( nsIPrincipal* loadingPrincipal = LoaderPrincipal(); nsIPrincipal* triggeringPrincipal = loadingPrincipal; nsresult rv = CheckContentPolicy(loadingPrincipal, triggeringPrincipal, aURL, - mDocument, u""_ns, aPreloadKind); + mDocument, aNonce, aPreloadKind); if (NS_FAILED(rv)) { return Err(rv); } @@ -2120,7 +2100,7 @@ Result, nsresult> Loader::InternalLoadNonDocumentSheet( auto data = MakeRefPtr( this, aURL, sheet, SyncLoad(syncLoad), aUseSystemPrincipal, aPreloadKind, - aPreloadEncoding, aObserver, triggeringPrincipal, aReferrerInfo); + aPreloadEncoding, aObserver, triggeringPrincipal, aReferrerInfo, aNonce); MOZ_ASSERT(data->GetRequestingNode() == mDocument); if (state == SheetState::Complete) { LOG((" Sheet already complete")); diff --git a/layout/style/Loader.h b/layout/style/Loader.h index 57ea59793f35..73d7b806a18e 100644 --- a/layout/style/Loader.h +++ b/layout/style/Loader.h @@ -373,8 +373,8 @@ class Loader final { Result, nsresult> LoadSheet( nsIURI* aURI, StylePreloadKind, const Encoding* aPreloadEncoding, nsIReferrerInfo* aReferrerInfo, nsICSSLoaderObserver* aObserver, - uint64_t aEarlyHintPreloaderId, CORSMode = CORS_NONE, - const nsAString& aIntegrity = u""_ns); + uint64_t aEarlyHintPreloaderId, CORSMode aCORSMode, + const nsAString& aNonce, const nsAString& aIntegrity); /** * As above, but without caring for a couple things. @@ -539,7 +539,7 @@ class Loader final { nsIURI* aURL, StylePreloadKind, SheetParsingMode aParsingMode, UseSystemPrincipal, const Encoding* aPreloadEncoding, nsIReferrerInfo* aReferrerInfo, nsICSSLoaderObserver* aObserver, - CORSMode aCORSMode, const nsAString& aIntegrity, + CORSMode aCORSMode, const nsAString& aNonce, const nsAString& aIntegrity, uint64_t aEarlyHintPreloaderId); RefPtr LookupInlineSheetInCache(const nsAString&, nsIPrincipal*); diff --git a/layout/style/SheetLoadData.h b/layout/style/SheetLoadData.h index 6b4b526dbbcc..07459685ae8c 100644 --- a/layout/style/SheetLoadData.h +++ b/layout/style/SheetLoadData.h @@ -62,7 +62,8 @@ class SheetLoadData final SheetLoadData(css::Loader*, const nsAString& aTitle, nsIURI*, StyleSheet*, SyncLoad, nsINode* aOwningNode, IsAlternate, MediaMatched, StylePreloadKind, nsICSSLoaderObserver* aObserver, - nsIPrincipal* aTriggeringPrincipal, nsIReferrerInfo*); + nsIPrincipal* aTriggeringPrincipal, nsIReferrerInfo*, + const nsAString& aNonce); // Data for loading a sheet linked from an @import rule SheetLoadData(css::Loader*, nsIURI*, StyleSheet*, SheetLoadData* aParentData, @@ -74,10 +75,13 @@ class SheetLoadData final UseSystemPrincipal, StylePreloadKind, const Encoding* aPreloadEncoding, nsICSSLoaderObserver* aObserver, - nsIPrincipal* aTriggeringPrincipal, nsIReferrerInfo*); + nsIPrincipal* aTriggeringPrincipal, nsIReferrerInfo*, + const nsAString& aNonce); nsIReferrerInfo* ReferrerInfo() const { return mReferrerInfo; } + const nsString& Nonce() const { return mNonce; } + already_AddRefed PrepareLoadEventIfNeeded(); NotNull DetermineNonBOMEncoding(const nsACString& aSegment, @@ -221,6 +225,9 @@ class SheetLoadData final // Referrer info of the load. const nsCOMPtr mReferrerInfo; + // The cryptographic nonce of the load used for CSP checks. + const nsString mNonce; + // The encoding guessed from attributes and the document character set. const NotNull mGuessedEncoding; diff --git a/layout/style/StyleSheet.cpp b/layout/style/StyleSheet.cpp index 9459272d0cdc..64fe0faa7550 100644 --- a/layout/style/StyleSheet.cpp +++ b/layout/style/StyleSheet.cpp @@ -719,7 +719,8 @@ already_AddRefed StyleSheet::Replace(const nsACString& aText, loader, /* aURI = */ nullptr, this, css::SyncLoad::No, css::Loader::UseSystemPrincipal::No, css::StylePreloadKind::None, /* aPreloadEncoding */ nullptr, /* aObserver */ nullptr, - mConstructorDocument->NodePrincipal(), GetReferrerInfo()); + mConstructorDocument->NodePrincipal(), GetReferrerInfo(), + /* aNonce */ u""_ns); // In parallel // 5.1 Parse aText into rules.