Title: [125294] trunk/Source/WebCore
Revision
125294
Author
kl...@webkit.org
Date
2012-08-10 10:00:40 -0700 (Fri, 10 Aug 2012)

Log Message

CSS: Shrink RuleData by storing selector as index rather than pointer.
<http://webkit.org/b/93712>

Reviewed by Antti Koivisto.

Pack the selector's index in the rule in the RuleData bitfield, effectively
shrinking each RuleData by 8 bytes.

* css/CSSSelectorList.h:
(WebCore::CSSSelectorList::selectorAt):
(WebCore::CSSSelectorList::indexOfNextSelectorAfter):

    Add helpers to CSSSelectorList to iterate by index.

* css/StyleResolver.cpp:
(RuleData):
(WebCore::RuleData::selector):
(WebCore::RuleData::selectorIndex):
(SameSizeAsRuleData):
(RuleSet):
(WebCore::makeRuleSet):
(WebCore::StyleResolver::collectMatchingRulesForList):
* css/StyleResolver.h:
(WebCore::StyleResolver::RuleFeature::RuleFeature):
(RuleFeature):

    Store selector indices instead of CSSSelector* pointers.

Modified Paths

Diff

Modified: trunk/Source/WebCore/ChangeLog (125293 => 125294)


--- trunk/Source/WebCore/ChangeLog	2012-08-10 16:48:57 UTC (rev 125293)
+++ trunk/Source/WebCore/ChangeLog	2012-08-10 17:00:40 UTC (rev 125294)
@@ -1,3 +1,33 @@
+2012-08-10  Andreas Kling  <kl...@webkit.org>
+
+        CSS: Shrink RuleData by storing selector as index rather than pointer.
+        <http://webkit.org/b/93712>
+
+        Reviewed by Antti Koivisto.
+
+        Pack the selector's index in the rule in the RuleData bitfield, effectively
+        shrinking each RuleData by 8 bytes.
+
+        * css/CSSSelectorList.h:
+        (WebCore::CSSSelectorList::selectorAt):
+        (WebCore::CSSSelectorList::indexOfNextSelectorAfter):
+
+            Add helpers to CSSSelectorList to iterate by index.
+
+        * css/StyleResolver.cpp:
+        (RuleData):
+        (WebCore::RuleData::selector):
+        (WebCore::RuleData::selectorIndex):
+        (SameSizeAsRuleData):
+        (RuleSet):
+        (WebCore::makeRuleSet):
+        (WebCore::StyleResolver::collectMatchingRulesForList):
+        * css/StyleResolver.h:
+        (WebCore::StyleResolver::RuleFeature::RuleFeature):
+        (RuleFeature):
+
+            Store selector indices instead of CSSSelector* pointers.
+
 2012-08-10  Vineet Chaudhary  <rgf...@motorola.com>
 
         Remove custom bindings from WaveShaperNode.

Modified: trunk/Source/WebCore/css/CSSSelectorList.h (125293 => 125294)


--- trunk/Source/WebCore/css/CSSSelectorList.h	2012-08-10 16:48:57 UTC (rev 125293)
+++ trunk/Source/WebCore/css/CSSSelectorList.h	2012-08-10 17:00:40 UTC (rev 125294)
@@ -48,7 +48,17 @@
     CSSSelector* first() const { return m_selectorArray ? m_selectorArray : 0; }
     static CSSSelector* next(CSSSelector*);
     bool hasOneSelector() const { return m_selectorArray && !next(m_selectorArray); }
+    CSSSelector* selectorAt(size_t index) const { return &m_selectorArray[index]; }
 
+    size_t indexOfNextSelectorAfter(size_t index) const
+    {
+        CSSSelector* current = selectorAt(index);
+        current = next(current);
+        if (!current)
+            return notFound;
+        return current - m_selectorArray;
+    }
+
     bool selectorsNeedNamespaceResolution();
     bool hasUnknownPseudoElements() const;
 

Modified: trunk/Source/WebCore/css/StyleResolver.cpp (125293 => 125294)


--- trunk/Source/WebCore/css/StyleResolver.cpp	2012-08-10 16:48:57 UTC (rev 125293)
+++ trunk/Source/WebCore/css/StyleResolver.cpp	2012-08-10 17:00:40 UTC (rev 125294)
@@ -199,11 +199,12 @@
 
 class RuleData {
 public:
-    RuleData(StyleRule*, CSSSelector*, unsigned position, bool hasDocumentSecurityOrigin, bool canUseFastCheckSelector, bool inRegionRule);
+    RuleData(StyleRule*, unsigned selectorIndex, unsigned position, bool hasDocumentSecurityOrigin, bool canUseFastCheckSelector, bool inRegionRule);
 
     unsigned position() const { return m_position; }
     StyleRule* rule() const { return m_rule; }
-    CSSSelector* selector() const { return m_selector; }
+    CSSSelector* selector() const { return m_rule->selectorList().selectorAt(m_selectorIndex); }
+    unsigned selectorIndex() const { return m_selectorIndex; }
 
     bool hasFastCheckableSelector() const { return m_hasFastCheckableSelector; }
     bool hasMultipartSelector() const { return m_hasMultipartSelector; }
@@ -222,11 +223,11 @@
 
 private:
     StyleRule* m_rule;
-    CSSSelector* m_selector;
-    unsigned m_specificity;
+    unsigned m_selectorIndex : 12;
     // This number was picked fairly arbitrarily. We can probably lower it if we need to.
     // Some simple testing showed <100,000 RuleData's on large sites.
-    unsigned m_position : 24;
+    unsigned m_position : 20;
+    unsigned m_specificity : 24;
     unsigned m_hasFastCheckableSelector : 1;
     unsigned m_hasMultipartSelector : 1;
     unsigned m_hasRightmostSelectorMatchingHTMLBasedOnRuleHash : 1;
@@ -240,10 +241,8 @@
     
 struct SameSizeAsRuleData {
     void* a;
-    void* b;
-    unsigned c;
-    unsigned d;
-    unsigned e[4];
+    uint64_t b;
+    unsigned c[4];
 };
 
 COMPILE_ASSERT(sizeof(RuleData) == sizeof(SameSizeAsRuleData), RuleData_should_stay_small);
@@ -258,7 +257,7 @@
     void addRulesFromSheet(StyleSheetContents*, const MediaQueryEvaluator&, StyleResolver* = 0, const ContainerNode* = 0);
 
     void addStyleRule(StyleRule*, bool hasDocumentSecurityOrigin, bool canUseFastCheckSelector, bool isInRegionRule = false);
-    void addRule(StyleRule*, CSSSelector*, bool hasDocumentSecurityOrigin, bool canUseFastCheckSelector, bool isInRegionRule = false);
+    void addRule(StyleRule*, unsigned selectorIndex, bool hasDocumentSecurityOrigin, bool canUseFastCheckSelector, bool isInRegionRule = false);
     void addPageRule(StyleRulePage*);
     void addToRuleSet(AtomicStringImpl* key, AtomRuleMap&, const RuleData&);
     void addRegionRule(StyleRuleRegion*, bool hasDocumentSecurityOrigin);
@@ -481,7 +480,7 @@
         return nullptr;
     OwnPtr<RuleSet> ruleSet = RuleSet::create();
     for (size_t i = 0; i < size; ++i)
-        ruleSet->addRule(rules[i].rule, rules[i].selector, rules[i].hasDocumentSecurityOrigin, false);
+        ruleSet->addRule(rules[i].rule, rules[i].selectorIndex, rules[i].hasDocumentSecurityOrigin, false);
     ruleSet->shrinkToFit();
     return ruleSet.release();
 }
@@ -2495,20 +2494,22 @@
     return false;
 }
 
-RuleData::RuleData(StyleRule* rule, CSSSelector* selector, unsigned position, bool hasDocumentSecurityOrigin, bool canUseFastCheckSelector, bool inRegionRule)
+RuleData::RuleData(StyleRule* rule, unsigned selectorIndex, unsigned position, bool hasDocumentSecurityOrigin, bool canUseFastCheckSelector, bool inRegionRule)
     : m_rule(rule)
-    , m_selector(selector)
-    , m_specificity(selector->specificity())
+    , m_selectorIndex(selectorIndex)
     , m_position(position)
-    , m_hasFastCheckableSelector(canUseFastCheckSelector && SelectorChecker::isFastCheckableSelector(selector))
-    , m_hasMultipartSelector(!!selector->tagHistory())
-    , m_hasRightmostSelectorMatchingHTMLBasedOnRuleHash(isSelectorMatchingHTMLBasedOnRuleHash(selector))
-    , m_containsUncommonAttributeSelector(WebCore::containsUncommonAttributeSelector(selector))
-    , m_linkMatchType(SelectorChecker::determineLinkMatchType(selector))
+    , m_specificity(selector()->specificity())
+    , m_hasFastCheckableSelector(canUseFastCheckSelector && SelectorChecker::isFastCheckableSelector(selector()))
+    , m_hasMultipartSelector(!!selector()->tagHistory())
+    , m_hasRightmostSelectorMatchingHTMLBasedOnRuleHash(isSelectorMatchingHTMLBasedOnRuleHash(selector()))
+    , m_containsUncommonAttributeSelector(WebCore::containsUncommonAttributeSelector(selector()))
+    , m_linkMatchType(SelectorChecker::determineLinkMatchType(selector()))
     , m_hasDocumentSecurityOrigin(hasDocumentSecurityOrigin)
     , m_isInRegionRule(inRegionRule)
 {
-    SelectorChecker::collectIdentifierHashes(m_selector, m_descendantSelectorIdentifierHashes, maximumIdentifierCount);
+    ASSERT(m_position == position);
+    ASSERT(m_selectorIndex == selectorIndex);
+    SelectorChecker::collectIdentifierHashes(selector(), m_descendantSelectorIdentifierHashes, maximumIdentifierCount);
 }
 
 void RuleData::reportMemoryUsage(MemoryObjectInfo* memoryObjectInfo) const
@@ -2588,9 +2589,9 @@
             foundSiblingSelector = true;
     }
     if (foundSiblingSelector)
-        features.siblingRules.append(StyleResolver::RuleFeature(ruleData.rule(), ruleData.selector(), ruleData.hasDocumentSecurityOrigin()));
+        features.siblingRules.append(StyleResolver::RuleFeature(ruleData.rule(), ruleData.selectorIndex(), ruleData.hasDocumentSecurityOrigin()));
     if (ruleData.containsUncommonAttributeSelector())
-        features.uncommonAttributeRules.append(StyleResolver::RuleFeature(ruleData.rule(), ruleData.selector(), ruleData.hasDocumentSecurityOrigin()));
+        features.uncommonAttributeRules.append(StyleResolver::RuleFeature(ruleData.rule(), ruleData.selectorIndex(), ruleData.hasDocumentSecurityOrigin()));
 }
     
 void RuleSet::addToRuleSet(AtomicStringImpl* key, AtomRuleMap& map, const RuleData& ruleData)
@@ -2603,11 +2604,13 @@
     rules->append(ruleData);
 }
 
-void RuleSet::addRule(StyleRule* rule, CSSSelector* selector, bool hasDocumentSecurityOrigin, bool canUseFastCheckSelector, bool inRegionRule)
+void RuleSet::addRule(StyleRule* rule, unsigned selectorIndex, bool hasDocumentSecurityOrigin, bool canUseFastCheckSelector, bool inRegionRule)
 {
-    RuleData ruleData(rule, selector, m_ruleCount++, hasDocumentSecurityOrigin, canUseFastCheckSelector, inRegionRule);
+    RuleData ruleData(rule, selectorIndex, m_ruleCount++, hasDocumentSecurityOrigin, canUseFastCheckSelector, inRegionRule);
     collectFeaturesFromRuleData(m_features, ruleData);
 
+    CSSSelector* selector = ruleData.selector();
+
     if (selector->m_match == CSSSelector::Id) {
         addToRuleSet(selector->value().impl(), m_idRules, ruleData);
         return;
@@ -2748,8 +2751,8 @@
 
 void RuleSet::addStyleRule(StyleRule* rule, bool hasDocumentSecurityOrigin, bool canUseFastCheckSelector, bool isInRegionRule)
 {
-    for (CSSSelector* s = rule->selectorList().first(); s; s = CSSSelectorList::next(s))
-        addRule(rule, s, hasDocumentSecurityOrigin, canUseFastCheckSelector, isInRegionRule);
+    for (size_t selectorIndex = 0; selectorIndex != notFound; selectorIndex = rule->selectorList().indexOfNextSelectorAfter(selectorIndex))
+        addRule(rule, selectorIndex, hasDocumentSecurityOrigin, canUseFastCheckSelector, isInRegionRule);
 }
 
 static inline void shrinkMapVectorsToFit(RuleSet::AtomRuleMap& map)

Modified: trunk/Source/WebCore/css/StyleResolver.h (125293 => 125294)


--- trunk/Source/WebCore/css/StyleResolver.h	2012-08-10 16:48:57 UTC (rev 125293)
+++ trunk/Source/WebCore/css/StyleResolver.h	2012-08-10 17:00:40 UTC (rev 125294)
@@ -274,14 +274,14 @@
     void loadPendingResources();
 
     struct RuleFeature {
-        RuleFeature(StyleRule* rule, CSSSelector* selector, bool hasDocumentSecurityOrigin)
+        RuleFeature(StyleRule* rule, unsigned selectorIndex, bool hasDocumentSecurityOrigin)
             : rule(rule)
-            , selector(selector)
+            , selectorIndex(selectorIndex)
             , hasDocumentSecurityOrigin(hasDocumentSecurityOrigin) 
         { 
         }
         StyleRule* rule;
-        CSSSelector* selector;
+        unsigned selectorIndex;
         bool hasDocumentSecurityOrigin;
     };
     struct Features {
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
http://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to