| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org) | 2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org) |
| 3 * (C) 2004-2005 Allan Sandfeld Jensen (kde@carewolf.com) | 3 * (C) 2004-2005 Allan Sandfeld Jensen (kde@carewolf.com) |
| 4 * Copyright (C) 2006, 2007 Nicholas Shanks (webkit@nickshanks.com) | 4 * Copyright (C) 2006, 2007 Nicholas Shanks (webkit@nickshanks.com) |
| 5 * Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All r
ights reserved. | 5 * Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All r
ights reserved. |
| 6 * Copyright (C) 2007 Alexey Proskuryakov <ap@webkit.org> | 6 * Copyright (C) 2007 Alexey Proskuryakov <ap@webkit.org> |
| 7 * Copyright (C) 2007, 2008 Eric Seidel <eric@webkit.org> | 7 * Copyright (C) 2007, 2008 Eric Seidel <eric@webkit.org> |
| 8 * Copyright (C) 2008, 2009 Torch Mobile Inc. All rights reserved. (http://www.t
orchmobile.com/) | 8 * Copyright (C) 2008, 2009 Torch Mobile Inc. All rights reserved. (http://www.t
orchmobile.com/) |
| 9 * Copyright (c) 2011, Code Aurora Forum. All rights reserved. | 9 * Copyright (c) 2011, Code Aurora Forum. All rights reserved. |
| 10 * Copyright (C) Research In Motion Limited 2011. All rights reserved. | 10 * Copyright (C) Research In Motion Limited 2011. All rights reserved. |
| (...skipping 30 matching lines...) Expand all Loading... |
| 41 #include "core/css/StyleSheetContents.h" | 41 #include "core/css/StyleSheetContents.h" |
| 42 #include "core/html/track/TextTrackCue.h" | 42 #include "core/html/track/TextTrackCue.h" |
| 43 #include "platform/weborigin/SecurityOrigin.h" | 43 #include "platform/weborigin/SecurityOrigin.h" |
| 44 | 44 |
| 45 namespace WebCore { | 45 namespace WebCore { |
| 46 | 46 |
| 47 using namespace HTMLNames; | 47 using namespace HTMLNames; |
| 48 | 48 |
| 49 // ----------------------------------------------------------------- | 49 // ----------------------------------------------------------------- |
| 50 | 50 |
| 51 static inline bool isSelectorMatchingHTMLBasedOnRuleHash(const CSSSelector* sele
ctor) | 51 static inline bool isSelectorMatchingHTMLBasedOnRuleHash(const CSSSelector& sele
ctor) |
| 52 { | 52 { |
| 53 ASSERT(selector); | 53 if (selector.m_match == CSSSelector::Tag) { |
| 54 if (selector->m_match == CSSSelector::Tag) { | 54 const AtomicString& selectorNamespace = selector.tagQName().namespaceURI
(); |
| 55 const AtomicString& selectorNamespace = selector->tagQName().namespaceUR
I(); | |
| 56 if (selectorNamespace != starAtom && selectorNamespace != xhtmlNamespace
URI) | 55 if (selectorNamespace != starAtom && selectorNamespace != xhtmlNamespace
URI) |
| 57 return false; | 56 return false; |
| 58 if (selector->relation() == CSSSelector::SubSelector) | 57 if (selector.relation() == CSSSelector::SubSelector) { |
| 59 return isSelectorMatchingHTMLBasedOnRuleHash(selector->tagHistory())
; | 58 ASSERT(selector.tagHistory()); |
| 59 return isSelectorMatchingHTMLBasedOnRuleHash(*selector.tagHistory())
; |
| 60 } |
| 60 return true; | 61 return true; |
| 61 } | 62 } |
| 62 if (SelectorChecker::isCommonPseudoClassSelector(selector)) | 63 if (SelectorChecker::isCommonPseudoClassSelector(selector)) |
| 63 return true; | 64 return true; |
| 64 return selector->m_match == CSSSelector::Id || selector->m_match == CSSSelec
tor::Class; | 65 return selector.m_match == CSSSelector::Id || selector.m_match == CSSSelecto
r::Class; |
| 65 } | 66 } |
| 66 | 67 |
| 67 static inline bool selectorListContainsUncommonAttributeSelector(const CSSSelect
or* selector) | 68 static inline bool selectorListContainsUncommonAttributeSelector(const CSSSelect
or* selector) |
| 68 { | 69 { |
| 69 const CSSSelectorList* selectorList = selector->selectorList(); | 70 const CSSSelectorList* selectorList = selector->selectorList(); |
| 70 if (!selectorList) | 71 if (!selectorList) |
| 71 return false; | 72 return false; |
| 72 for (const CSSSelector* selector = selectorList->first(); selector; selector
= CSSSelectorList::next(selector)) { | 73 for (const CSSSelector* selector = selectorList->first(); selector; selector
= CSSSelectorList::next(*selector)) { |
| 73 for (const CSSSelector* component = selector; component; component = com
ponent->tagHistory()) { | 74 for (const CSSSelector* component = selector; component; component = com
ponent->tagHistory()) { |
| 74 if (component->isAttributeSelector()) | 75 if (component->isAttributeSelector()) |
| 75 return true; | 76 return true; |
| 76 } | 77 } |
| 77 } | 78 } |
| 78 return false; | 79 return false; |
| 79 } | 80 } |
| 80 | 81 |
| 81 static inline bool isCommonAttributeSelectorAttribute(const QualifiedName& attri
bute) | 82 static inline bool isCommonAttributeSelectorAttribute(const QualifiedName& attri
bute) |
| 82 { | 83 { |
| 83 // These are explicitly tested for equality in canShareStyleWithElement. | 84 // These are explicitly tested for equality in canShareStyleWithElement. |
| 84 return attribute == typeAttr || attribute == readonlyAttr; | 85 return attribute == typeAttr || attribute == readonlyAttr; |
| 85 } | 86 } |
| 86 | 87 |
| 87 static inline bool containsUncommonAttributeSelector(const CSSSelector* selector
) | 88 static inline bool containsUncommonAttributeSelector(const CSSSelector& selector
) |
| 88 { | 89 { |
| 89 for (; selector; selector = selector->tagHistory()) { | 90 const CSSSelector* current = &selector; |
| 91 for (; current; current = current->tagHistory()) { |
| 90 // Allow certain common attributes (used in the default style) in the se
lectors that match the current element. | 92 // Allow certain common attributes (used in the default style) in the se
lectors that match the current element. |
| 91 if (selector->isAttributeSelector() && !isCommonAttributeSelectorAttribu
te(selector->attribute())) | 93 if (current->isAttributeSelector() && !isCommonAttributeSelectorAttribut
e(current->attribute())) |
| 92 return true; | 94 return true; |
| 93 if (selectorListContainsUncommonAttributeSelector(selector)) | 95 if (selectorListContainsUncommonAttributeSelector(current)) |
| 94 return true; | 96 return true; |
| 95 if (selector->relation() != CSSSelector::SubSelector) { | 97 if (current->relation() != CSSSelector::SubSelector) { |
| 96 selector = selector->tagHistory(); | 98 current = current->tagHistory(); |
| 97 break; | 99 break; |
| 98 } | 100 } |
| 99 } | 101 } |
| 100 | 102 |
| 101 for (; selector; selector = selector->tagHistory()) { | 103 for (; current; current = current->tagHistory()) { |
| 102 if (selector->isAttributeSelector()) | 104 if (current->isAttributeSelector()) |
| 103 return true; | 105 return true; |
| 104 if (selectorListContainsUncommonAttributeSelector(selector)) | 106 if (selectorListContainsUncommonAttributeSelector(current)) |
| 105 return true; | 107 return true; |
| 106 } | 108 } |
| 107 return false; | 109 return false; |
| 108 } | 110 } |
| 109 | 111 |
| 110 static inline PropertyWhitelistType determinePropertyWhitelistType(const AddRule
Flags addRuleFlags, const CSSSelector* selector) | 112 static inline PropertyWhitelistType determinePropertyWhitelistType(const AddRule
Flags addRuleFlags, const CSSSelector& selector) |
| 111 { | 113 { |
| 112 if (addRuleFlags & RuleIsInRegionRule) | 114 if (addRuleFlags & RuleIsInRegionRule) |
| 113 return PropertyWhitelistRegion; | 115 return PropertyWhitelistRegion; |
| 114 for (const CSSSelector* component = selector; component; component = compone
nt->tagHistory()) { | 116 for (const CSSSelector* component = &selector; component; component = compon
ent->tagHistory()) { |
| 115 if (component->pseudoType() == CSSSelector::PseudoCue || (component->m_m
atch == CSSSelector::PseudoElement && component->value() == TextTrackCue::cueSha
dowPseudoId())) | 117 if (component->pseudoType() == CSSSelector::PseudoCue || (component->m_m
atch == CSSSelector::PseudoElement && component->value() == TextTrackCue::cueSha
dowPseudoId())) |
| 116 return PropertyWhitelistCue; | 118 return PropertyWhitelistCue; |
| 117 } | 119 } |
| 118 return PropertyWhitelistNone; | 120 return PropertyWhitelistNone; |
| 119 } | 121 } |
| 120 | 122 |
| 121 namespace { | 123 namespace { |
| 122 | 124 |
| 123 // FIXME: Should we move this class to WTF? | 125 // FIXME: Should we move this class to WTF? |
| 124 template<typename T> | 126 template<typename T> |
| (...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 187 }; | 189 }; |
| 188 | 190 |
| 189 } | 191 } |
| 190 | 192 |
| 191 RuleData::RuleData(StyleRule* rule, unsigned selectorIndex, unsigned position, A
ddRuleFlags addRuleFlags) | 193 RuleData::RuleData(StyleRule* rule, unsigned selectorIndex, unsigned position, A
ddRuleFlags addRuleFlags) |
| 192 : m_rule(rule) | 194 : m_rule(rule) |
| 193 , m_selectorIndex(selectorIndex) | 195 , m_selectorIndex(selectorIndex) |
| 194 , m_isLastInArray(false) | 196 , m_isLastInArray(false) |
| 195 , m_position(position) | 197 , m_position(position) |
| 196 , m_hasFastCheckableSelector((addRuleFlags & RuleCanUseFastCheckSelector) &&
SelectorCheckerFastPath::canUse(selector())) | 198 , m_hasFastCheckableSelector((addRuleFlags & RuleCanUseFastCheckSelector) &&
SelectorCheckerFastPath::canUse(selector())) |
| 197 , m_specificity(selector()->specificity()) | 199 , m_specificity(selector().specificity()) |
| 198 , m_hasMultipartSelector(!!selector()->tagHistory()) | 200 , m_hasMultipartSelector(!!selector().tagHistory()) |
| 199 , m_hasRightmostSelectorMatchingHTMLBasedOnRuleHash(isSelectorMatchingHTMLBa
sedOnRuleHash(selector())) | 201 , m_hasRightmostSelectorMatchingHTMLBasedOnRuleHash(isSelectorMatchingHTMLBa
sedOnRuleHash(selector())) |
| 200 , m_containsUncommonAttributeSelector(WebCore::containsUncommonAttributeSele
ctor(selector())) | 202 , m_containsUncommonAttributeSelector(WebCore::containsUncommonAttributeSele
ctor(selector())) |
| 201 , m_linkMatchType(SelectorChecker::determineLinkMatchType(selector())) | 203 , m_linkMatchType(SelectorChecker::determineLinkMatchType(selector())) |
| 202 , m_hasDocumentSecurityOrigin(addRuleFlags & RuleHasDocumentSecurityOrigin) | 204 , m_hasDocumentSecurityOrigin(addRuleFlags & RuleHasDocumentSecurityOrigin) |
| 203 , m_propertyWhitelistType(determinePropertyWhitelistType(addRuleFlags, selec
tor())) | 205 , m_propertyWhitelistType(determinePropertyWhitelistType(addRuleFlags, selec
tor())) |
| 204 { | 206 { |
| 205 ASSERT(m_position == position); | 207 ASSERT(m_position == position); |
| 206 ASSERT(m_selectorIndex == selectorIndex); | 208 ASSERT(m_selectorIndex == selectorIndex); |
| 207 SelectorFilter::collectIdentifierHashes(selector(), m_descendantSelectorIden
tifierHashes, maximumIdentifierCount); | 209 SelectorFilter::collectIdentifierHashes(selector(), m_descendantSelectorIden
tifierHashes, maximumIdentifierCount); |
| 208 } | 210 } |
| 209 | 211 |
| 210 void RuleSet::addToRuleSet(StringImpl* key, PendingRuleMap& map, const RuleData&
ruleData) | 212 void RuleSet::addToRuleSet(StringImpl* key, PendingRuleMap& map, const RuleData&
ruleData) |
| 211 { | 213 { |
| 212 if (!key) | 214 if (!key) |
| 213 return; | 215 return; |
| 214 OwnPtr<LinkedStack<RuleData> >& rules = map.add(key, nullptr).iterator->valu
e; | 216 OwnPtr<LinkedStack<RuleData> >& rules = map.add(key, nullptr).iterator->valu
e; |
| 215 if (!rules) | 217 if (!rules) |
| 216 rules = adoptPtr(new LinkedStack<RuleData>); | 218 rules = adoptPtr(new LinkedStack<RuleData>); |
| 217 rules->push(ruleData); | 219 rules->push(ruleData); |
| 218 } | 220 } |
| 219 | 221 |
| 220 bool RuleSet::findBestRuleSetAndAdd(const CSSSelector* component, RuleData& rule
Data) | 222 bool RuleSet::findBestRuleSetAndAdd(const CSSSelector& component, RuleData& rule
Data) |
| 221 { | 223 { |
| 222 if (component->m_match == CSSSelector::Id) { | 224 if (component.m_match == CSSSelector::Id) { |
| 223 addToRuleSet(component->value().impl(), ensurePendingRules()->idRules, r
uleData); | 225 addToRuleSet(component.value().impl(), ensurePendingRules()->idRules, ru
leData); |
| 224 return true; | 226 return true; |
| 225 } | 227 } |
| 226 if (component->m_match == CSSSelector::Class) { | 228 if (component.m_match == CSSSelector::Class) { |
| 227 addToRuleSet(component->value().impl(), ensurePendingRules()->classRules
, ruleData); | 229 addToRuleSet(component.value().impl(), ensurePendingRules()->classRules,
ruleData); |
| 228 return true; | 230 return true; |
| 229 } | 231 } |
| 230 if (component->isCustomPseudoElement()) { | 232 if (component.isCustomPseudoElement()) { |
| 231 addToRuleSet(component->value().impl(), ensurePendingRules()->shadowPseu
doElementRules, ruleData); | 233 addToRuleSet(component.value().impl(), ensurePendingRules()->shadowPseud
oElementRules, ruleData); |
| 232 return true; | 234 return true; |
| 233 } | 235 } |
| 234 if (component->pseudoType() == CSSSelector::PseudoCue) { | 236 if (component.pseudoType() == CSSSelector::PseudoCue) { |
| 235 m_cuePseudoRules.append(ruleData); | 237 m_cuePseudoRules.append(ruleData); |
| 236 return true; | 238 return true; |
| 237 } | 239 } |
| 238 if (SelectorChecker::isCommonPseudoClassSelector(component)) { | 240 if (SelectorChecker::isCommonPseudoClassSelector(component)) { |
| 239 switch (component->pseudoType()) { | 241 switch (component.pseudoType()) { |
| 240 case CSSSelector::PseudoLink: | 242 case CSSSelector::PseudoLink: |
| 241 case CSSSelector::PseudoVisited: | 243 case CSSSelector::PseudoVisited: |
| 242 case CSSSelector::PseudoAnyLink: | 244 case CSSSelector::PseudoAnyLink: |
| 243 m_linkPseudoClassRules.append(ruleData); | 245 m_linkPseudoClassRules.append(ruleData); |
| 244 return true; | 246 return true; |
| 245 case CSSSelector::PseudoFocus: | 247 case CSSSelector::PseudoFocus: |
| 246 m_focusPseudoClassRules.append(ruleData); | 248 m_focusPseudoClassRules.append(ruleData); |
| 247 return true; | 249 return true; |
| 248 default: | 250 default: |
| 249 ASSERT_NOT_REACHED(); | 251 ASSERT_NOT_REACHED(); |
| 250 return true; | 252 return true; |
| 251 } | 253 } |
| 252 } | 254 } |
| 253 | 255 |
| 254 if (component->m_match == CSSSelector::Tag) { | 256 if (component.m_match == CSSSelector::Tag) { |
| 255 if (component->tagQName().localName() != starAtom) { | 257 if (component.tagQName().localName() != starAtom) { |
| 256 // If this is part of a subselector chain, recurse ahead to find a n
arrower set (ID/class.) | 258 // If this is part of a subselector chain, recurse ahead to find a n
arrower set (ID/class.) |
| 257 if (component->relation() == CSSSelector::SubSelector | 259 if (component.relation() == CSSSelector::SubSelector |
| 258 && (component->tagHistory()->m_match == CSSSelector::Class || co
mponent->tagHistory()->m_match == CSSSelector::Id || SelectorChecker::isCommonPs
eudoClassSelector(component->tagHistory())) | 260 && (component.tagHistory()->m_match == CSSSelector::Class || com
ponent.tagHistory()->m_match == CSSSelector::Id || SelectorChecker::isCommonPseu
doClassSelector(*component.tagHistory())) |
| 259 && findBestRuleSetAndAdd(component->tagHistory(), ruleData)) | 261 && findBestRuleSetAndAdd(*component.tagHistory(), ruleData)) |
| 260 return true; | 262 return true; |
| 261 | 263 |
| 262 addToRuleSet(component->tagQName().localName().impl(), ensurePending
Rules()->tagRules, ruleData); | 264 addToRuleSet(component.tagQName().localName().impl(), ensurePendingR
ules()->tagRules, ruleData); |
| 263 return true; | 265 return true; |
| 264 } | 266 } |
| 265 } | 267 } |
| 266 return false; | 268 return false; |
| 267 } | 269 } |
| 268 | 270 |
| 269 void RuleSet::addRule(StyleRule* rule, unsigned selectorIndex, AddRuleFlags addR
uleFlags) | 271 void RuleSet::addRule(StyleRule* rule, unsigned selectorIndex, AddRuleFlags addR
uleFlags) |
| 270 { | 272 { |
| 271 RuleData ruleData(rule, selectorIndex, m_ruleCount++, addRuleFlags); | 273 RuleData ruleData(rule, selectorIndex, m_ruleCount++, addRuleFlags); |
| 272 m_features.collectFeaturesFromRuleData(ruleData); | 274 m_features.collectFeaturesFromRuleData(ruleData); |
| (...skipping 144 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 417 m_universalRules.shrinkToFit(); | 419 m_universalRules.shrinkToFit(); |
| 418 m_pageRules.shrinkToFit(); | 420 m_pageRules.shrinkToFit(); |
| 419 m_viewportRules.shrinkToFit(); | 421 m_viewportRules.shrinkToFit(); |
| 420 m_fontFaceRules.shrinkToFit(); | 422 m_fontFaceRules.shrinkToFit(); |
| 421 m_keyframesRules.shrinkToFit(); | 423 m_keyframesRules.shrinkToFit(); |
| 422 m_treeBoundaryCrossingRules.shrinkToFit(); | 424 m_treeBoundaryCrossingRules.shrinkToFit(); |
| 423 m_shadowDistributedRules.shrinkToFit(); | 425 m_shadowDistributedRules.shrinkToFit(); |
| 424 } | 426 } |
| 425 | 427 |
| 426 } // namespace WebCore | 428 } // namespace WebCore |
| OLD | NEW |