From 21ff29fca8cd4047009d2fa84d5465ab809d05a3 Mon Sep 17 00:00:00 2001 From: roytam1 Date: Fri, 25 Jul 2025 23:29:37 +0800 Subject: [PATCH] import from UXP: Issue #2828 - Part 1: Build and store the array of layer name tokens in the layer at-rules (53e6317b) --- layout/style/nsCSSParser.cpp | 74 ++++++++++++++++++------------------ layout/style/nsCSSRules.cpp | 58 +++++++++++++++++++++++++--- layout/style/nsCSSRules.h | 7 ++++ 3 files changed, 95 insertions(+), 44 deletions(-) diff --git a/layout/style/nsCSSParser.cpp b/layout/style/nsCSSParser.cpp index 8321e1982..a4c89db93 100644 --- a/layout/style/nsCSSParser.cpp +++ b/layout/style/nsCSSParser.cpp @@ -5232,8 +5232,11 @@ CSSParserImpl::ParseSupportsConditionTermsAfterOperator( bool CSSParserImpl::ParseLayerRule(RuleAppendFunc aAppendFunc, void* aProcessData) { - nsString layerName; - nsTArray* nameList = new nsTArray(); + nsString name; + nsTArray path; + + nsTArray nameList; + nsTArray> pathList; uint32_t linenum, colnum; if (!GetNextTokenLocation(true, &linenum, &colnum)) { @@ -5249,8 +5252,8 @@ CSSParserImpl::ParseLayerRule(RuleAppendFunc aAppendFunc, void* aProcessData) // followed by a "{", which indicates an anonymous layer. bool isStatement = false; if (tk->mType == eCSSToken_Ident) { - nsString* currentName = new nsString(); - currentName->Assign(tk->mIdent); + name.Assign(tk->mIdent); + path.AppendElement(tk->mIdent); bool parsing = true; bool expectIdent = false; @@ -5263,49 +5266,40 @@ CSSParserImpl::ParseLayerRule(RuleAppendFunc aAppendFunc, void* aProcessData) case eCSSToken_Symbol: { if ('.' == tk->mSymbol) { expectIdent = true; - if (!currentName->IsEmpty()) { - currentName->Append(tk->mSymbol); + if (!name.IsEmpty()) { + name.Append(tk->mSymbol); continue; } parsing = false; break; - } else if (',' == tk->mSymbol) { + } else if (',' == tk->mSymbol || ';' == tk->mSymbol || '{' == tk->mSymbol) { if (expectIdent) { parsing = false; break; } - nameList->AppendElement(*currentName); - currentName = new nsString(); + nameList.AppendElement(name); + pathList.AppendElement(path); + if ('{' == tk->mSymbol) { + if (nameList.Length() > 1) { + return false; + } + parsing = false; + break; + } else if (';' == tk->mSymbol) { + isStatement = true; + parsing = false; + break; + } + name.Truncate(); + path.Clear(); expectIdent = true; continue; - } else if (';' == tk->mSymbol) { - if (expectIdent) { - parsing = false; - break; - } - nameList->AppendElement(*currentName); - currentName = new nsString(); - isStatement = true; - parsing = false; - break; - } else if ('{' == tk->mSymbol) { - if (expectIdent) { - parsing = false; - break; - } - nameList->AppendElement(*currentName); - uint32_t nameListLength = nameList->Length(); - if (nameListLength == 0 || nameListLength > 1) { - return false; - } - layerName.Assign(nameList->ElementAt(0)); - parsing = false; - break; } } case eCSSToken_Ident: { expectIdent = false; - currentName->Append(tk->mIdent); + name.Append(tk->mIdent); + path.AppendElement(tk->mIdent); break; } default: { @@ -5317,22 +5311,26 @@ CSSParserImpl::ParseLayerRule(RuleAppendFunc aAppendFunc, void* aProcessData) if (expectIdent) { UngetToken(); return false; - } - } else if (tk->mType == eCSSToken_Symbol && '{' != tk->mSymbol) { - UngetToken(); + } + } else if (tk->mType == eCSSToken_Symbol) { + if ('{' != tk->mSymbol) { + UngetToken(); + return false; + } + } else { return false; } if (isStatement) { RefPtr rule = - new CSSLayerStatementRule(*nameList, linenum, colnum); + new CSSLayerStatementRule(nameList, pathList, linenum, colnum); (*aAppendFunc)(rule, aProcessData); return true; } UngetToken(); RefPtr rule = - new CSSLayerBlockRule(layerName, linenum, colnum); + new CSSLayerBlockRule(name, path, linenum, colnum); return ParseGroupRule(rule, aAppendFunc, aProcessData); } diff --git a/layout/style/nsCSSRules.cpp b/layout/style/nsCSSRules.cpp index 00915a4a0..afdbfc1cb 100644 --- a/layout/style/nsCSSRules.cpp +++ b/layout/style/nsCSSRules.cpp @@ -3355,15 +3355,18 @@ namespace mozilla { CSSLayerStatementRule::CSSLayerStatementRule( const nsTArray& aNameList, + const nsTArray>& aPathList, uint32_t aLineNumber, uint32_t aColumnNumber) : Rule(aLineNumber, aColumnNumber) , mNameList(aNameList) + , mPathList(aPathList) { } CSSLayerStatementRule::CSSLayerStatementRule(const CSSLayerStatementRule& aCopy) : Rule(aCopy) , mNameList(aCopy.mNameList) + , mPathList(aCopy.mPathList) { } @@ -3390,6 +3393,7 @@ NS_IMPL_CYCLE_COLLECTION_CLASS(CSSLayerStatementRule) NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN(CSSLayerStatementRule) tmp->mNameList.Clear(); + tmp->mPathList.Clear(); NS_IMPL_CYCLE_COLLECTION_UNLINK_END NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(CSSLayerStatementRule, mozilla::css::Rule) @@ -3441,10 +3445,28 @@ CSSLayerStatementRule::GetNameList(nsTArray& aResult) aResult = mNameList; } +void +CSSLayerStatementRule::GetPathList(nsTArray>& aResult) +{ + aResult = mPathList; +} + /* virtual */ size_t CSSLayerStatementRule::SizeOfIncludingThis(MallocSizeOf aMallocSizeOf) const { - return aMallocSizeOf(this); + size_t n = aMallocSizeOf(this); + n += mNameList.ShallowSizeOfExcludingThis(aMallocSizeOf); + for (const nsString& s : mNameList) { + n += s.SizeOfExcludingThisIfUnshared(aMallocSizeOf); + } + n += mPathList.ShallowSizeOfExcludingThis(aMallocSizeOf); + for (const nsTArray& inner : mPathList) { + n += inner.ShallowSizeOfExcludingThis(aMallocSizeOf); + for (const nsString& str : inner) { + n += str.SizeOfExcludingThisIfUnshared(aMallocSizeOf); + } + } + return n; } /* virtual */ JSObject* @@ -3460,9 +3482,11 @@ CSSLayerStatementRule::WrapObject(JSContext* aCx, // CSSLayerBlockRule::CSSLayerBlockRule(const nsString& aName, + const nsTArray& aPath, uint32_t aLineNumber, uint32_t aColumnNumber) : css::GroupRule(aLineNumber, aColumnNumber) , mName(aName) + , mPath(aPath) { } @@ -3473,6 +3497,7 @@ CSSLayerBlockRule::~CSSLayerBlockRule() CSSLayerBlockRule::CSSLayerBlockRule(const CSSLayerBlockRule& aCopy) : css::GroupRule(aCopy) , mName(aCopy.mName) + , mPath(aCopy.mPath) { } @@ -3505,15 +3530,32 @@ CSSLayerBlockRule::UseForPresentation(nsPresContext* aPresContext, return true; } -NS_IMPL_ADDREF_INHERITED(CSSLayerBlockRule, css::GroupRule) -NS_IMPL_RELEASE_INHERITED(CSSLayerBlockRule, css::GroupRule) +void +CSSLayerBlockRule::GetPath(nsTArray& aResult) +{ + aResult = mPath; +} + +NS_IMPL_ADDREF_INHERITED(CSSLayerBlockRule, GroupRule) +NS_IMPL_RELEASE_INHERITED(CSSLayerBlockRule, GroupRule) // QueryInterface implementation for CSSLayerBlockRule -NS_INTERFACE_MAP_BEGIN(CSSLayerBlockRule) +NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(CSSLayerBlockRule) NS_INTERFACE_MAP_ENTRY(nsIDOMCSSGroupingRule) NS_INTERFACE_MAP_ENTRY(nsIDOMCSSLayerBlockRule) NS_INTERFACE_MAP_END_INHERITING(GroupRule) +NS_IMPL_CYCLE_COLLECTION_CLASS(CSSLayerBlockRule) + +NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(CSSLayerBlockRule, + GroupRule) + tmp->mPath.Clear(); +NS_IMPL_CYCLE_COLLECTION_UNLINK_END + +NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(CSSLayerBlockRule, + GroupRule) +NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END + uint16_t CSSLayerBlockRule::Type() const { @@ -3549,9 +3591,9 @@ CSSLayerBlockRule::DeleteRule(uint32_t aIndex) // nsIDOMCSSLayerBlockRule methods NS_IMETHODIMP -CSSLayerBlockRule::GetName(nsAString& aConditionText) +CSSLayerBlockRule::GetName(nsAString& aLayerName) { - aConditionText.Assign(mName); + aLayerName.Assign(mName); return NS_OK; } @@ -3561,6 +3603,10 @@ CSSLayerBlockRule::SizeOfIncludingThis(MallocSizeOf aMallocSizeOf) const size_t n = aMallocSizeOf(this); n += css::GroupRule::SizeOfExcludingThis(aMallocSizeOf); n += mName.SizeOfExcludingThisIfUnshared(aMallocSizeOf); + n += mPath.ShallowSizeOfExcludingThis(aMallocSizeOf); + for (const nsString& s : mPath) { + n += s.SizeOfExcludingThisIfUnshared(aMallocSizeOf); + } return n; } diff --git a/layout/style/nsCSSRules.h b/layout/style/nsCSSRules.h index 32b4b688f..ab56b21cb 100644 --- a/layout/style/nsCSSRules.h +++ b/layout/style/nsCSSRules.h @@ -758,6 +758,7 @@ class CSSLayerStatementRule final : public css::Rule, { public: CSSLayerStatementRule(const nsTArray& aNameList, + const nsTArray>& aPathList, uint32_t aLineNumber, uint32_t aColumnNumber); CSSLayerStatementRule(const CSSLayerStatementRule& aCopy); @@ -780,6 +781,7 @@ public: uint16_t Type() const override; void GetCssTextImpl(nsAString& aCssText) const override; void GetNameList(nsTArray& aResult); + void GetPathList(nsTArray>& aResult); virtual size_t SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const override; @@ -789,6 +791,7 @@ protected: virtual ~CSSLayerStatementRule(); nsTArray mNameList; + nsTArray> mPathList; }; class CSSLayerBlockRule final : public css::GroupRule, @@ -796,6 +799,7 @@ class CSSLayerBlockRule final : public css::GroupRule, { public: CSSLayerBlockRule(const nsString& aName, + const nsTArray& aPath, uint32_t aLineNumber, uint32_t aColumnNumber); CSSLayerBlockRule(const CSSLayerBlockRule& aCopy); @@ -808,7 +812,9 @@ public: virtual already_AddRefed Clone() const override; virtual bool UseForPresentation(nsPresContext* aPresContext, nsMediaQueryResultCacheKey& aKey) override; + void GetPath(nsTArray& aResult); + NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(CSSLayerBlockRule, GroupRule) NS_DECL_ISUPPORTS_INHERITED // nsIDOMCSSGroupingRule interface @@ -830,6 +836,7 @@ protected: virtual ~CSSLayerBlockRule(); nsString mName; + nsTArray mPath; }; } // namespace mozilla