From 8884b0618e3b5b23a8686435a9873ca7520284c7 Mon Sep 17 00:00:00 2001 From: Gijs Kruitbosch Date: Sat, 26 Sep 2015 23:51:42 +0200 Subject: [PATCH] Bug 1207084 - keep sheet level on tokenstream for use in ruledata when resolving variables, to fix hcm issues with CSS variables, r=heycam --HG-- extra : commitid : LOEulYWs1jS extra : rebase_source : b9741e3bc6a4a762a2f6295d8d81069aca66745f extra : amend_source : 13dd115d63546f57127fe65163c2aaacf8c6b043 --- layout/style/nsCSSDataBlock.cpp | 9 +++++++++ layout/style/nsCSSValue.cpp | 2 ++ layout/style/nsCSSValue.h | 1 + layout/style/nsRuleNode.cpp | 6 ++++++ 4 files changed, 18 insertions(+) diff --git a/layout/style/nsCSSDataBlock.cpp b/layout/style/nsCSSDataBlock.cpp index 54fc58a780a5..602a071eeb8e 100644 --- a/layout/style/nsCSSDataBlock.cpp +++ b/layout/style/nsCSSDataBlock.cpp @@ -262,6 +262,15 @@ nsCSSCompressedDataBlock::MapRuleInfoInto(nsRuleData *aRuleData) const nsCSSValue* target = aRuleData->ValueFor(iProp); if (target->GetUnit() == eCSSUnit_Null) { const nsCSSValue *val = ValueAtIndex(i); + // In order for variable resolution to have the right information + // about the stylesheet level of a value, that level needs to be + // stored on the token stream. We can't do that at creation time + // because the CSS parser (which creates the object) has no idea + // about the stylesheet level, so we do it here instead, where + // the rule walking will have just updated aRuleData. + if (val->GetUnit() == eCSSUnit_TokenStream) { + val->GetTokenStreamValue()->mLevel = aRuleData->mLevel; + } MapSinglePropertyInto(iProp, val, target, aRuleData); } } diff --git a/layout/style/nsCSSValue.cpp b/layout/style/nsCSSValue.cpp index fce74b3d5384..c9d072b66cd5 100644 --- a/layout/style/nsCSSValue.cpp +++ b/layout/style/nsCSSValue.cpp @@ -23,6 +23,7 @@ #include "nsPresContext.h" #include "nsStyleUtil.h" #include "nsDeviceContext.h" +#include "nsStyleSet.h" using namespace mozilla; @@ -2537,6 +2538,7 @@ nsCSSValueGradient::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) con nsCSSValueTokenStream::nsCSSValueTokenStream() : mPropertyID(eCSSProperty_UNKNOWN) , mShorthandPropertyID(eCSSProperty_UNKNOWN) + , mLevel(nsStyleSet::eSheetTypeCount) { MOZ_COUNT_CTOR(nsCSSValueTokenStream); } diff --git a/layout/style/nsCSSValue.h b/layout/style/nsCSSValue.h index 009991834ead..225dd9061438 100644 --- a/layout/style/nsCSSValue.h +++ b/layout/style/nsCSSValue.h @@ -1541,6 +1541,7 @@ public: // mozilla::CSSStyleSheet* mSheet; uint32_t mLineNumber; uint32_t mLineOffset; + uint16_t mLevel; // an nsStyleSet::sheetType private: nsCSSValueTokenStream(const nsCSSValueTokenStream& aOther) = delete; diff --git a/layout/style/nsRuleNode.cpp b/layout/style/nsRuleNode.cpp index 8c19ef5ee509..427fb243bbaa 100644 --- a/layout/style/nsRuleNode.cpp +++ b/layout/style/nsRuleNode.cpp @@ -2180,6 +2180,12 @@ nsRuleNode::ResolveVariableReferences(const nsStyleStructID aSID, &aContext->StyleVariables()->mVariables; nsCSSValueTokenStream* tokenStream = value->GetTokenStreamValue(); + MOZ_ASSERT(tokenStream->mLevel != nsStyleSet::eSheetTypeCount, + "Token stream should have a defined level"); + + AutoRestore saveLevel(aRuleData->mLevel); + aRuleData->mLevel = tokenStream->mLevel; + // Note that ParsePropertyWithVariableReferences relies on the fact // that the nsCSSValue in aRuleData for the property we are re-parsing // is still the token stream value. When