Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(134)

Side by Side Diff: third_party/WebKit/Source/core/css/parser/CSSSelectorParser.cpp

Issue 1587643004: Restrict use of pseudo elements within compound. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@valid-selectors
Patch Set: Workaround for invalid selectors in UA style. Created 4 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "core/css/parser/CSSSelectorParser.h" 5 #include "core/css/parser/CSSSelectorParser.h"
6 6
7 #include "core/css/CSSSelectorList.h" 7 #include "core/css/CSSSelectorList.h"
8 #include "core/css/StyleSheetContents.h" 8 #include "core/css/StyleSheetContents.h"
9 #include "core/frame/UseCounter.h" 9 #include "core/frame/UseCounter.h"
10 #include "platform/RuntimeEnabledFeatures.h" 10 #include "platform/RuntimeEnabledFeatures.h"
(...skipping 145 matching lines...) Expand 10 before | Expand all | Expand 10 after
156 end->setRelationIsAffectedByPseudoContent(); 156 end->setRelationIsAffectedByPseudoContent();
157 previousCompoundHasContentPseudo = compoundHasContentPseudo; 157 previousCompoundHasContentPseudo = compoundHasContentPseudo;
158 end->setTagHistory(selector.release()); 158 end->setTagHistory(selector.release());
159 159
160 selector = nextSelector.release(); 160 selector = nextSelector.release();
161 } 161 }
162 162
163 return selector.release(); 163 return selector.release();
164 } 164 }
165 165
166 namespace {
167
168 bool isScrollbarPseudoClass(CSSSelector::PseudoType pseudo)
169 {
170 switch (pseudo) {
171 case CSSSelector::PseudoEnabled:
172 case CSSSelector::PseudoDisabled:
173 case CSSSelector::PseudoHover:
174 case CSSSelector::PseudoActive:
175 case CSSSelector::PseudoHorizontal:
176 case CSSSelector::PseudoVertical:
177 case CSSSelector::PseudoDecrement:
178 case CSSSelector::PseudoIncrement:
179 case CSSSelector::PseudoStart:
180 case CSSSelector::PseudoEnd:
181 case CSSSelector::PseudoDoubleButton:
182 case CSSSelector::PseudoSingleButton:
183 case CSSSelector::PseudoNoButton:
184 case CSSSelector::PseudoCornerPresent:
185 case CSSSelector::PseudoWindowInactive:
186 return true;
187 default:
188 return false;
189 }
190 }
191
192 bool isUserActionPseudoClass(CSSSelector::PseudoType pseudo)
193 {
194 switch (pseudo) {
195 case CSSSelector::PseudoHover:
196 case CSSSelector::PseudoFocus:
197 case CSSSelector::PseudoActive:
198 return true;
199 default:
200 return false;
201 }
202 }
203
204 bool isPseudoClassValidAfterPseudoElement(CSSSelector::PseudoType pseudoClass, C SSSelector::PseudoType compoundPseudoElement)
205 {
206 switch (compoundPseudoElement) {
207 case CSSSelector::PseudoResizer:
208 case CSSSelector::PseudoScrollbar:
209 case CSSSelector::PseudoScrollbarCorner:
210 case CSSSelector::PseudoScrollbarButton:
211 case CSSSelector::PseudoScrollbarThumb:
212 case CSSSelector::PseudoScrollbarTrack:
213 case CSSSelector::PseudoScrollbarTrackPiece:
214 return isScrollbarPseudoClass(pseudoClass);
215 case CSSSelector::PseudoSelection:
216 return pseudoClass == CSSSelector::PseudoWindowInactive;
217 case CSSSelector::PseudoWebKitCustomElement:
218 return isUserActionPseudoClass(pseudoClass);
219 default:
220 return false;
221 }
222 }
223
224 bool isSimpleSelectorValidAfterPseudoElement(const CSSParserSelector& simpleSele ctor, CSSSelector::PseudoType compoundPseudoElement)
225 {
226 if (compoundPseudoElement == CSSSelector::PseudoUnknown)
227 return true;
228 if (simpleSelector.match() != CSSSelector::PseudoClass)
229 return false;
230 CSSSelector::PseudoType pseudo = simpleSelector.pseudoType();
231 if (pseudo == CSSSelector::PseudoNot) {
232 ASSERT(simpleSelector.selectorList());
233 ASSERT(simpleSelector.selectorList()->first());
234 ASSERT(!simpleSelector.selectorList()->first()->tagHistory());
235 pseudo = simpleSelector.selectorList()->first()->pseudoType();
236 }
237 return isPseudoClassValidAfterPseudoElement(pseudo, compoundPseudoElement);
238 }
239
240 } // namespace
241
166 PassOwnPtr<CSSParserSelector> CSSSelectorParser::consumeCompoundSelector(CSSPars erTokenRange& range) 242 PassOwnPtr<CSSParserSelector> CSSSelectorParser::consumeCompoundSelector(CSSPars erTokenRange& range)
167 { 243 {
168 OwnPtr<CSSParserSelector> compoundSelector; 244 OwnPtr<CSSParserSelector> compoundSelector;
169 245
170 AtomicString namespacePrefix; 246 AtomicString namespacePrefix;
171 AtomicString elementName; 247 AtomicString elementName;
248 CSSSelector::PseudoType compoundPseudoElement = CSSSelector::PseudoUnknown;
172 if (!consumeName(range, elementName, namespacePrefix)) { 249 if (!consumeName(range, elementName, namespacePrefix)) {
173 compoundSelector = consumeSimpleSelector(range); 250 compoundSelector = consumeSimpleSelector(range);
174 if (!compoundSelector) 251 if (!compoundSelector)
175 return nullptr; 252 return nullptr;
253 if (compoundSelector->match() == CSSSelector::PseudoElement)
254 compoundPseudoElement = compoundSelector->pseudoType();
176 } 255 }
177 if (m_context.isHTMLDocument()) 256 if (m_context.isHTMLDocument())
178 elementName = elementName.lower(); 257 elementName = elementName.lower();
179 258
180 while (OwnPtr<CSSParserSelector> simpleSelector = consumeSimpleSelector(rang e)) { 259 while (OwnPtr<CSSParserSelector> simpleSelector = consumeSimpleSelector(rang e)) {
260 // TODO(rune@opera.com): crbug.com/578131
261 // The UASheetMode check is a work-around to allow this selector in medi aControls(New).css:
262 // video::-webkit-media-text-track-region-container.scrolling
263 if (m_context.mode() != UASheetMode && !isSimpleSelectorValidAfterPseudo Element(*simpleSelector.get(), compoundPseudoElement))
264 return nullptr;
265 if (simpleSelector->match() == CSSSelector::PseudoElement)
266 compoundPseudoElement = simpleSelector->pseudoType();
267
181 if (compoundSelector) 268 if (compoundSelector)
182 compoundSelector = addSimpleSelectorToCompound(compoundSelector.rele ase(), simpleSelector.release()); 269 compoundSelector = addSimpleSelectorToCompound(compoundSelector.rele ase(), simpleSelector.release());
183 else 270 else
184 compoundSelector = simpleSelector.release(); 271 compoundSelector = simpleSelector.release();
185 } 272 }
186 273
187 if (!compoundSelector) { 274 if (!compoundSelector) {
188 AtomicString namespaceURI = determineNamespace(namespacePrefix); 275 AtomicString namespaceURI = determineNamespace(namespacePrefix);
189 if (namespaceURI.isNull()) 276 if (namespaceURI.isNull())
190 return nullptr; 277 return nullptr;
(...skipping 437 matching lines...) Expand 10 before | Expand all | Expand 10 after
628 715
629 if (!splitAfter || !splitAfter->tagHistory()) 716 if (!splitAfter || !splitAfter->tagHistory())
630 return compoundSelector; 717 return compoundSelector;
631 718
632 OwnPtr<CSSParserSelector> secondCompound = splitAfter->releaseTagHistory(); 719 OwnPtr<CSSParserSelector> secondCompound = splitAfter->releaseTagHistory();
633 secondCompound->appendTagHistory(CSSSelector::ShadowPseudo, compoundSelector ); 720 secondCompound->appendTagHistory(CSSSelector::ShadowPseudo, compoundSelector );
634 return secondCompound.release(); 721 return secondCompound.release();
635 } 722 }
636 723
637 } // namespace blink 724 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698